zigbee(cc2530)定位软件的实现

2025-11-19 22:17:09

1、由于是三点定位。  我们需要一个1. 协调器一个 2. 路由器两个 3.终端设备一个

基础知识:协调器负责组网,也可以当设备用,路由器负责转发,也可以当设备用。

1. 协调器 , 和两个路由器 定时 发送心跳包(带有自己的ID 1和2和3)。

2.终端设备 会收到  协调器 和 两个路由器发的心跳包。 取出这三种信号强度。

3. 终端设备 将这 3条信号强度数据发送给 协调器。

4.协调器 接收到这 3条信号强度值传给pc机。pc机进行运算。算出带定位的设备的坐标。(算法参看另一篇经验 “如何用zigbee实现三角立体定位-算法”)

zigbee(cc2530)定位软件的实现

2、协调器 初始化的修改  设置串口功能

void GenericApp_Init( uint8 task_id )

{

   halUARTCfg_t uartConfig; //20131014

  GenericApp_TaskID = task_id;

  GenericApp_NwkState = DEV_INIT;

  GenericApp_TransID = 0;

  // Device hardware initialization can be added here or in main() (Zmain.c).

  // If the hardware is application specific - add it here.

  // If the hardware is other parts of the device add it in main().

  GenericApp_DstAddr.addrMode = (afAddrMode_t)AddrNotPresent;

  GenericApp_DstAddr.endPoint = 0;

  GenericApp_DstAddr.addr.shortAddr = 0;

  // Fill out the endpoint description.

  GenericApp_epDesc.endPoint = GENERICAPP_ENDPOINT;

  GenericApp_epDesc.task_id = &GenericApp_TaskID;

  GenericApp_epDesc.simpleDesc

            = (SimpleDescriptionFormat_t *)&GenericApp_SimpleDesc;

  GenericApp_epDesc.latencyReq = noLatencyReqs;

  // Register the endpoint description with the AF

  afRegister( &GenericApp_epDesc );

  // Register for all key events - This app will handle all key events

  RegisterForKeys( GenericApp_TaskID );

  

  uartConfig.configured = TRUE;//20131014

  uartConfig.baudRate = HAL_UART_BR_115200;

  uartConfig.flowControl = FALSE;

  HalUARTOpen(1, &uartConfig);//20131014

  ZDO_RegisterForZDOMsg( GenericApp_TaskID, End_Device_Bind_rsp );

  ZDO_RegisterForZDOMsg( GenericApp_TaskID, Match_Desc_rsp );

}

zigbee(cc2530)定位软件的实现

3、协调器或者路由器定时6秒发一个心跳包

uint16 GenericApp_ProcessEvent( uint8 task_id, uint16 events )

{

  afIncomingMSGPacket_t *MSGpkt;

  afDataConfirm_t *afDataConfirm;

  // Data Confirmation message fields

  byte sentEP;

  ZStatus_t sentStatus;

  byte sentTransID;       // This should match the value sent

  (void)task_id;  // Intentionally unreferenced parameter

  if ( events & SYS_EVENT_MSG )

  {

    MSGpkt = (afIncomingMSGPacket_t *)osal_msg_receive( GenericApp_TaskID );

    while ( MSGpkt )

    {

      switch ( MSGpkt->hdr.event )

      {

        case ZDO_CB_MSG:

          GenericApp_ProcessZDOMsgs( (zdoIncomingMsg_t *)MSGpkt );

          break;

        case KEY_CHANGE:

          //GenericApp_HandleKeys( ((keyChange_t *)MSGpkt)->state, ((keyChange_t *)MSGpkt)->keys );

          break;

        case AF_DATA_CONFIRM_CMD:

          // This message is received as a confirmation of a data packet sent.

          // The status is of ZStatus_t type [defined in ZComDef.h]

          // The message fields are defined in AF.h

          afDataConfirm = (afDataConfirm_t *)MSGpkt;

          sentEP = afDataConfirm->endpoint;

          sentStatus = afDataConfirm->hdr.status;

          sentTransID = afDataConfirm->transID;

          (void)sentEP;

          (void)sentTransID;

          // Action taken when confirmation is received.

          if ( sentStatus != ZSuccess )

          {

            // The data wasn't delivered -- Do something

          }

          break;

        case AF_INCOMING_MSG_CMD:

          GenericApp_MessageMSGCB( MSGpkt );

          break;

        case ZDO_STATE_CHANGE:

          GenericApp_NwkState = (devStates_t)(MSGpkt->hdr.status);

          if ( (GenericApp_NwkState == DEV_ZB_COORD)

              || (GenericApp_NwkState == DEV_ROUTER)

              || (GenericApp_NwkState == DEV_END_DEVICE) )

          {

            // Start sending "the" message in a regular interval.

            //osal_start_timerEx( GenericApp_TaskID,

                               // GENERICAPP_SEND_MSG_EVT,

                               // GENERICAPP_SEND_MSG_TIMEOUT );

            osal_start_timerEx( GenericApp_TaskID, COORDINATOR_UART_BROADCAST, 6000);  //定时6秒   到了会报COORDINATOR_UART_BROADCAST事件

          }

          

          break;

        default:

          break;

      }

      // Release the memory

      osal_msg_deallocate( (uint8 *)MSGpkt );

      // Next

      MSGpkt = (afIncomingMSGPacket_t *)osal_msg_receive( GenericApp_TaskID );

    }

    // return unprocessed events

    return (events ^ SYS_EVENT_MSG);

  }

  if(events & COORDINATOR_UART_BROADCAST)   //COORDINATOR_UART_BROADCAST  事件产生

  {

      GenericApp_SendTheMessage();

      osal_start_timerEx( GenericApp_TaskID, COORDINATOR_UART_BROADCAST, 6000);

      //osal_msg_deallocate( (uint8 *)MSGpkt );

      // Next

      //MSGpkt = (afIncomingMSGPacket_t *)osal_msg_receive( GenericApp_TaskID );

      return (events ^ COORDINATOR_UART_BROADCAST);

  }

  // Send a message out - This event is generated by a timer

  //  (setup in GenericApp_Init()).

  if ( events & GENERICAPP_SEND_MSG_EVT )

  {

    // Send "the" message

    //GenericApp_SendTheMessage();

    // Setup to send message again

    //osal_start_timerEx( GenericApp_TaskID,

                        //GENERICAPP_SEND_MSG_EVT,

                        //GENERICAPP_SEND_MSG_TIMEOUT );

    // return unprocessed events

    return (events ^ GENERICAPP_SEND_MSG_EVT);

  }

  

#if defined( IAR_ARMCM3_LM )

  // Receive a message from the RTOS queue

  if ( events & GENERICAPP_RTOS_MSG_EVT )

  {

    // Process message from RTOS queue

    //GenericApp_ProcessRtosMessage();

    // return unprocessed events

    return (events ^ GENERICAPP_RTOS_MSG_EVT);

  }

#endif

  // Discard unknown events

  return 0;

}

zigbee(cc2530)定位软件的实现

4、协调器收到设备发送的数据时通过串口发送给PC。四个字节。

static void GenericApp_MessageMSGCB( afIncomingMSGPacket_t *pkt )

{

  //unsigned char buffer[4] = "";

  unsigned char buffer[6] = "";

  switch ( pkt->clusterId )

  {

    case GENERICAPP_CLUSTERID:

      osal_memcpy(buffer,pkt->cmd.Data,4);  //读取收到的数据

      HalUARTWrite(1,buffer,4);    //发给PC。4个数据(ID+rssi+温度)

      break;

  }

}

协调器或者路由器的心跳包发送。

static void GenericApp_SendTheMessage( void )

{

       char theMessageData[]  = "1";  //1为协调器,2为路由一 3 为路由二

       GenericApp_DstAddr.addrMode = (afAddrMode_t)AddrBroadcast;

        GenericApp_DstAddr.addr.shortAddr = NWK_BROADCAST_SHORTADDR_DEVALL;

        GenericApp_DstAddr.endPoint = AF_BROADCAST_ENDPOINT;

        if ( AF_DataRequest( &GenericApp_DstAddr, &GenericApp_epDesc,

                       GENERICAPP_CLUSTERID,

                       (byte)osal_strlen( theMessageData ),

                       (byte *)&theMessageData,

                       &GenericApp_TransID,

                       AF_DISCV_ROUTE, AF_DEFAULT_RADIUS ) == afStatus_SUCCESS )

        {

          int i=0;

          i++;

        }

}

zigbee(cc2530)定位软件的实现

5、终端设备

加了一个读温度函数

//TEMPERATURE SENSOR

int8 readTemp(void)

{

static uint16 reference_voltage;

static uint8 bCalibrate = TRUE;

uint16 value;

int8 temp;

ATEST = 0X01;

TR0 |=0X01;

ADCIF = 0;

ADCCON3= (HAL_ADC_REF_115V | HAL_ADC_DEC_256 | HAL_ADC_CHN_TEMP);

while(!ADCIF);

ADCIF = 0;

value = ADCL;

value |= ((uint16) ADCH) << 8;

value >>= 4;

if(bCalibrate)

{

reference_voltage = value ;

bCalibrate = FALSE ;

}

temp = 22+((value - reference_voltage) /4);

return temp;

}

终端收到路由或者协调器的心跳时就将  ID(1代表协调器,2代表路由一 ,3代表路由二) 和 rssi 和 温度  发给协调器。共四个字节

static void GenericApp_MessageMSGCB( afIncomingMSGPacket_t *pkt )

{

int8 tvalue;

tvalue = readTemp();

  //if(strlen(cmd.Data) == 2)

  unsigned char buffer[6] = "";

  afAddrType_t my_DstAddr;

  osal_memcpy(buffer,pkt->cmd.Data,1);  //读取收到的数据  可能是1,2,3之一

  buffer[1] = pkt->rssi;

  buffer[2] = tvalue/10 + '0';

  buffer[3] = tvalue%10 + '0';

 my_DstAddr.addrMode = (afAddrMode_t)Addr16Bit;////

 my_DstAddr.endPoint = GENERICAPP_ENDPOINT;

 my_DstAddr.addr.shortAddr = 0x0000;

 AF_DataRequest( &my_DstAddr, &GenericApp_epDesc,

  GENERICAPP_CLUSTERID,

  4,

  buffer,

  &GenericApp_TransID,

  AF_DISCV_ROUTE,

  AF_DEFAULT_RADIUS);

}

zigbee(cc2530)定位软件的实现

声明:本网站引用、摘录或转载内容仅供网站访问者交流或参考,不代表本站立场,如存在版权或非法内容,请联系站长删除,联系邮箱:site.kefu@qq.com。
猜你喜欢