您的位置:首页 > 移动开发

ZIGBEE中SerialApp_ProcessEvent分析

2015-12-09 20:04 381 查看

在ZIGBEE中消息处理是在SerialApp_ProcessEvent中,分析一下代码

UINT16 SerialApp_ProcessEvent( uint8 task_id, UINT16 events )
{
(void)task_id;
if ( events & SYS_EVENT_MSG )
{
afIncomingMSGPacket_t *MSGpkt;

while ( (MSGpkt = (afIncomingMSGPacket_t *)osal_msg_receive( SerialApp_TaskID )) )
{
switch ( MSGpkt->hdr.event )
{
case ZDO_CB_MSG:
SerialApp_ProcessZDOMsgs( (zdoIncomingMsg_t *)MSGpkt );
break;

case KEY_CHANGE:
SerialApp_HandleKeys( ((keyChange_t *)MSGpkt)->state, ((keyChange_t *)MSGpkt)->keys );
break;

case AF_INCOMING_MSG_CMD:
SerialApp_ProcessMSGCmd( MSGpkt );
break;
case ZDO_STATE_CHANGE:
SerialApp_NwkState = (devStates_t)(MSGpkt->hdr.status);
if ( (SerialApp_NwkState == DEV_ZB_COORD)
|| (SerialApp_NwkState == DEV_ROUTER)
|| (SerialApp_NwkState == DEV_END_DEVICE) )
{
#if defined(ZDO_COORDINATOR)
Broadcast_DstAddr.addrMode = (afAddrMode_t)AddrBroadcast;
Broadcast_DstAddr.endPoint = SERIALAPP_ENDPOINT;
Broadcast_DstAddr.addr.shortAddr = 0xFFFF;
#if UART_DEBUG
PrintAddrInfo( NLME_GetShortAddr(), aExtendedAddress + Z_EXTADDR_LEN - 1);
#endif
for(int i=0; i<MAX_DEVICE; i++)
{
endDevInfo[i].addr=i+1;
}
#else
AfSendAddrInfo();
osal_start_timerEx( SerialApp_TaskID,
SERIALAPP_SEND_PERIODIC_EVT,
SERIALAPP_SEND_PERIODIC_TIMEOUT );
#endif

}
break;
default:
break;
}

osal_msg_deallocate( (uint8 *)MSGpkt );
}

return ( events ^ SYS_EVENT_MSG );
}
if ( events & SERIALAPP_SEND_PERIODIC_EVT )
{
SerialApp_SendPeriodicMessage();

osal_start_timerEx( SerialApp_TaskID, SERIALAPP_SEND_PERIODIC_EVT,
(SERIALAPP_SEND_PERIODIC_TIMEOUT + (osal_rand() & 0x00FF)) );
return (events ^ SERIALAPP_SEND_PERIODIC_EVT);
}
if ( events & SERIALAPP_SEND_EVT )
{
SerialApp_Send();
return ( events ^ SERIALAPP_SEND_EVT );
}
if ( events & SERIALAPP_RESP_EVT )
{
SerialApp_Resp();
return ( events ^ SERIALAPP_RESP_EVT );
}

return ( 0 );
}


在if ( events & SYS_EVENT_MSG )里的都是系统的注册事件,代码中主要有设备状态改变事件(ZDO_CB_MSG),按键按下事件(KEY_CHANGE),接受到无线数据事件(AF_INCOMING_MSG_CMD),网络改变事件(ZDO_STATE_CHANGE)这些ID在ZComDef.h中都有定义,具体可查看手册或数据文档。

而用户在之后的事件:重复发数据(SERIALAPP_SEND_PERIODIC_EVT),串口发送数据(SERIALAPP_SEND_EVT)和重新发送(SERIALAPP_RESP_EVT)中定义数据发送。

SerialApp_ProcessMSGCmd函数中主要是可以添加数据处理,在进行数据加密或功能定义时可在这编写:

在代码中SerialApp_ProcessMSGCmd有两个事件(用户可自定义):

1.接受到了无线数据SERIALAPP_CLUSTERID

2.接受到了无线响应

SERIALAPP_CLUSTERID2

SerialApp_HandleKeys函数中处理按键响应事件:

代码中按键功能大致为:

1.自动匹配:

if ( keys & HAL_KEY_SW_4 )
{
HalLedSet ( HAL_LED_4, HAL_LED_MODE_OFF );
// Initiate a Match Description Request (Service Discovery)
txAddr.addrMode = AddrBroadcast;
txAddr.addr.shortAddr = NWK_BROADCAST_SHORTADDR;
ZDP_MatchDescReq( &txAddr, NWK_BROADCAST_SHORTADDR,
SERIALAPP_PROFID,
SERIALAPP_MAX_CLUSTERS, (cId_t *)SerialApp_ClusterList,
SERIALAPP_MAX_CLUSTERS, (cId_t *)SerialApp_ClusterList,
FALSE );
}


2.绑定协调器:

if ( keys & HAL_KEY_SW_2 )
{
HalLedSet ( HAL_LED_4, HAL_LED_MODE_OFF );
HalUARTWrite(UART1, "S2", 2);
// Initiate an End Device Bind Request for the mandatory endpoint
txAddr.addrMode = Addr16Bit;
txAddr.addr.shortAddr = 0x0000; // Coordinator
ZDP_EndDeviceBindReq( &txAddr, NLME_GetShortAddr(),
SerialApp_epDesc.endPoint,
SERIALAPP_PROFID,
SERIALAPP_MAX_CLUSTERS, (cId_t *)SerialApp_ClusterList,
SERIALAPP_MAX_CLUSTERS, (cId_t *)SerialApp_ClusterList,
FALSE );
}


3.终端周期性上报事件:

if ( keys & HAL_KEY_SW_6 )
{
if(SendFlag == 0)
{
SendFlag = 1;
HalLedSet ( HAL_LED_1, HAL_LED_MODE_ON );
osal_start_timerEx( SerialApp_TaskID,
SERIALAPP_SEND_PERIODIC_EVT,
SERIALAPP_SEND_PERIODIC_TIMEOUT );
}
else
{
SendFlag = 0;
HalLedSet ( HAL_LED_1, HAL_LED_MODE_OFF );
osal_stop_timerEx(SerialApp_TaskID, SERIALAPP_SEND_PERIODIC_EVT);
}
}


所以在SerialApp_Init函数中,配置了一个按键事件,这样使得终端与协调器自动连接。

ZDO_STATE_CHANGE网络状态改变事件,目的是在绑定后周期性的发送数据:

osal_start_timerEx( SerialApp_TaskID,                            SERIALAPP_SEND_PERIODIC_EVT,                         SERIALAPP_SEND_PERIODIC_TIMEOUT );


erialApp_TaskID:任务ID

SERIALAPP_SEND_EVT:同一任务下多个事件,事件编号

SERIALAPP_SEND_PERIODIC_TIMEOUT:延时
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: