CC2530:How to achieve high-frequency communication between the terminals and the coordinator

Part Number: CC2530
Other Parts Discussed in Thread: Z-STACK

As a novice user of the CC2530, I recently encountered a problem that I couldn't solve; Firstly, I carried out the work based on three terminals and one coordinator(ZStack-2.5.1). The aim was to achieve voltage acquisition at a rate of 30Hz or higher (at the terminals), and then send the data to the coordinator in a point-to-point manner. The coordinator would then print out the data via the serial port.

Currently, the solution I am adopting is that the coordinator sends AD acquisition commands to the three terminals in a cyclic manner through point-to-point polling; after receiving the data returned by the current terminal, it then sends an AD acquisition command to the next terminal to have it upload the data; if I want to achieve a sampling rate of 30Hz, then the time for one polling cycle (polling the three terminals) by the coordinator needs to be 30ms; however, at present, the time for the coordinator to poll all three terminals is approximately 100ms (as shown in the figure1).

I have tried many methods, including modifying the parameters in files such as f8wCoord.cfg, f8wConfig.cfg and f8wEndev.cfg(as shown in the figure2,3,4). Eventually, I could only increase the sampling rate to around 10Hz.Below, I have provided the core code for implementing this function.
I really need everyone's help to solve this problem. If you could offer me some suggestions, I would be extremely grateful.

 figure2figure3figure4

/*********************************************************************
 * INCLUDES
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "AF.h"
#include "OnBoard.h"
#include "OSAL_Tasks.h"
#include "SampleApp.h"
#include "ZDApp.h"
#include "ZDObject.h"
#include "ZDProfile.h"

#include "hal_drivers.h"
#include "hal_key.h"
#if defined ( LCD_SUPPORTED )
  #include "hal_lcd.h"
#endif
#include "hal_led.h"
#include "hal_uart.h"
#include "hal_adc.h"
#include "OSAL_PwrMgr.h"


/*********************************************************************
 * MACROS
 */

/*********************************************************************
 * CONSTANTS
 */

#if !defined( SAMPLE_APP_PORT )
#define SAMPLE_APP_PORT  0
#endif

#if !defined( SAMPLE_APP_BAUD )
  #define SAMPLE_APP_BAUD  HAL_UART_BR_115200
#endif

// When the Rx buf space is less than this threshold, invoke the Rx callback.
#if !defined( SAMPLE_APP_THRESH )
#define SAMPLE_APP_THRESH  64
#endif

#if !defined( SAMPLE_APP_RX_SZ )
#define SAMPLE_APP_RX_SZ  128
#endif

#if !defined( SAMPLE_APP_TX_SZ )
#define SAMPLE_APP_TX_SZ  128
#endif

// Millisecs of idle time after a byte is received before invoking Rx callback.
#if !defined( SAMPLE_APP_IDLE )
#define SAMPLE_APP_IDLE  6
#endif

// Loopback Rx bytes to Tx for throughput testing.
#if !defined( SAMPLE_APP_LOOPBACK )
#define SAMPLE_APP_LOOPBACK  FALSE
#endif

// This is the max byte count per OTA message.
#if !defined( SAMPLE_APP_TX_MAX )
#define SAMPLE_APP_TX_MAX  80
#endif

#define SAMPLE_APP_RSP_CNT  4
#define ADC_CHANNEL_COUNT 5  // 采集5路AD

const uint8 adcChannels[ADC_CHANNEL_COUNT] = 
{
  HAL_ADC_CHANNEL_0,  // P0_0
  HAL_ADC_CHANNEL_4,  // P0_4
  HAL_ADC_CHANNEL_5,  // P0_5
  HAL_ADC_CHANNEL_6,  // P0_6
  HAL_ADC_CHANNEL_7   // P0_7
};

// This list should be filled with Application specific Cluster IDs.
const cId_t SampleApp_ClusterList[SAMPLE_MAX_CLUSTERS] =
{
  SAMPLEAPP_P2P_CLUSTERID,
  SAMPLEAPP_FLASH_CLUSTERID,
  SAMPLEAPP_ADDR_CLUSTERID
};

const SimpleDescriptionFormat_t SampleApp_SimpleDesc =
{
  SAMPLEAPP_ENDPOINT,              //  int   Endpoint;
  SAMPLEAPP_PROFID,                //  uint16 AppProfId[2];
  SAMPLEAPP_DEVICEID,              //  uint16 AppDeviceId[2];
  SAMPLEAPP_DEVICE_VERSION,        //  int   AppDevVer:4;
  SAMPLEAPP_FLAGS,                 //  int   AppFlags:4;
  SAMPLE_MAX_CLUSTERS,          //  byte  AppNumInClusters;
  (cId_t *)SampleApp_ClusterList,  //  byte *pAppInClusterList;
  SAMPLE_MAX_CLUSTERS,          //  byte  AppNumOutClusters;
  (cId_t *)SampleApp_ClusterList   //  byte *pAppOutClusterList;
};

endPointDesc_t SampleApp_epDesc =
{
  SAMPLEAPP_ENDPOINT,
 &SampleApp_TaskID,
  (SimpleDescriptionFormat_t *)&SampleApp_SimpleDesc,
  noLatencyReqs
};

/*********************************************************************
 * TYPEDEFS
 */

/*********************************************************************
 * GLOBAL VARIABLES
 */
devStates_t SampleApp_NwkState;   
uint8 SampleApp_TaskID;           // Task ID for internal task/event processing.
uint8 SampleApp_TransID;  // This is the unique message ID (counter)

/*********************************************************************
 * EXTERNAL VARIABLES
 */

/*********************************************************************
 * EXTERNAL FUNCTIONS
 */

/*********************************************************************
 * LOCAL VARIABLES
 */

static uint8 SampleApp_MsgID;

afAddrType_t SampleApp_Periodic_DstAddr; //广播
afAddrType_t SampleApp_Flash_DstAddr;    //组播
afAddrType_t SampleApp_P2P_DstAddr;      //点播


static afAddrType_t SampleApp_TxAddr;
static uint8 SampleApp_TxSeq;
static uint8 SampleApp_TxBuf[SAMPLE_APP_TX_MAX+1];
static uint8 SampleApp_TxLen;

static afAddrType_t SampleApp_RxAddr;
static uint8 SampleApp_RxSeq;
static uint8 SampleApp_RspBuf[SAMPLE_APP_RSP_CNT];

//重要,定时终端ID
//范围:1~MAX_DEVICE,不同的终端或者协调器,要修改此值
uint8 deviceId = 1;
DEVICES mDevice[MAX_DEVICE];

/*********************************************************************
 * LOCAL FUNCTIONS
 */

static void SampleApp_ProcessMSGCmd( afIncomingMSGPacket_t *pkt );
void SampleApp_CallBack(uint8 port, uint8 event); 
static void SampleApp_Send_ADC_Message( void );
static void floatToStr(float vol, char *result, int maxLen);
static void reverse(char *str, int len);
static void intToStr(int num, char *str, int *index);
void SendMsgToShortAddr(uint8* buff, uint8 len, uint16 addr);
void SendShortAddrToCoor();
void SendAckToCoordinator(void);


#define SAMPLEAPP_CMD_TRIGGER_ADC 0x01  // 触发ADC采集的指令
#define SAMPLEAPP_COORDINATOR 0x0000    // 协调器短地址
#define MAX_CONNECTED_DEVICES 10        // 最大连接设备数
#define CMD_SEND_INTERVAL 5             // 指令发送间隔(ms)
#define RESPONSE_TIMEOUT_MS 1000         // 响应超时时间(ms)


static uint8 connectedDevices[MAX_CONNECTED_DEVICES];  // 存储已连接设备ID
static uint8 deviceCount = 0;                          // 已连接设备数量
static uint8 currentDeviceIndex = 0;                   // 当前轮询的设备索引
static uint8 isCoordinator = FALSE;                    // 是否为协调器
//static uint8 ADsuccess = 0;                    // 是否为协调器
static uint8 isWaitingForResponse = FALSE;             // 新增:是否在等待终端响应
static uint16 currentTargetAddr = 0;                   // 当前发送目标地址

/*********************************************************************
 * @fn      SampleApp_Init
 *
 * @brief   This is called during OSAL tasks' initialization.
 *
 * @param   task_id - the Task ID assigned by OSAL.
 *
 * @return  none
 */
void SampleApp_Init( uint8 task_id )
{
  halUARTCfg_t uartConfig;

  SampleApp_TaskID = task_id;
  SampleApp_RxSeq = 0xC3;
  SampleApp_NwkState = DEV_INIT; 
  SampleApp_TransID = 0;

  MT_UartInit();                  //串口初始化
  MT_UartRegisterTaskID(task_id); //注册串口任务
  afRegister( (endPointDesc_t *)&SampleApp_epDesc );
  RegisterForKeys( task_id );
  osal_pwrmgr_device(PWRMGR_ALWAYS_ON); 
  
    for(uint8 i=0; i<MAX_DEVICE; i++)
  {
    mDevice[i].id=i+1;//1~MAX_DEVICE
    mDevice[i].shortAddr=0;//短地址清0
  }  

 // 初始化已连接设备列表
  memset(connectedDevices, 0, sizeof(connectedDevices));
  deviceCount = 0;
  currentDeviceIndex = 0;
  
  SampleApp_Periodic_DstAddr.addrMode = (afAddrMode_t)AddrBroadcast;//广播
  SampleApp_Periodic_DstAddr.endPoint = SAMPLEAPP_ENDPOINT;
  SampleApp_Periodic_DstAddr.addr.shortAddr = 0xFFFF;

  // Setup for the flash command's destination address - Group 1
  SampleApp_Flash_DstAddr.addrMode = (afAddrMode_t)afAddrGroup;//组播
  SampleApp_Flash_DstAddr.endPoint = SAMPLEAPP_ENDPOINT;
  SampleApp_Flash_DstAddr.addr.shortAddr = SAMPLEAPP_FLASH_GROUP;
  
  SampleApp_P2P_DstAddr.addrMode = (afAddrMode_t)Addr16Bit; //点播 
  SampleApp_P2P_DstAddr.endPoint = SAMPLEAPP_ENDPOINT; 
  SampleApp_P2P_DstAddr.addr.shortAddr = 0x0000;            //发给协调器

  
}

/*********************************************************************
 * @fn      SampleApp_ProcessEvent
 *
 * @brief   Generic Application Task event processor.
 *
 * @param   task_id  - The OSAL assigned task ID.
 * @param   events   - Bit map of events to process.
 *
 * @return  Event flags of all unprocessed events.
 */
UINT16 SampleApp_ProcessEvent( uint8 task_id, UINT16 events )
{
  (void)task_id;  // Intentionally unreferenced parameter
 
  
  if ( events & SYS_EVENT_MSG )
  {
    afIncomingMSGPacket_t *MSGpkt;

    while ( (MSGpkt = (afIncomingMSGPacket_t *)osal_msg_receive( SampleApp_TaskID )) )
    {
      switch ( MSGpkt->hdr.event )
      {
      case AF_INCOMING_MSG_CMD:
        SampleApp_ProcessMSGCmd( MSGpkt );
        break;
        
      case ZDO_STATE_CHANGE:
        SampleApp_NwkState = (devStates_t)(MSGpkt->hdr.status);
        if (SampleApp_NwkState == DEV_ZB_COORD)
        {
            // 标识当前设备为协调器
            isCoordinator = TRUE;
            HalUARTWrite(0, "Coordinator started\r\n", 20);
            
            // 启动设备轮询定时器
            osal_start_timerEx( SampleApp_TaskID,
                             SAMPLEAPP_POLL_DEVICES_EVT,
                              CMD_SEND_INTERVAL );
        }
        else if ((SampleApp_NwkState == DEV_ROUTER) || 
                 (SampleApp_NwkState == DEV_END_DEVICE))
        {
            // 终端设备入网后发送自身ID给协调器
            SendShortAddrToCoor();
            osal_pwrmgr_device(PWRMGR_ALWAYS_ON);
        }
        else
        {
        }
        break;


      default:
        break;
      }

      osal_msg_deallocate( (uint8 *)MSGpkt );
    }

    return ( events ^ SYS_EVENT_MSG );
  }

  // 协调器轮询设备事件
  if ( events & SAMPLEAPP_POLL_DEVICES_EVT && isCoordinator )
  {
    if (deviceCount > 0 && !isWaitingForResponse)
    //if (deviceCount > 0 )
    {
      // 发送ADC采集指令给当前设备
      uint8 cmd = SAMPLEAPP_CMD_TRIGGER_ADC;
      uint16 targetAddr = 0;
      //ADsuccess = 0;
      
      // 查找当前设备的短地址
      for(uint8 i=0; i<MAX_DEVICE; i++)
      {
        if(mDevice[i].id == connectedDevices[currentDeviceIndex])
        {
          targetAddr = mDevice[i].shortAddr;
          break;
        }
      }
      
      // 发送指令
      if(targetAddr != 0)
      {
        char log[32];
        char send[] = "sended\r\n";
        sprintf(log, "Sending ADC cmd to device %d\r\n", connectedDevices[currentDeviceIndex]);
        HalUARTWrite(0, log, strlen(log));
        SendMsgToShortAddr(&cmd, 1, targetAddr);
        //HalUARTWrite(0, send, strlen(send));
        isWaitingForResponse = TRUE;  // 标记为等待响应状态
        currentTargetAddr = targetAddr;  // 保存当前目标地址
        
        // 启动响应超时定时器
        osal_start_timerEx(SampleApp_TaskID, SAMPLEAPP_RESPONSE_TIMEOUT_EVT, RESPONSE_TIMEOUT_MS);
      }
      
      // 更新索引,循环轮询
     currentDeviceIndex = (currentDeviceIndex + 1) % deviceCount;
    }
    
    // 重新启动定时器
      osal_start_timerEx( SampleApp_TaskID,
                       SAMPLEAPP_POLL_DEVICES_EVT,
                       CMD_SEND_INTERVAL );
    
    return (events ^ SAMPLEAPP_POLL_DEVICES_EVT);
  }
  
  // 触发下一个设备轮询
  //if (events & SAMPLEAPP_NEXT_DEVICE_EVT && isCoordinator)
  //{
    // 切换到下一个设备
    //currentDeviceIndex = (currentDeviceIndex + 1) % deviceCount;
    // 触发下一次轮询
    //osal_start_timerEx(SampleApp_TaskID, SAMPLEAPP_POLL_DEVICES_EVT, 5);  // 短延迟后轮询下一个
    //return (events ^ SAMPLEAPP_NEXT_DEVICE_EVT);
  //}

  // 响应超时事件处理
  if (events & SAMPLEAPP_RESPONSE_TIMEOUT_EVT && isCoordinator)
  {
    if (isWaitingForResponse)
    {
      // 超时处理
      char log[64];
      sprintf(log, "Response timeout from device at address 0x%X\r\n", currentTargetAddr);
      HalUARTWrite(0, log, strlen(log));
      
      // 重置等待状态,继续轮询
      isWaitingForResponse = FALSE;
      currentTargetAddr = 0;
      
      // 继续轮询下一个设备
      currentDeviceIndex = (currentDeviceIndex + 1) % deviceCount;
    }
    
    return (events ^ SAMPLEAPP_RESPONSE_TIMEOUT_EVT);
  }

  return ( 0 );  // Discard unknown events.
}

/*********************************************************************
 * @fn      SerialApp_ProcessMSGCmd
 *
 * @brief   Data message processor callback. This function processes
 *          any incoming data - probably from other devices. Based
 *          on the cluster ID, perform the intended action.
 *
 * @param   pkt - pointer to the incoming message packet
 *
 * @return  TRUE if the 'pkt' parameter is being used and will be freed later,
 *          FALSE otherwise.
 */
void SampleApp_ProcessMSGCmd( afIncomingMSGPacket_t *pkt )
{
  uint8 buff[64]={0};
  char addrBuf[6] = {0};

  switch ( pkt->clusterId )
  {
    case SAMPLEAPP_P2P_CLUSTERID: 
      {
        // 协调器接收终端发送的ADC数据
        if(isCoordinator)
        {
          uint16 srcShortAddr = pkt->srcAddr.addr.shortAddr;
          sprintf(addrBuf, "0x%X", srcShortAddr);

          HalUARTWrite(0, "Received data from ", 18);
          HalUARTWrite(0, addrBuf, osal_strlen(addrBuf));
          HalUARTWrite(0, ": ", 2);
          HalUARTWrite(0, pkt->cmd.Data, pkt->cmd.DataLength);
          HalUARTWrite(0, "\r\n", 2);
         
          // 取消超时定时器
          osal_stop_timerEx(SampleApp_TaskID, SAMPLEAPP_RESPONSE_TIMEOUT_EVT);
          isWaitingForResponse = FALSE;
          currentTargetAddr = 0;
          //osal_start_timerEx(SampleApp_TaskID, SAMPLEAPP_NEXT_DEVICE_EVT, 5);  // 短延迟后处理下一个
        }
      }
      break;

    case SAMPLEAPP_FLASH_CLUSTERID:
      // 终端接收协调器的ADC采集指令
      if(pkt->cmd.Data[0] == SAMPLEAPP_CMD_TRIGGER_ADC)
      {
        SendAckToCoordinator();
        // 执行ADC采集并发送给协调器
        SampleApp_Send_ADC_Message();
      }
      break;
    
    case SAMPLEAPP_ADDR_CLUSTERID:
      // 协调器处理终端发送的ID和地址信息
      if(isCoordinator)
      {
        uint8 deviceId = pkt->cmd.Data[0];
        uint16 shortAddr = BUILD_UINT16(pkt->cmd.Data[1], pkt->cmd.Data[2]);
        
        // 存储设备信息
        for(uint8 i=0; i<MAX_DEVICE; i++)
        {
          if(mDevice[i].id == deviceId)
          {
            mDevice[i].shortAddr = shortAddr;
            
            // 如果是新设备,添加到已连接设备列表
            bool isNewDevice = TRUE;
            for(uint8 j=0; j<deviceCount; j++)
            {
              if(connectedDevices[j] == deviceId)
              {
                isNewDevice = FALSE;
                break;
              }
            }
            
            if(isNewDevice && deviceCount < MAX_CONNECTED_DEVICES)
            {
              connectedDevices[deviceCount++] = deviceId;
              char log[32];
              sprintf(log, "New device connected: %d\r\n", deviceId);
              HalUARTWrite(0, log, strlen(log));
            }
            break;
          }
        }
      }
      break;
      
          // 新增:处理终端发送的确认消息
    case SAMPLEAPP_ACK_CLUSTERID:
      if(isCoordinator)
      {
        uint16 srcShortAddr = pkt->srcAddr.addr.shortAddr;
        sprintf(addrBuf, "0x%X", srcShortAddr);
        HalUARTWrite(0, "Received ACK from ", 17);
        HalUARTWrite(0, addrBuf, osal_strlen(addrBuf));
        HalUARTWrite(0, "\r\n", 2);
      }
      break;

    default:
      break;
  }
}


/*********************************************************************
 * @fn      SampleApp_CallBack
 *
 * @brief   Send data OTA.
 *
 * @param   port - UART port.
 * @param   event - the UART port event flag.
 *
 * @return  none
 */
void SampleApp_CallBack(uint8 port, uint8 event)
{
  (void)port;

  if ((event & (HAL_UART_RX_FULL | HAL_UART_RX_ABOUT_FULL | HAL_UART_RX_TIMEOUT)) &&
#if SAMPLE_APP_LOOPBACK
      (SampleApp_TxLen < SAMPLE_APP_TX_MAX))
#else
      !SampleApp_TxLen)
#endif
  {
    SampleApp_TxLen += HalUARTRead(SAMPLE_APP_PORT, SampleApp_TxBuf+SampleApp_TxLen+1,
                                                      SAMPLE_APP_TX_MAX-SampleApp_TxLen);
  }
}


/*********************************************************************
*********************************************************************/

/*********************************************************************
 * @fn      SampleApp_Send_ADC_Message
 *
 * @brief   point to point.
 *
 * @param   none
 *
 * @return  none
 */
void SampleApp_Send_ADC_Message( void )
{
  byte str_adc[64]={0};
  //char *str_adc = "V:";
  float voltages[ADC_CHANNEL_COUNT] = {0.0};  // 存储各通道电压
  uint16 adcValues[ADC_CHANNEL_COUNT] = {0}; // 存储各通道原始值 
  byte len=19;
  //osal_memset(str_adc, ' ', 63);
  
  for (uint8 i = 0; i < ADC_CHANNEL_COUNT; i++) 
  {
    // 读取ADC值(参考电压使用AVDD,即3.3V)
    char str_vol[20] = {0};
    adcValues[i] = HalAdcRead(adcChannels[i], HAL_ADC_RESOLUTION_14);
    if(adcValues[i]>=8192)
    {
      sprintf(str_adc,"error\r\n");
    }
    else
    {// 计算电压(14位ADC,最大值8192)
      voltages[i] = (float)(adcValues[i] * 3.3)/ 8192.0;
      floatToStr(voltages[i], str_vol, sizeof(str_vol));
      strcat(str_vol,"\r\n");
      strcat(str_adc, str_vol);
      //str_adc = concatDynamic(str_adc, str_vol);
    }
  }


  //for (uint8_t i = 0; i < ADC_CHANNEL_COUNT; i++) 
  //{
    // 格式化当前通道数据并追加到字符串
    // 格式:"Vx:1.234 "(x为通道号,保留3位小数)
    //strLen += sprintf(&str_adc[strLen], "V%d:%.3f ", 
    //                 (adcChannels[i] + 1),  // 通道号从1开始显示
      //               voltages[i]);
  //}

  //
  len=osal_strlen(str_adc);//计算长度
  
  // 确保数据发送给协调器
  SampleApp_P2P_DstAddr.addr.shortAddr = SAMPLEAPP_COORDINATOR;

  if ( AF_DataRequest( &SampleApp_P2P_DstAddr, &SampleApp_epDesc,
                       SAMPLEAPP_P2P_CLUSTERID,
                       len,
                       str_adc,
                       &SampleApp_MsgID,
                       AF_DISCV_ROUTE,
                       AF_DEFAULT_RADIUS ) == afStatus_SUCCESS )
  {
   // free(str_adc);  
  }
  else
  {
   //free(str_adc);  // Error occurred in request to send.
  }
}

void SendShortAddrToCoor()
{
    char buff[5]={0};
    afAddrType_t DstAddr;
    uint16 addr=NLME_GetShortAddr();


    //点播,协调器的短地址为0
    DstAddr.addrMode = (afAddrMode_t)Addr16Bit;
    DstAddr.endPoint = SAMPLEAPP_ENDPOINT;
    DstAddr.addr.shortAddr = 0x0;

    //填发送的数据
    buff[0]=deviceId;//第一个字节,终端编号
    buff[1]=LO_UINT16(addr);//第二个字节,终端短地址低字节
    buff[2]=HI_UINT16(addr);//第三个字节,终端短地址高字节
    //
    
    //发送
    if ( AF_DataRequest( &DstAddr, &SampleApp_epDesc,
                       SAMPLEAPP_ADDR_CLUSTERID,
                       3,
                       buff,
                       &SampleApp_TransID,
                       AF_DISCV_ROUTE,
                       AF_DEFAULT_RADIUS ) == afStatus_SUCCESS )
    {
    }
    else
    {
    // Error occurred in request to send.
    }
}

void SendAckToCoordinator(void)
{
    uint8 ackMsg[] = "Received"; // 确认消息内容
    afAddrType_t dstAddr;
    
    dstAddr.addrMode = Addr16Bit;
    dstAddr.endPoint = SAMPLEAPP_ENDPOINT;
    dstAddr.addr.shortAddr = SAMPLEAPP_COORDINATOR; // 目标为协调器
    
    if ( AF_DataRequest(&dstAddr, &SampleApp_epDesc,
                  SAMPLEAPP_ACK_CLUSTERID,
                  sizeof(ackMsg) - 1, // 不包含字符串结束符
                  ackMsg,
                  &SampleApp_TransID,
                  AF_DISCV_ROUTE,
                  AF_DEFAULT_RADIUS) == afStatus_SUCCESS )
    {
    }
    else
    { // Error occurred in request to send.
    }
}

const char* afStatusStr[] = {
  "afStatus_SUCCESS",          // 0: 成功
  "afStatus_FAILED",           // 1: 失败
  "afStatus_INVALID_PARAMETER",// 2: 参数无效
  "afStatus_NO_ROUTE",         // 3: 无路由
  "afStatus_NO_RESOURCES",     // 4: 资源不足
  "afStatus_NOT_SUPPORTED",    // 5: 不支持
  "afStatus_TIMEOUT"           // 6: 超时(根据实际枚举扩展)
  // ... 其他状态码
};

void SendMsgToShortAddr(uint8* buff, uint8 len, uint16 addr)
{
    afAddrType_t DstAddr;
    SampleApp_TransID++; 
    
    //点播
    DstAddr.addrMode = (afAddrMode_t)Addr16Bit;
    DstAddr.endPoint = SAMPLEAPP_ENDPOINT;
    DstAddr.addr.shortAddr = addr;
    
    afStatus_t status = AF_DataRequest( &DstAddr, &SampleApp_epDesc,
                       SAMPLEAPP_FLASH_CLUSTERID,
                       len,
                       buff,
                       &SampleApp_TransID,
                       AF_DISCV_ROUTE,
                       AF_DEFAULT_RADIUS );

    // 准备打印缓冲区(存储状态码和描述)
    char uartBuf[64];
    uint16 bufLen;
    

    //发送
    if ( status == afStatus_SUCCESS )
    {
        char send[] = "sended\r\n";
        HalUARTWrite(0, send, strlen(send)); 
    }
    else
    {
        if (status < sizeof(afStatusStr)/sizeof(afStatusStr[0])) 
        {
          sprintf(uartBuf, "AF_DataRequest status: %d (%s)\r\n", status, afStatusStr[status]);
        } 
        else 
        {
          sprintf(uartBuf, "AF_DataRequest status: %d (Unknown)\r\n", status);
        }
        HalUARTWrite(0, (uint8*)uartBuf, strlen(uartBuf));
    }
}

// 共用体
union FloatUnion {
    float f;
    unsigned char bytes[4]; // float占4字节
};

// 反转字符串
void reverse(char *str, int len) {
    int i = 0, j = len - 1;
    char temp;
    while (i < j) {
        temp = str[i];
        str[i] = str[j];
        str[j] = temp;
        i++;
        j--;
    }
}

// 整数转换
void intToStr(int num, char *str, int *index) {
    int i = 0;
    // 处理0的特殊情况
    if (num == 0) {
        str[(*index)++] = '0';
        return;
    }
    // 提取每一位数字
    while (num != 0) {
        int rem = num % 10;
        str[i++] = (rem > 9) ? (rem - 10) + 'a' : rem + '0';
        num = num / 10;
    }
    // 反转得到正确顺序
    reverse(str + *index, i);
    *index += i;
}

// 浮点数转为字符串
void floatToStr(float vol, char *result, int maxLen) {
    union FloatUnion u;
    u.f = vol;
    int index = 0;

    // 检查缓冲区是否足够
    if (maxLen < 10) { 
        result[0] = '\0';
        return;
    }

    // 处理符号位
    if (vol < 0) {
        result[index++] = '-';
        vol = -vol; // 转为正数处理
    }

    // 分离整数部分和小数部分
    int intPart = (int)vol;
    float fracPart = vol - intPart;

    // 转换整数部分
    intToStr(intPart, result, &index);

    // 添加小数点
    result[index++] = '.';

    // 转换小数部分(保留3位)
    for (int i = 0; i < 3; i++) {
        fracPart *= 10;
        int fracDigit = (int)fracPart;
        result[index++] = fracDigit + '0';
        fracPart -= fracDigit;
    }

    // 添加字符串结束符
    result[index] = '\0';
}

  • 您好,
    POLL_RATE=1(意味着数据轮询间隔为1毫秒)不是有效条目,因此可能使用100毫秒作为最低值。

    由于ZED接收器始终处于开启状态(RFD_RCVC_ALWAYS_ON=TRUE),因此这不是一种低功耗设备,因此您可以广播AD采集命令以立即接收终端数据,而无需等待数据轮询。

    或者您可以使用ZR节点而不是ZED,随时发送单播。否则,我建议ZED以30毫秒的间隔发送数据,而无需等待来自ZC的AD采集命令。

    请注意,Z-Stack 2.5.1是一个已经归档的栈,因此支持有限。

  • 您好,

    非常感谢您的回应,这对我的启发很大,我会按你的建议去尝试不同的解决方案。

    再次对您的帮助表示感谢,祝您生活愉快!