EasyLink_transmitCcaAsync的一些问题

我在使用 EasyLink_transmitCcaAsync这个函数进行周期发送时,在发送几十到几百个包之间时,会发送程序卡死的情况,多次测试,发送包数量不同,但必定出现程序卡死。

平台: simplink的 rfNode工程,根据LBT工程改写发送.

测试方式:  1: 先对node和concentrator分别烧写程序,然后观察两个节点打印信息,发现如上问题  ,然后为了排除变量,修改为 仅仅对node上电,1s发送一个数据包 ,通过串口和LED闪烁观察是否程序卡死。然后通过屏蔽代码方式得到如下现象:

使用代码1进行发送,发送一千多个包,均为卡死

 if (EasyLink_transmit(&currentRadioOperation.easyLinkTxPacket) != EasyLink_Status_Success)
{
      Event_post(radioOperationEventHandle, RADIO_EVENT_SEND_FAIL);
}
else
{
   Event_post(radioOperationEventHandle, RADIO_EVENT_DATA_ACK_RECEIVED);
}

使用代码2进行发送,几十到几百个包后发送卡死现象

if( EasyLink_transmitCcaAsync(&currentRadioOperation.easyLinkTxPacket, lbtCallback) != EasyLink_Status_Success)
{

}

void lbtCallback(EasyLink_Status status)
{
   Event_post(radioOperationEventHandle, RADIO_EVENT_DATA_ACK_RECEIVED);
}

感觉就说  代码1是阻塞发送,代码而是非阻塞发送。请问可能是哪方面的原因呢,使用EasyLink_transmitCcaAsync函数发送就会卡死掉。

非常感谢

4 个回复

  • 您的理解是正确的。
    EasyLink_transmit() Blocking Transmit
    EasyLink_transmitCCAAsync() Non-blocking Transmit with Clear Channel Assessment

    EasyLink_transmit() is blocking and EasyLink_transmitCCAAsync() are non-blocking
    EasyLink_transmit() for a scheduled command, or if TX cannot start
    The EasyLink API does not queue messages so calling another API function while in either EasyLink_transmitCCAAsync() will return EasyLink_Status_Busy_Error

    请问您是否能单步跟踪下到底是卡在哪一行?另外您现在的每包数据量有多大?
  • 回复 Susan Yang:

    这个很难调试,因为死掉的时间不确定,有的时候十几个包,有的时候发几百个包的时候,发包时间现在是1s一次,单包数据在20个字节。

    请问下列代码 是必须的么?

        if(EasyLink_getAbsTime(&absTime) != EasyLink_Status_Success)
        {
        }
        easyLinkTxPacket.absTime = absTime + EasyLink_ms_To_RadioTime(100);

    我观察LBT例程,这些参数貌似是 在发送前进行的延时么

  • 一开始使用rfnode工程,发着发着挂掉,然后我就按照LBT工程修改,发现还是会死掉,代码入下

    /***** Function definitions *****/
    void NodeRadioTask_init(void) {
    
        Task_Params_init(&lbtTaskParams);
        lbtTaskParams.stackSize = RFEASYLINKLBT_TASK_STACK_SIZE;
        lbtTaskParams.priority  = RFEASYLINKLBT_TASK_PRIORITY;
        lbtTaskParams.stack     = (void *)&lbtTaskStack[0];
        lbtTaskParams.arg0      = (UInt)1000000;
        Task_construct(&lbtTask, nodeRadioTaskFunction, &lbtTaskParams, NULL);
    }
    
    //发包回调
    void lbtDoneCb(EasyLink_Status status)
    {
        if (status == EasyLink_Status_Success)
        {
            EasyLink_setCtrl(EasyLink_Ctrl_AsyncRx_TimeOut, EasyLink_ms_To_RadioTime(NORERADIO_RCV_TIMEOUT_TIME_MS));
            /* 打开接收器 */
            if (EasyLink_receiveAsync(rxDoneCallback, 0) != EasyLink_Status_Success)
            {
                //System_abort("EasyLink_receiveAsync failed");
            }
        }
        else if (status == EasyLink_Status_Busy_Error)
        {
        }
        else
        {
        }
    }
    
    static void nodeRadioTaskFunction(UArg arg0, UArg arg1)
    {
        uint32_t absTime;
    
        //创建一个信号
        Semaphore_Params params;
        Error_Block eb;
    
        /* Init params */
        Semaphore_Params_init(&params);
        Error_init(&eb);
        /* Create a semaphore instance */
        lbtDoneSem = Semaphore_create(0, &params, &eb);
        if(lbtDoneSem == NULL)
        {
        }
    
        EasyLink_Params easyLink_params;
        EasyLink_Params_init(&easyLink_params);
        easyLink_params.ui32ModType = EasyLink_Phy_Custom;
        easyLink_params.pGrnFxn = (EasyLink_GetRandomNumber)HalTRNG_GetTRNG;
    
        /* Initialize EasyLink */
        if(EasyLink_init(&easyLink_params) != EasyLink_Status_Success){
        }
    
    //    //读取MAC作为节点地址
         ieee_addr_cpy_to(dmSensorPacket.header.sourceAddress);
    
        while (1)
        {
            Semaphore_pend(lbtDoneSem, BIOS_WAIT_FOREVER);
            EasyLink_transmitCcaAsync(&lbtPacket, lbtDoneCb);
        }
    }
    
    
    //更新数据,传入负载
    uint8_t NodeRadioTask_sendAdcData(uint8_t *data,uint8_t len)
    {
        uint32_t absTime;
        uint8_t i=0;
    
        //目标地址
        memcpy( lbtPacket.dstAddr,concentratorAddress,8);
        //节点地址
        memcpy( lbtPacket.payload, dmSensorPacket.header.sourceAddress,8);
        i+=8;
        //长度
        lbtPacket.payload[i++] = len;
        //负载
        if(len==0 )
          memcpy(lbtPacket.payload+i,data,len);
        i+=len;
        //总长度
        lbtPacket.len = i;
    
        if(EasyLink_getAbsTime(&absTime) != EasyLink_Status_Success)
        {
        }
        lbtPacket.absTime = absTime + EasyLink_ms_To_RadioTime(100);
    
        //发送信号量 发送数据
        Semaphore_post(lbtDoneSem);
        return 1;
    }

    谢谢

  • 你好:

    我使用rfEasyLinkListenBeforeTalk_CC1310_LAUNCHXL_tirtos_ccs这个例程运行,发送回调添加了打印信息,如下代码

    void lbtDoneCb(EasyLink_Status status)
    {
        static uint16_t temp=0;
        Display_printf(hDisplaySerial, 0, 0, "send a pck %d statue:%d\n",temp++,status);
        if (status == EasyLink_Status_Success)
        {
            /* Toggle LED1 to indicate TX */
            PIN_setOutputValue(pinHandle, Board_PIN_LED1, !PIN_getOutputValue(Board_PIN_LED1));
    #if RFEASYLINKLBT_RETRANSMIT_PACKETS
            bAttemptRetransmission = false;
    #endif // RFEASYLINKLBT_RETRANSMIT_PACKETS
        }
        else if (status == EasyLink_Status_Busy_Error)
        {
            /* Toggle LED2 to indicate maximum retries reached */
            PIN_setOutputValue(pinHandle, Board_PIN_LED2, !PIN_getOutputValue(Board_PIN_LED2));
    
    #if RFEASYLINKLBT_RETRANSMIT_PACKETS
            bAttemptRetransmission = true;
    #endif // RFEASYLINKLBT_RETRANSMIT_PACKETS
        }
        else
        {
            /* Toggle LED1 and LED2 to indicate error */
            PIN_setOutputValue(pinHandle, Board_PIN_LED1, !PIN_getOutputValue(Board_PIN_LED1));
            PIN_setOutputValue(pinHandle, Board_PIN_LED2, !PIN_getOutputValue(Board_PIN_LED2));
        }
    
        Semaphore_post(lbtDoneSem);
    }

    然后运行测试,发现当状态返回9,也就是EasyLink_Status_Busy_Error 时,程序死掉了,如下图

    请问是什么原因呢,有没有解决办法呢。