TI E2E™ 英文论坛海量技术问答的中文版全新上线,可点击相关论坛查看,或在站内搜索 “参考译文” 获取。

This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

CC1310: CC1310的rfWakeOnRadioRx例程中如何把RF_runCmd引起的阻塞方式修改为非阻塞方式

Part Number: CC1310

基于此sdk路径下的rfWakeOnRadioRx例程:C:\ti\simplelink_cc13x0_sdk_4_10_03_10\examples\rtos\CC1310_LAUNCHXL\drivers\rfWakeOnRadioRx

其进入低功耗模式使用的是阻塞方式,代码如下:

RF_cmdPropRxSniff.startTime = RF_getCurrentTime();
RF_cmdPropRxSniff.startTime += WOR_WAKE_UP_INTERVAL_RAT_TICKS(WOR_WAKEUPS_PER_SECOND);
/* Schedule RX */
result_Mode = RF_runCmd(rfHandle, (RF_Op*)&RF_cmdPropRxSniff, RF_PriorityNormal, &callback, RF_EventRxEntryDone);

这种阻塞的方式,带来的问题是需要阻塞跑完RF_runCmd后(比如周期设置的是1S,则需要阻塞1S),才允许运行接下来的任务逻辑,导致应用程序不能及时响应。

请问有没有方法把此阻塞方式改为非阻塞方式,且低功耗模式能正常运行?试过RF_runCmd直接改为RF_postCmd是不行的!

  • 您好我们已收到您的问题并反馈,预计将于24小时内给您答复。谢谢!

  • 好的,尽快帮忙看看哈,项目卡住了

  • 您好,我们认为这似乎与无线电命令池中发布的命令数量有关。

    一次最多可发布 8 条命令。 在您给出的示例中,如果您只是将 runCmd () 替换为 postCmd () ,那么在执行命令之前,可能会发布 8 个以上的命令。 而这会导致无线电中出现 CMD_ALLOC_ERROR。 因此需要实现一个逻辑,在该逻辑中,应该在特定的时间段后安排命令。

    请您试试看以上方法对您是否有帮助,如果有问题请联系我,我会持续跟进您的情况。

  • 您好,按你的意思,我对代码做了如下修改,发现功耗未能降下来(2.3mA左右),就是单纯跑RF_postCmd并没有进入理想的低功耗模式。

    if(hal_clock_time_exceed( rf_listen_unix ) > 500) //超时500ms后安排一次命令
    {
           /* Save the current radio time */
          RF_cmdPropRxSniff.startTime = RF_getCurrentTime();
          RF_cmdPropRxSniff.startTime += WOR_WAKE_UP_INTERVAL_RAT_TICKS(WOR_WAKEUPS_PER_SECOND);
          /* Schedule RX */
          result_Mode = RF_postCmd(rfHandle, (RF_Op*)&RF_cmdPropRxSniff, RF_PriorityNormal, &callback, RF_EventRxEntryDone);
          rf_listen_unix = hal_clock_get_system_ms();   //获取系统时间RF_getCurrentTime();
    }
    else
    {
           //sleep(1);
    }

  • 我已将您的问题跟进给工程师,如有答复将尽快回复您。

  • 好的,帮忙跟进一下,感谢!

  • 您好工程师正在查看您的问题,预计回复时间稍晚。感谢理解!

  • 您好,rfWakeOnRadioRx 示例允许用户在每个sniff之间执行活动。

    runCmd () 确实会阻止执行,但注意这只会从 runCmd () 被调用开始进行阻止,直到触发并执行 sniff 命令。

    执行 sniff 命令后则可以执行其他任务。

    如果您在 while 循环中执行其他任务,那下次调用 runCmd () 时将会稍晚,并且更接近 SniffCmd () 的触发器,因此由 runCmd () 阻止的时间会更短。

    下面代码直观显示了这一点:代码中添加了另一个循环,用于切换10次绿色 LED:

        while(1)
        {
            /* Set next wakeup time in the future */
            RF_cmdPropRxSniff.startTime += WOR_WAKE_UP_INTERVAL_RAT_TICKS(WOR_WAKEUPS_PER_SECOND);
    
            /* Schedule RX */
            RF_runCmd(rfHandle, (RF_Op*)&RF_cmdPropRxSniff, RF_PriorityNormal, &callback, RF_EventRxEntryDone);
    
            // sleep 100 ms before toggling Green LED
            usleep(100000);
            // Functional code
            for (i=0; i < 10; i++)
            {
                // Toggle LED for every 10 ms
                PIN_setOutputValue(ledPinHandle, CONFIG_PIN_GLED, !PIN_getOutputValue(CONFIG_PIN_GLED));
                // sleep 10ms
                usleep(10000);
            }

    从上图中您可以看到,我们正在执行 sniffs 之间的切换,它实际上不会增加 sniffs 命令的任何延迟。

    请您查看以上方法对您是否有所帮助,如有其他问题请随时联系我们。

  • 是的,我这边所要反馈的就是这个问题,你们测试的图中明显能看到阻塞周期就是500ms,相当于应用层代码如果想一直翻转LED指示灯,那就会出现中途不连续的情况(在阻塞的情况下不能翻转LED)。问题是能否把阻塞的机制改掉?保证应用逻辑的连续性!

  • 好的收到您的问题,由于工程师外出,预计回复您的时间将在下周。敬请谅解。

  • 您好!你们这周分析出什么结果了吗?

  • 您好,由于我们是将您的问题升级到英文论坛,所以回复您的时间可能较慢。我已通过邮件提醒工程师,非常抱歉让您久等了,如有答复我将尽快回复您。敬请谅解!

  • 您好很抱歉回复晚了。

    阻塞周期并不需要一定是精准的500ms ,阻塞周期从调用 runCmd 时开始,直到触发命令以及 sniff 命令的持续时间。 sniff命令的持续时间通常以微秒为单位。 如果 runCmd () 的调用非常接近实际触发器,那么阻塞时间将更短。

    runCmd () 方法的优点是:如果在触发器之前执行 runCmd () 可以确保阻止应用程序,然后可以在触发器上执行 SniffCmd。

    在使用 postCmd () 时,应用程序需要确保以下内容:

    应用程序不应向 RF 命令队列泛洪,超过 8 个未执行的 postCmds()。 此外,请确保在确切时间执行嗅探 Cmd 的适当触发时间。

  • 感谢耐心解答!但还是没听明白,感觉我们的思路不在一个点上。你说的 ”阻塞周期从调用 runCmd 时开始,直到触发命令以及 sniff 命令的持续时间“ ,这个时间是不是接近500ms?而且在此期间功耗接近休眠功耗2uA ?而且在此接近长达500ms的时间内是有阻塞的不能执行我自己的应用程序?

  • 已将您的问题反馈给工程师,预计答复您的时间为下周。谢谢!

  • runCmd () 在 500ms 的固定周期内不会进行阻塞。

    让我们来检查线路:

    RF_cmdPropRxSniff.startTime += WOR_WAKE_UP_INTERVAL_RAT_TICKS(WOR_WAKEUPS_PER_SECOND);
    RF_runCmd(rfHandle, (RF_Op*)&RF_cmdPropRxSniff, RF_PriorityNormal, &callback, RF_EventRxEntryDone);

    这些线路确保每 500ms 会触发一次 sniff 命令。

    第一种情况:在不做任何更改的情况下来考虑 rfWakeOnRadioRx 应用程序。 在 runCmd () 之后没有太多代码要执行,那么请立即返回上述两行代码。 这会导致 runCmd () 阻塞 500ms。 因为需要在之后500ms 内执行 SniffCmd。

    另一种情况:在整个循环中运行 Cmd () 之后有一些代码行需要执行,执行时间为 400ms。

    由于 SniffCmd 之后要运行 500ms ,runCmd () 将首次在循环中阻塞 500ms。但是我们将执行代码行,而这将花费 400ms。

    然后当您在循环的第二个运行中返回到上述代码行时,之后会仅安排 100ms 的时间。因此runCmd () 块只能持续 100ms。

    当 runCmd () 阻止执行时,不能在此任务上运行任何其他代码。

    当 runCmd () 阻止执行时,通常会进入低功耗模式。

  • 理解您的意思了,还有两个疑问:

    1、如果我的代码行运行时间超过500ms比如600ms,会如何运行?还会定时500ms去自动调用runCmd()吗?

    2、假如我有一个按键短按检测的功能,检测机制是按键中断触发后在应用代码行中持续检测其电平值持续超过10ms就认为短按,但是实际测试中发现每次需要长按超过500ms+10ms的时间才能有效触发按键短按的逻辑。在检测按键的时候我并没有在runCmd()后使用while(1)去一直检测按键的电平值,也就是跟第1点说的不一样,没有使用延时去执行一个任务的机制,请问有什么好方法?

  • 好的收到您的问题,已跟进给工程师,如有答复将尽快回复您。

  • 1、如果我的代码行运行时间超过500ms比如600ms,会如何运行?还会定时500ms去自动调用runCmd()吗?

    在这种情况下, runCmd() 不会在 500ms 时自动执行,而是在调用 runCmd() 时立即执行。 这是因为我们使 startTrigger.pasTrig = 1。 一旦 runCmd() 被执行,就会触发一个过去已经触发的触发器。

    2、假如我有一个按键短按检测的功能,检测机制是按键中断触发后在应用代码行中持续检测其电平值持续超过10ms就认为短按,但是实际测试中发现每次需要长按超过500ms+10ms的时间才能有效触发按键短按的逻辑。在检测按键的时候我并没有在runCmd()后使用while(1)去一直检测按键的电平值,也就是跟第1点说的不一样,没有使用延时去执行一个任务的机制,请问有什么好方法?

    我们建议您可以执行多任务,一个任务运行 Wakeonradio 功能,另一个任务运行按钮按功能。 这时, runCmd () 仅阻止 Wakeonradio 任务,而按钮状态可由另一个任务监控。

    您可以参考以下多任务运行的例子:https://dev.ti.com/tirex/explore/node?node=AM9c0MGM9EMVY4y74SB8VQ__eCfARaV__LATEST

    希望以上回答对您有所帮助,如有其他问题请随时联系我们。

  • 好的,非常感谢您的耐心解答!下面我将进一步测试,有问题再联系您。