zstack学习--绑定确认过程

来源:互联网 发布:知乎 射击游戏 鼠标 编辑:程序博客网 时间:2024/04/29 00:27
注1:本文以CC2430 ZStack-1.4.3-1.2.1里的simpleCollector-simpleSensor为例。
注2:看本文先弄懂绑定基本正确的流程。


simpleSensor端:

 传感节点发送网络,并且加入网络后(此处放到以后分析),就会进入MY_FIND_COLLECTOR_EVT事件,注意事件的位运算操作,MY_FIND_COLLECTOR_EVT属于ZB_USER_EVENTS事件中的一种。按如下的流程:zb_HandleOsalEvent( ) --> zb_BindDevice(),在zb_BindDevice()函数里,会执行如下代码:

{      
   ret = ZB_INVALID_PARAMETER;
        destination.addrMode = Addr16Bit;
        destination.addr.shortAddr = NWK_BROADCAST_SHORTADDR;
        if ( ZDO_AnyClusterMatches( 1, &commandId, sapi_epDesc.simpleDesc->AppNumOutClusters,
                                                sapi_epDesc.simpleDesc->pAppOutClusterList ) )
        {
          // Try to match with a device in the allow bind mode
          ret = ZDP_MatchDescReq( &destination, NWK_BROADCAST_SHORTADDR,
              sapi_epDesc.simpleDesc->AppProfId, 1, &commandId, 0, (cId_t *)NULL, 0 );
        }
        else if ( ZDO_AnyClusterMatches( 1, &commandId, sapi_epDesc.simpleDesc->AppNumInClusters,
                                                sapi_epDesc.simpleDesc->pAppInClusterList ) )
        {
          ret = ZDP_MatchDescReq( &destination, NWK_BROADCAST_SHORTADDR,
              sapi_epDesc.simpleDesc->AppProfId, 0, (cId_t *)NULL, 1, &commandId, 0 );
        }

        if ( ret == ZB_SUCCESS )
        {
          // Set a timer to make sure bind completes
#if ( ZG_BUILD_RTR_TYPE )
          osal_start_timerEx(sapi_TaskID, ZB_BIND_TIMER, AIB_MaxBindingTime);
#else
          // AIB_MaxBindingTime is not defined for an End Device
          osal_start_timerEx(sapi_TaskID, ZB_BIND_TIMER, zgApsDefaultMaxBindingTime);
#endif
          sapi_bindInProgress = commandId;
          return; // dont send cback event

}
需要注意的是ret = ZDP_MatchDescReq( &destination, NWK_BROADCAST_SHORTADDR, sapi_epDesc.simpleDesc->AppProfId,  1, &commandId, 0, (cId_t *)NULL, 0 );本句最终会调用无线发射信号的语句,只要信号发送出去了(不论是否收到,也不管有没有匹配的端点),得到的ret总是为ZB_SUCCESS ,于是总会这一句:osal_start_timerEx(sapi_TaskID, ZB_BIND_TIMER, zgApsDefaultMaxBindingTime);而这一句的作用是发送完绑定请求(匹配描述符请求)后给应用层的一个确认。下面分两种情况来处理ZB_BIND_TIMER事件。

一、绑定不成功
       传感节点将绑定请求信息(匹配描述符请求信息)发送给采集节点后,就会等待采集节点发过来匹配描述符响应事件,如果绑定不成功(原因很多,比如采集节点没有开启允许绑定(zb_AllowBind( 0xFF )),采集节点没有匹配端点),则传感节点收不到匹配描述符响应事件,经过zgApsDefaultMaxBindingTime段时间后,传感节点就会执行ZB_BIND_TIMER事件。依次经过如下流程:SAPI_BindConfirm --> zb_BindConfirm,在zb_BindConfirm函数里,有如下代码
void zb_BindConfirm( uint16 commandId, uint8 status )
{
  if ( ( status == ZB_SUCCESS ) && ( myAppState == APP_START ) )
  {
    myAppState = APP_BOUND;
   
    //Added by jacky 01-12-2015
     HalLedSet( HAL_LED_2, HAL_LED_MODE_ON);
    //Added end.
     
    //Start reporting sensor values
    myApp_StartReporting();
  }
  else
  {
    // Continue to discover a collector
    osal_start_timerEx( sapi_TaskID, MY_FIND_COLLECTOR_EVT, myBindRetryDelay );
  }
}
上面程序会进入else分支,这样又会再次发送MY_FIND_COLLECTOR_EVT,在MY_FIND_COLLECTOR_EVT里,会进入绑定,这样就进入一个不断发送绑定请求的循环。

二、绑定成功
       如果绑定成功,传感节点会收到采集节点发送过来的Match_desp_res(此事件是由谁触发还待进一步确认消息。传感节点程序执行的流程为应用层的SYS_EVENT_MSG --> ZDO_CB_MSG --> SAPI_ProcessZDOMsgs( (zdoIncomingMsg_t *)pMsg ) --> Match_Desc_rsp 在这个事件里,会执行如下这句osal_stop_timerEx(sapi_TaskID,  ZB_BIND_TIMER);这句会将ZB_BIND_TIMER事件取消。紧接着后面有zb_BindConfirm( sapi_bindInProgress, ZB_SUCCESS );

这时会进入If分支,进而通过 myApp_StartReporting();传送数据。

0 0
原创粉丝点击