袁霞+蒲实
摘要:以运行Windows CE7.0操作系统的AM3359主板为开发平台,介绍了AM3359处理器、Windows CE7.0系统架构和硬件接口电路,详细阐述了在嵌入式平台WinCE7.0操作系统中DS1388芯片驱动程序设计原理和实现过程。该软件已应用在某缝制终端系列设备中,为系统提供精准的实时时钟功能。
关键词:AM3359处理器;WinCE7.0;RTC时钟;DS1388芯片
中图分类号:TP319
文献标识码:A
文章编号:16727800(2017)004013504
0引言
当AM3359处理器自带RTC时钟不能满足用户更高要求,或因PMIC输出电压不正常导致RTC功能受到影响时,需要在PCB布局中添加单独的RTC芯片DS1388,直接由电池供电,以保证系统能正确设置、保存、获取实时时间,掉电不消失。对于外接DS1388芯片,AM3359处理器BSP包中自带的RTC驱动程序不能实现DS1388芯片的实时时钟功能,需对RTC时钟驱动重新编写,完成芯片寄存器配置、实时时钟读写以及初始化功能。
1平台介绍
1.1AM3359处理器
AM3359是TI(德州仪器)基于 ARM Cortex-A8内核的32位 RISC微处理器,支持主频275-MHz、500-MHz、600-MHz和 720-MHz,因其价格便宜,支持操作系统齐全等特性,在工业控制、医疗电子、数控、汽车电子等行业的环境恶劣场合中广泛应用[1],功能框架如图1所示。
1.2WinCE7.0操作系统
Windows Embedded Compact 7简称WinCE7.0,是一种安全可靠的实时高性能嵌入式操作系统,其将最新的网络、多媒体和通信技术封装于小型设备中,具有抢占式多任务执行特性和强大的通讯能力。WinCE7拥有Windows 7特点,支持虚拟内存机制,按需分配内存和内存映射文件,专门为信息设备、移动计算、消费类电子产品和嵌入式应用等非PC领域而设计,为不同的应用和设备提供强大的可定制功能。WinCE7作为微软最新一代Windows CE操作系统,提供了新的功能和特性,适用于更为广泛的设备类别和应用场景,为消费者提供更友好的人机界面和用户体验[2]。
基于Windows CE的嵌入式系统采用四层体系结构,具有层次性强、可移植性好、组件可剪裁、强调编程接口和支持上层应用等特点。系统从下而上分为硬件层、OEM 硬件适配层、操作系统服务层、应用层[3],系统架构如图2所示。
OAL部分负责Windows CE与硬件通信,它与CPU、中断、内存、时钟和调试口等核心设备相关,用于屏蔽CPU平台细节,保证操作系统内核的可移植性[3]。RTC时钟驱动在OAL层中开发实现。
DS1388 I2C实时时钟(RTC)、监控器、EEPROM是一个多功能器件,提供时钟/日历、可编程看门狗定时器、具有复位功能的电源监视器和512字节EEPROM。时钟部分可提供百分之一秒、秒、分钟和小时等信息,工作于24小时制式或带AM/PM指示的12小时制式。日历部分提供星期、日、月和年信息。对少于31天的月份,可对月末日期自动调整,包括对闰年的校正。看门狗定时器可对没有响应的微处理器复位。可以以10ms为间隔,在0.01-99.99秒范围内编程。经过温度补偿的电压基准和比较器电路对VCC状态进行监视。如果探测到主电源失效,器件自动切换至备份电源,驱动复位输出为有效状态。在失去VCC情况下,备份电源维持时钟/日历部分继续工作。当VCC恢复至正常电平时,复位输出继续保持为低一段时间,以等待电源和处理器工作稳定。器件还具有一个按键式复位控制器[4],可通过I2C串行接口访问该器件。RTC计算百分秒、秒、分、时、星期、日期、月和年,闰年修正有效期至2100年。
1.4开发环境
本文硬件平台采用英蓓特提供的Devkit8600评估板,对某缝制设备终端订制AMM3359开发板,软件使用Devkit8600提供的BSP包并針对应用进行适配,基于Windows Embedded Compact7操作系统 和Visual Studio 2008进行芯片驱动程序开发。
2硬件接口电路设计
DS1388芯片与 AM3359处理器之间使用I2C总线进行连接通信,芯片的SCL脚和SDA脚分别与处理器的I2C0_SCL脚和I2C0_SDA脚相连,其它外围电路不作描述。硬件接口电路设计如图3所示。
3RTC时钟驱动程序设计与实现
WinCE7.0中 RTC时钟驱动是在OEM接口层即OAL层实现的,其源代码位置在:\\WINCE700\\platform\\common\\src\\soc\\COMMON_TI_V1\\COMMON_TI_AMXX\\OAL\\OALRTC\\oalrtc.c文件中。
3.1工作原理
应用层程序调用操作系统层的应用API,通过OAL层的RTC时钟驱动操作DS1388时钟芯片,通过转码算法达到控制RTC实时时钟目的,详细流程见图4。
3.2I2C总线驱动
处理器外接RTC的时钟芯片通过I2C总线进行访问,本文通过使用I2C总线操作DS1388芯片寄存器,因此需确保I2C总线驱动正常运行。BSP包中I2C驱动已全部实现并通过测试,本文不再详述I2C驱动程序原理和实现过程。
3.3BCD与BIN转码
BIN码就是二进制编码,用二进制记录数据; BCD码亦称二进码十进数或二、十进制代码,就是用4位二进制数表示1位十进制数的编码。最常用的BCD编码使用0-9这10个数值的二进码表示。〖BT3〗3.3.1BCD码转BIN码算法bin = bcd低四位数值+bcd高四位值*10static UINT8 BCDtoBIN(UINT8 bt){ return (bt & 0xf) + (((bt & 0xf0) >> 4)* 10); }
3.3.2BIN码转BCD码算法bcd 高四位= bin/10;bcd 低四位= bin%10static UINT8 BINtoBCD(UINT8 bt){ return (((bt/10) << 4) | (bt % 10));}
3.4時钟设计与实现
在WinCE7.0中,RTC驱动主要实现3个重要函数:①设置当前时间:BOOL OEMSetRealTime( SYSTEMTIME *pSystemTime );②获取当前时间:BOOL OEMGetRealTime(SYSTEMTIME *pSystemTime);③设置报警时间:BOOL OEMSetAlarmTime(SYSTEMTIME *pSystemTime )。本文主要实现当前时间的设置和获取,以及芯片初始化功能[5]。
3.4.1参数宏定义对照DS1388芯片手册,芯片寄存器定义如下:// Global variables#define MILLISECONDS_DS1388 0x0// MilliSeconds Register#define SECONDS_DS1388 0x1// Seconds Register#define MINUTES_DS1388 0x2 // Minutes Register……//定义时、周、天、月、年寄存器地址#define FLAG_REG 0xB// 芯片标识寄存器#define CTRL_REG 0xC// 芯片控制寄存器#define BASE_YEAR_DS1388 2000 //系统初始时间#define MAX_YEARS 99static void *g_hI2C = NULL;OMAP_DEVICE i2cdev = 4 ;//I2C0设备号static UINT16 g_devAddr = 0x0068;//Write Mode,0xD1 :Read Modestatic UINT16 g_baseYear = 2000;
3.4.2设置时钟函数实现
BOOL RTC_SetTime(LPSYSTEMTIME time){ UCHAR cmdBuffer[8]; //依次将年月日、周、天、时分秒等数据从BIN码转变为BCD码 cmdBuffer[SECONDS_DS1388] = (UINT32)BINtoBCD((UINT8)time->wSecond);…… cmdBuffer[WEEK_DS1388] = (UINT32)BINtoBCD((UINT8)time->wDayOfWeek); if( RTCI2CWrite(0,cmdBuffer,8)==FALSE)//通过I2C总线将数据写入芯片寄存器 { OALMSG(1,(L"RTC_SetTime():Failed to write the date/time to the RTC.\\r\\n")); return FALSE; }}
3.4.3获取时钟函数实现
BOOL RTC_GetTime(LPSYSTEMTIME time){ UCHAR receiveBuffer[8]; if (RTCI2CRead(0,receiveBuffer,8) == FALSE) {//通过I2C总线从芯片寄存器中读取当前时间}//将BCD码转变成上层应用识别的BIN码并分别赋值给时间结构体time的各个元素 time->wSecond = BCDtoBIN((UINT8)(receiveBuffer[SECONDS_DS1388] & 0x7F));…… time->wDayOfWeek = BCDtoBIN((UINT8)(receiveBuffer[WEEK_DS1388] & 0x7F)); time->wMilliseconds = 0;; return TRUE;}
3.4.4RTC时钟初始化实现
BOOL OAL3XX_RTCInit(UINT32 rtc_base_pa,DWORD rtc_irq){ OALI2CInit(4);//I2C初始化 g_hI2C = I2COpen(i2cdev);//打开I2C RTCI2CWrite(CTRL_REG,&buf,1); // 设置 DS1388 控制寄存器}
4测试
4.1时钟测试设置
当WinCE启动后,会在界面右下角看到时间显示。在界面中设置时间,系统就会调用OEMSetRealTime将设置的时间写入到RTC模块并保存。测试情况如下: 开机初始化时间为2000.1.1 12:00,如图5所示。设置时间为2016.8.17 8:54:25,保存,如图6所示。 间隔几分钟后再次开机时间为2016.8.17 8:56:35,如图7所示,测试结果表明实时时钟设置运行成功。
4.2时钟测试获取
WinCE启动后,默认情况下系统会每隔一段时间调用OEMGetRealTime函数获得系统时间,这种方式称为hardware mode。同样用户也可以通过调用Windows时钟基本API,即编写测试程序调用OEMGetRealTime获取当前时间,每隔1秒显示一次当前时间,部分代码如下:
void Ctimer_testDlg::OnTimer(UINT_PTR nIDEvent){ SYSTEMTIME Time ,CString str,LPCTSTR lpctstr; GetLocalTime(&Time);//获取当前时间 //显示当前时间 str.Format(_T("%04d.%02d.%02d %02d:%02d:%02d"), Time.wYear,Time.wMonth,Time.wDay, Time.wHour,Time.wMinute,Time.wSecond ); lpctstr = str.GetBuffer(str.GetLength()+1); str.ReleaseBuffer(); SetDlgItemText(IDC_TIME,lpctstr); CDialog::OnTimer(nIDEvent);//实时显示}
测试结果如图8所示。
5结语
本文介绍了WinCE系统结构和RTC时钟工作原理,以外接DS1388 RTC时钟芯片为例,阐述了在AM3359和WinCE7.0平台下,DS1388时钟芯片驱动程序的设计实现过程,并通过设置时间和获取时间测试验证了驱动程序。驱动程序运行稳定可靠,满足设计要求。
参考文献:[1]刘洪涛,邹南.ARM处理器开发详解[M].北京:电子工业出版社,2012.
[2]Texas Instruments.AM335X arm Cortex-A8 mMicroprocessors (MPUs) technical reference manual[Z].Literature Number:SPRUH73H,2011.
[3]尹成,黄永兵,胡耀文,等.Windows CE 7开发实战详解[M].北京:人民邮电出版社,2012.
[4]李红,冯庆胜,曾洁.实时时钟芯片DS1388的原理和应用[J].电子元器件应用,2006(1):7274.
[5]周建设.Windows CE 设备驱动及BSP开发指南[M].北京:中国电力出版社,2009.
(责任编辑:杜能钢)