1、从零开始学习 Zstack 之 1Zstack 情况:本人采用的是 TI 的 Zstack1.4.3 协议,据说这个需要 IAR7.30B 及以上版本,而目前市面上又没有破解,所以用的人很少,这也是我的机会!呵呵!(傻笑有点多,关键是 WORD 里没有表情符号,不能正常表达我此时的心情!)正式开始:开始之前在说一句:从 TI 网站上下载的 Zstack 的方法就不介绍了。否则就是从-1 开始了而不是从 0 开始了-我是这么觉得的!第一步:安装 Zstack从 TI 官方网站上下载的 Zstack 为:swrc072c.zip,我想这个压缩包大家都认识。解压之后为:ZStack- CC2430-
2、1.4.3.exe 文件。这个安装文件大家都会了。默认安装路径为:C:Texas InstrumentsZStack-1.4.3。安装之后在 C:Texas InstrumentsZStack-1.4.3目录下有各 PDF 文档为:Getting Started Guide CC2430.pdf,不用多说,这个肯定是要看的。既然把它放到这么前面,说明它是入门中的入门文档。下面就简单介绍下这个文档:1、 介绍了安装 ZStack-CC2430-1.4.3.exe 需要的硬件软件条件:需要电脑、操作系统为 Windows 2000 或 Windows XP。至于更高或更低版本的本人没有尝试。2、
3、讲了安装流程。这个有点多余了,这年月哪个有电脑的没有安装上百上千次的软件啊?但是需要强调的是安装路径-默认就好!3、 接下来就是让我们看的第一个文档为:Start-Programs-Texas Instruments-ZStack-1.4.3-Z-Stack Users Guide,既然让我看我就来看看这个文档! 第二步:Z-Stack 用户指导这个文档的更新时间为:2007 年 12 月 21 日-应该还是比较新的版本。由于本人英文的却有限,就不翻译了,浏览一遍,把大概意思说下就可以了:1、 介绍1.1、 适用范围本文档适用于 CC2430ZigBee 开发板-CC2430ZDK。2、产品包
4、描述(TI 提供的 CC2430ZDK 工具包)2.1、安装包内容这个就是上面提到的的 ZStack-CC2430-1.4.3.exe 安装之后的所有内容了。说白了就是包含 Zstack 开发所需要的所有软件和文档资料等。2.2、开发板介绍两块 SmartRF04EB 评估版,每个都可以用于 CC2430EM 评估模块。如图 1-1 所示:Figure 1: Chipcon SmartRF04EB Evaluation Board with CC2430EM5 块 CC2430DB 评估板,如图 1-2 所示:Figure 2: Chipcon CC2430DB Development Boa
5、rd10 个 SOC_BB 评估板,每个都可以用于 CC2430EM 或 CC2431EM。如图 1-3 所示:Figure 3: Chipcon SOC_BB Battery Board2.3、电缆也就是包含开发包所需要的电缆,如 RS232 串口线,USB 线等等附属配件。3、安装配置3.1、主机配置一台个人计算机-也就是电脑哈。我想玩嵌入式的应该都有,而现今不过时的配置就可以:下面是最低配置? .NET 1.1 架构? Windows XP Service Pack 1 (i 如果是 Windows XP)? 1 个串口(也就是 RS232 接口)s? 1 USB 接口个人认为要求已经相
6、当低了,如果你的电脑没有这配置,个人强烈建议马上扔掉!不过如今笔记本电脑很少有串口的,所以建议使用台式电脑,而且装机的时候一定要把串口引出,否则就比较麻烦了!3.2、目标板需求其实也是开发环境需求- IAR EW8051。目前需要的版本为 7.30B 及以上。4、产品安装过程4.1、安装 Z-Stack这个也就是安装 ZStack-CC2430-1.4.3.exe 的过程。4.2、IAR 安装一般来说安装选择默认路径,但是自定义路径也不会出问题的。注意 IAR 版本 7.30B 及以上版本才可以运行 1.4.3 协议。4.3、设备 IEEE 地址每个 CC2430DB, CC2430EM,和
7、CC2431EM 都已经排列了一个唯一的 64 位物理地址(IEEE 地址),这个地址已经写到了 CC2430 内部 FLASH 里面,在 CC2430DB, CC2430EM,和 CC2431EM 板的底部有这个地址标签。这个地址被写入到 FLASH 的 0x1FFF8 地址中,注意这个地址也可以更改的,通过些 FLASH软件,一般 0xFFFFFFFFFFFFFFFF 地址被认为是无效地址。5、配置并试用 Z-Stack5.1、配置 Z-Stack这个详见 5.3 节。5.2、逻辑类型这里主要是介绍了 ZIGBEE 协议中的三种设备类型:? ZigBee 协调者(ZC):这个设备被配置为初
8、始化并建立一个 PAN 网络? ZigBee 路由器(ZR):该设备被配置为加入一个存在的网络,可以加入一个协调求或路由器,然后允许其他设备加入它,在网络中路有数据信息。? ZigBee 终端节点 (ZED):该设备被配置为加入一个存在的网络,可以加入一个协调求或路由器。5.3、建立样品应用设备:SampleApp基本上就是采用 SampleApp 应用中的 Demo 例子来演示整个流程,就是采用一个协调器和一个或多个路由器来形成一个 ZigBee 网络演示。在该例子中主要通过 SmartRF04EB 板上的某些跳线来完成设备类型的选型,当然这个方法在程序中是需要判断哪个按键被拉低或拉高,对于
9、做个设计的来说应该是相当好理解的。申明:由于本人很穷,所以没钱买 TI 原装开发包,当然也就没有上面提到的硬件,本人采用的是某家公司(为了避免广告,这里就不说明了)的硬件系统。5.4、建立一个 SampleLight 协调器设备至于提到的硬件连接这里一律省略。无疑:首先要打开对应工程,如图 1-4 所示:图 1-4在工作窗口中选择 DemoEB,如图 1-5 所示:图 1-5然后选择工程菜单(Project)下的全部编译(Rebuild All)选项,如图 1-6 所示:图 1-6然后选择工程菜单(Project)下的调试(Debug)选项,如图 1-7 所示:图 1-7下载完之后就可以退出调
10、试状态,通过选中调试菜单下的停止调试选项,如图 1-8 所示:图 1-8按照此种方法下载至少两个 CC2430EM 模块,就可以进行 Demo 演示了。6、 Z-Stack 示范略至于详细的示范流程,这里先不说了,因为本人采用的硬件与原装有点差异,即使按照这个方法下载仍然不能演示,因为我这个不能用跳线来选择设备类型。所以我必须进入程序把跳线判断程序进行简单必要的修改才能演示。该文档介绍的演示结果及现象都是基于 CHIPCON 原厂评估板。7. PanID 和通道(Channel)选择ZigBee 协议规范规定,一个 14 位的个域网标志符(PAN ID)来标识唯一的一个网络。Z-Stack 可
11、以用两种方式由用户自己选择其 PAN ID,当 ZDAPP_CONFIG_PAN_ID 值设置不为0xFFFF 时,那么设备建立或加入网络的 PAN ID 由 ZDAPP_CONFIG_PAN_ID 指定;如果设置ZDAPP_CONFIG_PAN_ID 为 0xFFFF;那么设备就将建立或加入它发现网络中的“最好”的网络。关于这里提到的“最好”的网络,我觉得可能是有些参数评估,只不过这里没有详细的介绍,在后续文档中应该有介绍的。在 2.4G 频段上,IEEE 802.15.4/ZIGBEE 规范规定了 16 各频道。用户可以通过选择DEFAULT_CHANLIST 不同的值可以选择不同的频道,
12、其频道如图 1-9 所示。改协议默认频道为 0xB 及 0x00000800。图 1-9DEFAULT_CHANLIST 和 ZDAPP_CONFIG_PAN_ID 都作为 IAR IDE 中的编译选项可以进行设置,在应用文件中的ProjectsToolsCC2430DB 目录下的 f8wConfig.cfg 文件中有相应设置,如图 1-10 所示。图 1-10该节到此结束,下节就进入 SampleApp 例程中进行学习!从零开始学习 Zstack 之 2上节基本上初步认识了 Zstack 的一些情况,今天继续我的学习,打开 Sample 例子看看,究竟 ZIGBEE 是怎么回事。毫无疑问:如
13、果是第一次打开这个例子工程,肯定很迷糊,因为此时我迷糊了。对图 2-1我简直是相当迷糊。图 2-1两条路:1 就是先看主函数,2 就是看看 TI 提供例子说明文档没有。我这里先看看主函数再说哈!因为我就知道从主函数看起.没办法大概每个文件夹找啊,主函数的特征还是比较明明显的,见图 2-2 所示:图 2-2下面把主函数复制过来简单看下:ZSEG int main( void )/ Turn off interrupts-关闭中断osal_int_disable( INTS_ALL );/ Initialize HAL-初始化 HAL,关于 HAL 是什么我想后面会有介绍的。HAL_BOARD_I
14、NIT();/ Make sure supply voltage is high enough to run-电压检测,最好是能保证芯片能正常工作的电压zmain_vdd_check();/ Initialize stack memory-初始化 stack 存储区zmain_ram_init();/ Initialize board I/O-初始化板载 IOInitBoard( OB_COLD );/ Initialze HAL drivers-初始化 HAL 驱动HalDriverInit();/ Initialize NV System-初始化 NV 系统,NV 是什么后面我想也会有介绍
15、的osal_nv_init( NULL );/ Determine the extended address-确定扩展地址(64 位 IEEE/物理地址)zmain_ext_addr();/ Initialize basic NV items-初始化基本 NV 条目zgInit();/ Initialize the MAC-初始化 MACZMacInit();#ifndef NONWK/ Since the AF isnt a task, call its initialization routineafInit();#endif/ Initialize the operating syste
16、m-初始化操作系统,看样子这里面还有OS,麻烦了!osal_init_system(); / Allow interrupts-允许中断osal_int_enable( INTS_ALL );/ Final board initialization-最后的版在初始化InitBoard( OB_READY );/ Display information about this device-显示设备信息zmain_dev_info();-液晶支持显示#ifdef LCD_SUPPORTEDzmain_lcd_init();#endifosal_start_system(); / No Return
17、 from here-这里没有返回,大概是进入 OS 了。 / main()可以看到基本上都是初始化函数,因为函数名称都基本上带了 init 字样的,呵呵,个人觉得 TI 的变成习惯比我好,一看名称就知道大概功能了。所以这里也奉劝各位像我这样菜鸟级的初学者,一开始一定就要养成规范化编程的习惯,据说这样维护以及以后升级或者移植兼容性都比较好。我就先不管各个初始化函数是怎么实现的,我先看看各个功能是什么,现掌握整体功能在细化,我觉得这样的学习方法比较好,因为代码是在太多了,从一开始就逐句看,我敢保证没几个人有耐心看完看明白!幸好每个初始化函数都有一句说明,虽然是英文的,但是理解起来一点都不难的。关
18、于每个函数的功能我就直接写在上面的程序里面,节省纸张哈!.一句话:主函数的功能就是初始化!主函数看完了又开始模糊了,又从何看起呢?在无从下手之际,只有去寻求 TI 说明文档的帮助了。上节不是漏掉了内容,是关于演示结果的,这里做上补充,怕因为缺调一点后面遇到什么不理解的就惨了!Sample 例子演示演示现象:1、认识硬件-按键和 LED上节提到了 EM 和 DB 两个板子,其硬件是不一样的。按键 EM 就有 5 各 SW1SW5,而 DB 只有 1 各方向键,但是他们有个对应关系,如图 2-3 所示.图 2-3LED 数量和颜色也不一样,EM 有四个 LED,如图 2-4;而 DB 只有两个,如
19、图 2-5。如图 2-4如图 2-5关于上面几个图 2-4/5 中出现的 LEDx 实际上是程序中出现的关键字。2、初始化 64 位 IEEE 地址实际上在主函数中有这么个初始化函数的:zmain_ext_addr()。这里说如果地址复位为0xFFFFFFFFFFFFFFFF 的话,那么就会不停的闪烁 LED1,一直等到按键 SW5 按下后程序才能继续运行,意思就是说按下 SW5 后就把无效的地址初始化为有效地物理地址了,这个应该是程序上实现的,那么就来看看对应的程序 zmain_ext_addr。static ZSEG void zmain_ext_addr( void )uint8 i;u
20、int8 led;uint8 tmp;uint8 *xad;uint16 AtoD;/ Initialize extended address in NV 初始化 NV 里的扩载地址osal_nv_item_init( ZCD_NV_EXTADDR, Z_EXTADDR_LEN, NULL );osal_nv_read( ZCD_NV_EXTADDR, 0, Z_EXTADDR_LEN, / Check for uninitialized value (erased EEPROM = 0xFF)检查是否为无效值(地址)xad = (uint8*)for ( i = 0; i hdr.event
21、 )这里是判断 SYS_EVENT_MSG 事件类型,不同的 SYS_EVENT_MSG 类型需要不同的处理。case KEY_CHANGE:SampleApp_HandleKeys( (keyChange_t *)MSGpkt)-state,(keyChange_t *)MSGpkt)-keys );break;比如这里判断是否是键盘事件,如果键盘事件就调用键盘处理函数。如果一个 OSAL 任务已经被登记组侧,那么任何键盘事件都将接受一个 KEY_CHANGE 事件信息。可能有如下几种方式得到键盘事件信息1)、HAL 检测到键盘按下(中断或者查询检测)2)、HAL 的 OSAL 任务检测到一
22、个键盘状态改变调用回叫函数产生3)、OSAL 键盘改变回叫函数发送一个 OSAL 系统事件信息(KEY_CHANGE)。case AF_DATA_CONFIRM_CMD:/ The status is of ZStatus_t type defined in ZComDef.h/ The message fields are defined in AF.hafDataConfirm = (afDataConfirm_t *)MSGpkt;sentEP = afDataConfirm-endpoint;sentStatus = afDataConfirm-hdr.status;sentTrans
23、ID = afDataConfirm-transID;任何 AF_DataRequest()数据请求函数调用后,都通过 AF_DATA_CONFIRM_CMD 系统事件信息回叫返回成功 Zsuccess。case ZDO_STATE_CHANGE:SampleApp_NwkState = (devStates_t)(MSGpkt-hdr.status);if ( (SampleApp_NwkState = DEV_ZB_COORD)|(SampleApp_NwkState = DEV_ROUTER)|(SampleApp_NwkState = DEV_END_DEVICE) )/ Update
24、 the LCDs network indicator/ Start sending “the“ message in a regular interval.osal_start_timer( SAMPLEAPP_SEND_PERIODIC_MSG_EVT,SAMPLEAPP_SEND_PERIODIC_MSG_TIMEOUT );break;这里就是前面介绍的设备状态改变事件处理了。只要网络状态发生改变,那么通过 ZDO_STATE_CHANGE 事件通知所有的任务。注意:在这个例子中,一旦设备成功加入网络,是通过定时运行的方式运行的。一旦网络状态为加入”JOINED”,那么它可能不需要任何
25、的认为操作就能绑定其他设备,因为设置为自动发现并绑定的。/ Release the memoryosal_msg_deallocate( (uint8 *)MSGpkt );释放存储空间。if ( events / Setup to send message againosal_start_timer( SAMPLEAPP_SEND_PERIODIC_MSG_EVT,SAMPLEAPP_SEND_MSG_TIMEOUT );/ return unprocessed eventsreturn (events SAMPLEAPP_SEND_PERIODIC_MSG_EVT);这里检测事件是否为周期
26、发送信息事件。在 SampleApp.h 中定义了:#define SAMPLEAPP_SEND_PERIODIC_MSG_EVT 0x0001在这个应用中,调用了 osal_start_timer()函数来定时产生发送周期信息事件。而定时器的运行是设备一旦加入网络就不停的在运行。从上面可以看到,用函数SampleApp_SendPeriodicMessage()发送周期信息,而用函数 osal_start_timer( SAMPLEAPP_SEND_PERIODIC_MSG_EVT,SAMPLEAPP_SEND_MSG_TIMEOUT )来继续运行定时器定时发送这个周期信息。关于这个 osa
27、l_start_timer 可以多了解下,第一个参数 SAMPLEAPP_SEND_PERIODIC_MSG_EVT 四信息时间,也就是事件到了产生一个什么事件。第二各参数 SAMPLEAPP_SEND_MSG_TIMEOUT 是需要定时的时间,这里就是发送周期信息的时间周期。1.3、消息流程通过 OSAL 定时器,这个应用定时发送一个周期信息:void SampleApp_SendPeriodicMessage( void )afAddrType_t dstAddr;dstAddr. addrMode = afAddrBroadcast;dstAddr.addr.shortAddr = 0x
28、FFFF; / 广播发送dstAddr. endpoint = SAMPLEAPP_ENDPOINT;if ( AF_DataRequest( break;这里表示收到某个信息,然后在里面调用了收到信息的信息处理函数SampleApp_MessageMSGCB( MSGpkt )。void SampleApp_MessageMSGCB( afIncomingMSGPacket_t *pkt )switch ( pkt-clusterId )case SAMPLEAPP_PERIODIC_CLUSTERID:/ Display and increment a counter on the LCD
29、 in the periodic spacebreak;case SAMPLEAPP_FLASH_CLUSTERID:flashTime = BUILD_UINT16(pkt-cmd.Data1, pkt-cmd.Data2 );HalLedBlink( HAL_LED_4, 4, 50, (flashTime / 4) );break;这里判断了两种信息:周期信息闪灯信息不同的信息就相当于收到了不同的命令,然后根据不同的命令做出了不同的处理。是个会写程序都明白!到这里,我就基本上把这个应用文档看完了,至于理解了多少我迷糊,理解正确了多少我更加迷糊,反正我按照我自己的方式理解了!从零开始学 Z
30、-Stack 之 5(2009-03-23 20:20:13)标签:it 分类: WSN 学习前面虽然写了不少,但是回头看看大多都是废话,不过也没办法,没有废话的润色就太枯燥了,太技术化了,这个不是我的本意。不知道前面写的怎么样,技术含量肯定是不高的。这个本人是相当清楚,但是我最大的期望就是错误不要太多!突然想起来前面有个问题没有解决,我想很多人看到那里都很郁闷的。就是设备类型的选择,在 TI 原装系统上是通过板载跳线来选择的,但是我这里不是采用原装,那么就需要通过程序来修改其设备类型,然后编译下载。具体程序段如下:#if defined ( SOFT_START )if ( readCoor
31、dinatorJumper() )zgDeviceLogicalType = ZG_DEVICETYPE_COORDINATOR;elsezgDeviceLogicalType = ZG_DEVICETYPE_ROUTER;#endif / SOFT_START这里有个条件编译,其条件编译设置如图 5-1。图 5-1既然这里设置了 SOFT_START,那么上段程序就要被编译。那么第一句程序if ( readCoordinatorJumper() )就是检测跳线,其实稍微知道编程的都了解怎么修改了,哈哈!屏蔽:if ( readCoordinatorJumper() )zgDeviceLogi
32、calType = ZG_DEVICETYPE_COORDINATOR;else这 3 句,那么就只剩下:zgDeviceLogicalType = ZG_DEVICETYPE_ROUTER;了那么编译自然该设备就为路由器了。简单吧!?!协调器我就不想多说怎么做了哈!还有一个问题需要说下,就是 Ti 原装的 EM 板子用到了 LCD,所以在程序中可能在某个地方要对 LCD 初始化,那么如果没有液晶的板子或者与 TI 那个不完全一样的 LCD 就有可能运行不走,通俗的解决办法是禁止 LCD 初始化等操作,Ti 在这个方面做的很人性化,禁止 LCD 功能没有必要在程序中找到 LCD 相关程序删除,而是仅仅需要通过条件编译来禁止。显得相当简单,如 5-2 图就是禁止 LCD 的条件编译。图 5-2解决这个问题后一般都能够运行程序了。也就是说到这里如果还把 Demo 程序运行不起来的话,那就证明我所有的东西都白写了,反正我到这里我的 Demo 程序已经运行如飞了。那么接下来就是来看看 Z-Stack 具体的一些东西了,我打算先这样看起:1、Z-Stack 的结构,因为打开 Z-Stack 的目录可以看出还是比较复杂的,只有比较清楚了解其结构之后呢,在程序运行或者修改中才能顺利的找到自己想要的部分。2、Z-Stack 的应用建立。就是怎么在 TI 提供的协议(裸协议)上建立一个应用。这个层