ZigBee协议栈初始化网络启动流程Word格式.docx
《ZigBee协议栈初始化网络启动流程Word格式.docx》由会员分享,可在线阅读,更多相关《ZigBee协议栈初始化网络启动流程Word格式.docx(12页珍藏版)》请在冰豆网上搜索。
![ZigBee协议栈初始化网络启动流程Word格式.docx](https://file1.bdocx.com/fileroot1/2022-12/13/44b460fd-3c61-437a-875f-2b5c62116b48/44b460fd-3c61-437a-875f-2b5c62116b481.gif)
//InitializeboardI/O
InitBoard(OB_COLD);
//InitialzeHALdrivers
HalDriverInit();
//InitializeNVSystem
osal_nv_init(NULL);
//InitializetheMAC
ZMacInit();
//Determinetheextendedaddress
zmain_ext_addr();
//InitializebasicNVitems
zgInit();
#ifndefNONWK
//SincetheAFisn'
tatask,callit'
sinitializationroutine
afInit();
#endif
//Initializetheoperatingsystem
osal_init_system();
//Allowinterrupts
osal_int_enable(INTS_ALL);
//Finalboardinitialization
InitBoard(OB_READY);
//Displayinformationaboutthisdevice
zmain_dev_info();
/*DisplaythedeviceinfoontheLCD*/
#ifdefLCD_SUPPORTED
zmain_lcd_init();
#ifdefWDT_IN_PM1
/*IfWDTisused,thisisagoodplacetoenableit.*/
WatchDogEnable(WDTIMX);
osal_start_system();
//NoReturnfromhere
return0;
//Shouldn'
tgethere.
}//main()
1.2给任务添加ID
sapi.c中
voidosalInitTasks(void)//为各自进程添加ID用于任务的查找
uint8taskID=0;
tasksEvents=(uint16*)osal_mem_alloc(sizeof(uint16)*tasksCnt);
osal_memset(tasksEvents,0,(sizeof(uint16)*tasksCnt));
macTaskInit(taskID++);
nwk_init(taskID++);
Hal_Init(taskID++);
//硬件抽象层初始化
#ifdefined(MT_TASK)
MT_TaskInit(taskID++);
APS_Init(taskID++);
ZDApp_Init(taskID++);
//判断如果协调器节点建立网络、如果终端节点加入网络
SAPI_Init(taskID);
}
1.3初始化ZigBee协议栈网络
ZDApp.c
voidZDApp_Init(uint8task_id)
//SavethetaskID
ZDAppTaskID=task_id;
//InitializetheZDOglobaldeviceshortaddressstorage
ZDAppNwkAddr.addrMode=Addr16Bit;
ZDAppNwkAddr.addr.shortAddr=INVALID_NODE_ADDR;
(void)NLME_GetExtAddr();
//LoadthesaveExtAddrpointer.
//Checkformanual"
HoldAutoStart"
//检测到有手工设置HAL_KEY_SW_1则会设置devState=DEV_HOLD,从而避开网络初始化
ZDAppCheckForHoldKey();
//InitializeZDOitemsandsetupthedevice-typeofdevicetocreate.
ZDO_Init();
//通过判断预编译来开启一些函数功能
//RegistertheendpointdescriptionwiththeAF
//Thistaskdoesn'
thaveaSimpledescription,butwestillneed
//toregistertheendpoint.
afRegister((endPointDesc_t*)&
ZDApp_epDesc);
#ifdefined(ZDO_USERDESC_RESPONSE)
ZDApp_InitUserDesc();
#endif//ZDO_USERDESC_RESPONSE
//Startthedevice?
if(devState!
=DEV_HOLD)
ZDOInitDevice(0);
else
//BlinkLEDtoindicateHOLD_START
HalLedBlink(HAL_LED_4,0,50,500);
ZDApp_RegisterCBs();
}/*ZDApp_Init()*/
如果设置devState为DEV_HOLD,则不会执行ZDOInitDevice;
反之,系统会调用此函数是设备组网或者入网。
看下这个函数完成的功能是什么样子的。
ZDOInitDevice是设备在网络中启动。
它会读取NV中的ZCD_NV_STARTUP_OPTION选项决定是否恢复网络状态。
如果应用层强制进行新的join操作,它应该在调用这个函数之前设置ZCD_NV_STARTUP_OPTION中的ZCD_STARTOPT_DEFAULT_NETWORK_STATE位。
可以调用zgWrieStartupOptions()函数完成这些设置。
1.4初始化设备(启动网络和设置网络类型)
uint8ZDOInitDevice(uint16startDelay)
uint8networkStateNV=ZDO_INITDEV_NEW_NETWORK_STATE;
uint16extendedDelay=0;
if(devState==DEV_HOLD)
//InitializetheRAMitemstable,incaseanNVitemhasbeenupdated.
zgInitItems(FALSE);
ZDConfig_InitDescriptors();
//devtag.071807.todo-fixthistemporarysolution
_NIB.CapabilityInfo=ZDO_Config_Node_Descriptor.CapabilityFlags;
devState=DEV_INIT;
//RemovetheHoldstate
//函数读取NV项目ZCD_NV_LEAVE_CTRL的值,ZDApp_LeaveCtrl指向这个值
//Initializeleavecontrollogic
ZDApp_LeaveCtrlInit();
//Checkleavecontrolresetsettings//设备的断开会造成DEV_HOLD状态
ZDApp_LeaveCtrlStartup(&
devState,&
startDelay);
//Leavemaymaketheholdstatecomeback
//设置启动选项
//SettheNVstartupoptiontoforcea"
new"
join.
zgWriteStartupOptions(ZG_STARTUP_SET,ZCD_STARTOPT_DEFAULT_NETWORK_STATE);
//通知应用层触发事件
//Notifytheapplications
osal_set_event(ZDAppTaskID,ZDO_STATE_CHANGE_EVT);
return(ZDO_INITDEV_LEAVE_NOT_STARTED);
//Don'
tjoin-(onetime).
#ifdefined(NV_RESTORE)
//GetKeypaddirectlytoseeifaresetnvisneeded.
//HolddowntheSW_BYPASS_NVkey(definedinOnBoard.h)
//whilebootingtoskippastNVRestore.
if(HalKeyRead()==SW_BYPASS_NV)
networkStateNV=ZDO_INITDEV_NEW_NETWORK_STATE;
//通过读取ZCD_NV_STARTUP_OPTION选项决定是否进行网络恢复
//DetermineifNVshouldberestored
networkStateNV=ZDApp_ReadNetworkRestoreState();
if(networkStateNV==ZDO_INITDEV_RESTORED_NETWORK_STATE)
networkStateNV=ZDApp_RestoreNetworkState();
//WipeoutthenetworkstateinNV
NLME_InitNV();
NLME_SetDefaultNV();
if(networkStateNV==ZDO_INITDEV_NEW_NETWORK_STATE)//如果是要启动新的网络
ZDAppDetermineDeviceType();
//根据选项设置设备的网络类型,默认路由类型
//Onlydelayifjoiningnetwork-notrestoringnetworkstate
extendedDelay=(uint16)((NWK_START_DELAY+startDelay)
+(osal_rand()&
EXTENDED_JOINING_RANDOM_MASK));
//Initializethesecurityfortypeofdevice
ZDApp_SecInit(networkStateNV);
//触发启动网络
//Triggerthenetworkstart
ZDApp_NetworkInit(extendedDelay);
//setbroadcastaddressmasktosupportbroadcastfiltering用于处理合法的广播地址
NLME_SetBroadcastFilter(ZDO_Config_Node_Descriptor.CapabilityFlags);
return(networkStateNV);
这个函数注意功能:
初始化设备配置,ZDAppDetermineDeviceType()设置网络类型(协调、路由、终端),ZDApp_NetworkInit(extendedDelay)初始化网络并开启或加入网络。
1.5定时开启网络
进入ZDApp_NetworkInit()函数,等待一段时间在执行ZDO_NETWORK_INIT,跳入事件处理ZDApp层ZDAPP_EVENT_LOOP()函数开启网络。
voidZDApp_NetworkInit(uint16delay)
if(delay)
//Waitawhilebeforestartingthedevice
osal_start_timerEx(ZDAppTaskID,ZDO_NETWORK_INIT,delay);
//发送ZDO_NETWORK_INIT(网络初始化)消息到ZDApp层,转到ZDApp层,ZDApp_event_loop()函数。
osal_set_event(ZDAppTaskID,ZDO_NETWORK_INIT);
1.6启动设备
ZDApp_event_loop()函数是回调函数,循环处理主事件。
设备逻辑类型,启动模式,信标时间,超帧长度
UINT16ZDApp_event_loop(uint8task_id,UINT16events)
uint8*msg_ptr;
if(events&
SYS_EVENT_MSG)
while((msg_ptr=osal_msg_receive(ZDAppTaskID)))
ZDApp_ProcessOSALMsg((osal_event_hdr_t*)msg_ptr);
//Releasethememory
osal_msg_deallocate(msg_ptr);
//Returnunprocessedevents
return(events^SYS_EVENT_MSG);
ZDO_NETWORK_INIT)
//Initializeappsandstartthenetwork
//设备逻辑类型,启动模式,信标时间,超帧长度,接着转到去启动设备,转到ZDO_StartDevice()
ZDO_StartDevice((uint8)ZDO_Config_Node_Descriptor.LogicalType,devStartMode,