ZStack是TI公司为Zigbee量身定做的协议栈
通过到官方下载ZStack安装协议栈,可在C:/Texas Instruments/ZStack中查看到协议栈
目前协议栈已经更新到了3.0.1版本了。我用的是2.4.0-1.4.0版本,因为3.0.1要求IDE版本太高了,我这没更新IDE。
当需要根据协议栈进行开发时,仅需要将协议栈整个复制出来,放入项目目录
将根目录除了Components和Projects之外的文件/文件夹全部删除 是用不到的,有工具和帮助文档
在zstack/Samples中也仅需保留GenericApp这个目录,其余两个可删除
当我们要对GenericApp重命名时,将文件夹重命名成想要重命名的名字
然后进入该目录中的Source中。将3个文件内的GenericApp都替换成你重命名后的名字,保存。
然后将这3个文件的名字中的GenericApp也改成重命名之后的名字。
再进入到CC2530DB中,将GenericApp. 改成 重命名.(4个IAR工程文件)
并将这4个文件中的GenericApp也都替换一下。
eww文件可先改成txt打开替换后再改回eww
之后双击打开,就是重命名好的工程了
在左上角工程上方有个选项卡,可以下拉选择 协调器、路由器、终端
优先使用PRO就可以,功能没太大区别,但PRO更强大
通过在工程中添加模块化的串形数码管文件
将工程设置 c/c++ compiler中的Require prototype钩子取消
在Zmain.c main函数 osal_start_system()前输入初始化数码管的函数。
在APP/GenericApp.c中,有一个ProcessEvent,表示的是进程事件函数。
在ZDO_STATE_CHANGE这个case中,可以确认模块究竟是 协调器、路由器还是终端
在Tools/Config.cfg中
DDEFAULT_CHANLIST可以定义信道。可以将多个信道或操作,对于模块来说就意味着会在多个信道选择最优信道。
DZDAPP_CONFIG_PAN_ID用于定义局域网网号
非0xFFFF时,路由器和终端必须要加入到PANID为此时参数的网络中,如果没有就不加入网络。对于协调器来说,我必须要创建这样一个PANID的网络,如果说一个信道中已经有了该PANID的网络,会在PANID基础上+1创建网络。
如果为0xFFFF时,路由器和终端没有加入网络限制
协调器也会随机生成PANID
在ZStack中按照功能来划分,分为不同层,如物理层、网络层、应用层等
几乎每一个层都是一个任务,系统为每一个任务分配一个一个字节的唯一数值
这个数值叫做任务ID。他们能够处理的事物,叫做事件
处理事务
uint8 osal_set_event(uint8 task_id,uint16 event_flag)
在App/GenericApp.c的Init函数中,第一行就有保存GenericApp_TaskID。通过GenericApp_ProcessEvent中有GENERICAPP_SEND_MSG_EVT这样的event_flag,可以触发一个事件。当然也可以自定义flag。
延时处理事务 等待timeout_value毫秒后处理事务 仅处理一次
uint8 osl_start_timerEx(uint8 taskID,uint16 event_id,uint16 timeout_value)
如何添加自定义事件
一个任务可以定义16个事件
在GenericApp.h中,搜索Application Events 处可增加事件
需要注意的是 事件值转成2进制,16位里只能有1个是1,意味着有效值是从0x0001~0x000F + 0x0010
也就是16个事件可定义
之后再回到.c的GenericApp_ProcessEvent事件处理函数中,新增一个if
if (events & GENERICAPP_YOUR_EVT)
{
// return unprocessed events
return (events ^ GENERICAPP_YOUR_EVT);
}
要注意的是,ZMain会对学习板的硬件路径进行初始化,如果要对LED、串行数码管进行操作时,一定要按标准来设置。(普通IO还是偏上外设、输出还是输入、0还是1)。
如何添加消息
有些时候,16个事件是完全不够用的。ZStack引入了一种消息的概念
当需要应用层任务来处理某个事务时,首先给应用层任务发一个消息
调用osal_set_event,这样一来,应用层就会进入系统事件处理
在事件处理中判断到底产生事件的是哪一种类型的消息
根据消息的类型做相应的处理。
而消息的类型可以自定义,这样一来就打破了16个事件定义的限制。
keyChange_t *msgPtr;
msgPtr=(keyChange_t *)osal_msg_allocate(sizeof(keyChange_t));//定义按钮改变消息
if(msgPtr)
{
msgPtr->hdr.event=KEY_CHANGE;//类型是消息改变
msgPtr->keys=3; //消息内容是3
osal_msg_send(GenericApp_TaskID,(uint8 *)msgPtr);//将消息发送到消息队列(会自动调用osal_set_event( destination_task, SYS_EVENT_MSG ))
}
可以看出,消息只能在SYS_EVENT_MSG这个事件中触发,所以在使用时要注意代码填写的位置。
协议栈的消抖处理
在先前,我们为了写一个按钮的中断,会延时10ms,为了稳定按钮状态。在协议栈中,延时是致命的,会破坏协议栈的栈体运行情况。应该使用延时处理事务方法。不需要担心重复调用的问题,25ms之内再调用,会从0ms重新计时。相当于了消抖效果。
在Hal/Target/CC2530DB/Drivers中保存有各部件的默认中断代码,如果要使用外部引入的 文件的中断,需要将Drivers内的中断给备注掉(HAL_ISR_FUNCTION)
生成hex
在工程属性中
Linker内Output,Override Defaulth和下方的Allow C-SPY-specific extra output file勾选上,在Extra Output中勾选Generate,Override Default,将文件名改成*.hex,下方format改成intel extended,然后在工程Tools/2530.xcl中搜索Include these two lines when generating a .hex file for banked code model:,将该句后两行的注释取消之后编译就有hex生成在工程目录中了。
强势占领沙发~