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.

[参考译文] TMDSCNCD263:如何以100微秒的间隔处理数据

Guru**** 2975150 points

Other Parts Discussed in Thread: TMDSCNCD263, SYSCONFIG

请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/1123677/tmdscncd263-how-to-process-data-at-100usec-intervals

器件型号:TMDSCNCD263
Thread 中讨论的其他器件: SysConfig

我们尝试以100us 的间隔从外部传感器接收数据、并使用 TMDSCNCD263进行处理。

以100usec 的间隔将数据导入到微控制器中时、是否有任何要引用的示例代码?

根据使用互斥量启动固定周期任务的实现、中断中的变量增量与周期任务中的变量增量之间存在差异、单位为100微秒中断频率。

| 5. 49S:CPU 负载= 18.00%
|定时器计数:任务= 50330 / ISR = 50405
| 10. 49S:CPU 负载= 17.91%
|定时器计数:任务= 100327/ ISR = 100405

定时器计数的左侧是周期任务的计数、右侧是中断处理计数。
即使在固定期间任务开始之前错过了时间差、但在50、000次任务中、这一趋势仍将以相同的方式持续。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好

    您能否尝试 使用信标引用 FreeRTOS 任务开关示例。 位置: examples/kernel/freertos/task_switch

    https://software-dl.ti.com/mcu-plus-sdk/esd/AM263X/latest/exports/docs/api_guide_am263x/EXAMPLES_KERNEL_FREERTOS_TASK_SWITCH.html

    此致

    Sri Vidya

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好

    我已经在尝试处理任务切换。

    当在100USEC 周期执行中断处理时、中断处理和稳定状态处理之间的任务处理次数存在差异。

    由于中断处理和稳态处理之间的任务处理量存在差异、我们认为中断处理失败。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好  

    是否可以共享您的代码以供参考?

    [~引脚 userid="46428" URL"/support/microrims/arm-based microrims-group/arm-based microprocessors -group/arm -based microrims/f/arm-based microprocessors -forume/1123677/tmdscncd263-how to -process-data-at -100usec-intervals"]|5。 49S:CPU 负载= 18.00%
    |定时器计数:任务= 50330 / ISR = 50405
    | 10. 49S:CPU 负载= 17.91%
    |计时器计数:任务= 100327 / ISR = 100405[/QUERQ]

    从该打印稿中、我看到 ISR 比任务触发更多的时间。 我假设 ISR 必须从传感器获取数据、任务将处理此数据。

    是否可以 使用 FreeRTOS 事件组和事件位、  

    这样、任务就会等待  来自 ISR 的事件、并且每当 ISR 从传感器获取数据时、它就可以向任务发送信号以将其从等待中唤醒。 -- xEventGroupSetBitsFromISR()。

    因此、获取数据和处理数据都是同步进行的。

    此致

    Sri Vidya

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    附加源代码。

    #include
    #include
    #include "ti_drivers_config.h"
    #include "ti_board_config.h"
    #include "freertos.h"
    #include "task.h"
    /*用于稳态处理的信标*/
    #include
    /*用于中断信标*/
    #include

    #define MAIN_TASK_PRI (CONFIGMAX_Priorities -1)
    #define MAIN_THREAD_PRI (CONFIGMAX_PRIESS-2)

    #define MAIN_TASK_SIZE (16384U/sizeof (configSTACK_DEPTY_TYPE)
    StackType_t gMainTaskStack[main_task_size]__attribute__(aligned (32)));

    StaticTask_t gMainTaskObj;
    TaskHandle_t gMainTask;

    /*线程启动信标*/
    //sys_sem_t gThreadSem;
    StaticSemaphore_t gThreadSemObj;
    SemaphoreHandle_t gThreadSem;

    void enet_lwip_example (void *args);

    void FreeRTOS_MAIN (void * args)
    {
    enet_lwip_example (NULL);

    vTaskDelete (NULL);
    }

    /*周期性线程*/
    StackType_t gThreadStack[main_task_size]__attribute__(aligned (32)));
    StaticTask_t gThreadObj;
    TaskHandle_t gThread;
    void FreeRTOS_thread (void *args);

    int main()
    {
    /*初始化特定于 SOC 的模块*/
    system_init();
    Board_init();

    /*此任务是以最高优先级创建的,它应该创建更多任务,然后删除自己*/
    gMainTask = xTaskCreateStatic( FreeRTOS_MAIN,/*指向实现任务的函数的指针。 *
    "freertos_main"、//任务的文本名称。 这只是为了方便调试。 *
    main_task_size、/*堆栈深度、以 StackType_t 为单位、在32b CPU 上通常为 uint32_t *
    空,//我们不使用任务参数。 *
    MAIN_TASK_PRI、/*任务优先级、0为最低优先级、CONFIGMAX_Priority-1为最高*/
    gMainTaskStack、//指向栈基址的指针*/
    gMainTaskObj );//指向静态分配的任务对象内存的指针*/
    configASBERT (gMainTask!=空);

    /*信号量生成*/
    // err_t err;
    // err = sys_sem_new (&gThreadSem、0);
    // LWIP_assert ("创建 init_sem 失败"、err = ERR_OK);
    /*以下はISR用*/
    gThreadSem = xSemaphoreCreateBinaryStatic (&gThreadSemObj);
    configASBERT (gThreadSem!= NULL);
    vQueueAddToRegistry (gThreadSem、"Thread Sem");//这使得信号量在 CCS IDE 内的 ROV 中可见*/

    /*周期性线程*/
    gThread = xTaskCreateStatic (FreeRTOS_THread、
    "freertos_thread"、
    main_task_size、
    null、
    MAIN_thread_PRI、//优先级高于 MAIN_TASK *
    gThreadStack、
    gThreadObj);
    configASBERT (gThread!= NULL);

    /*启动调度程序以开始执行任务。 *
    vTaskStartScheduler();

    /*永远不应到达以下行,因为 vTaskStartScheduler()
    只有在没有足够的 FreeRTOS 堆内存可用时才会返回
    创建空闲和(如果配置)定时器任务。 堆管理、和
    陷印堆用尽的技术在书籍文本中进行了介绍。 *
    DebugP_assertNoLog (0);

    返回0;
    }

    /* C 运行时包括*/
    #include
    #include
    #include

    /* lwIP 内核包括*/
    #include "lwip/opt.h"
    #include "test_enet_lwip.h"
    #include
    /* SDK 包括*/
    #include "ti_drivers_open_close.h"
    #include "ti_board_open_close.h"
    #include
    #include

    #include

    /*用于中断信标*/
    #include

    extern void Board_cpswMuxSel (void);
    extern void Board_TxRxDelaySet (const EnetBoard_PhyCfg *板 PhyCfg);
    extern uint32_t Board_getEthBoardId (void);
    extern uint32_t Board_getEthType (void);

    /*计时器计数*/
    int gTimerCount;
    int gTimerCountISR;
    /*线程启动信标*/
    //extern sys_sem_t gThreadSem;
    extern StaticSemaphore_t gThreadSemObj;
    extern SemaphoreHandle_t gThreadSem;

    void print_cpu_load()
    {
    静态 uint32_t start_time = 0;
    uint32_t print_interval_in_s = 5;
    uint32_t cur_time = ClockP_getTimeUsec ()/1000;

    if (start_time=0)
    {
    start_time = cur_time;
    }
    其他
    if (cur_time-start_time)>=(print_interval_in_secs*1000)
    {
    uint32_t cpu_load = taskP_loadGetTotalCpuLoad();
    // uint32_t cpu_load = 0;

    DebugP_log ("%6d.%3ds:CPU 负载=%3d.%02d %\r\n"、
    CUR_TIME/1000、cur_time_1000、
    cpu_load/100、cpu_load%100);

    /*计时器处理计数打印*/
    DebugP_log ("计时器计数:任务=%d / ISR =%d\r\n"、
    gTimerCount、gTimerCountISR);

    start_time = cur_time;

    TaskP_loadResetAll();
    }
    }

    void enetApp_initLinkArgs (EnetPer_PortLinkCfg *链接 Args、
    Enet_MacPort macPort)
    {
    EnetPhy_Cfg * phyCfg =&linkArgs->phyCfg;
    EnetMacPort_LinkCfg *linkCfg =&linkArgs->linkCfg;
    EnetMacPort_Interface *MII =&linkArgs->MII;
    EnetBoard_EthPort ethPort;
    const EnetBoard_PhyCfg *板 PhyCfg;
    int32_t status;

    /*请求的以太网端口的设置板*/
    ethPort.instId = 0;
    ethPort.macPort = macPort;
    ethPort.boardId = Board_getEthBoardId();
    ethPort.enetType = Board_getEthType();
    ethPort.MII.layerType = ENET_MAC_LAYER_GMII;
    ethPort.MII.subayerType = ENET_MAC_subayer_Reduced;
    ethPort.MII.variantType = ENET_MAC_variant_forced;

    状态= EnetBoard_setupPorts (&ethPort、1U);
    EnetAppUtils_assert (status =ENET_Sok);

    IF (enet_isCpswFamily (ethPort.enetType))
    {
    CpswMacPort_Cfg * macCfg =(CpswMacPort_Cfg *) linkArgs->macCfg;
    CpswMacPort_initCfg (macCfg);
    IF (EnetMacPort_isSgmii (MII)|| EnetMacPort_isQsgmii (MII))
    {
    macCfg->sgmiiMode = ENET_MAC_SGMIIMODE_SGMII_WIT_PHY;
    }
    其他
    {
    macCfg->sgmiiMode = ENET_MAC_SGMIIMODE_INVALID;
    }
    }

    boardPhyCfg = EnetBoard_getPhyCfg (&ethPort);
    if (boardPhyCfg!=空)
    {
    EnetPhy_initCfg (phyCfg);
    phyCfg->phyAddr = CONFIG_ENET_CPSW0_PHY0_ADDR;
    phyCfg->isStrapped = boardPhyCfg->isStrapped;
    phyCfg->loopbackEn = false;
    phyCfg->skipExtendedCfg =板 PhyCfg->skipExtendedCfg;
    phyCfg->extendedCfgSize = boardPhyCfg->extendedCfgSize;
    /*设置 Tx 和 Rx 偏斜延迟值*/
    Board_TxRxDelaySet (boardPhyCfg);
    memcpy (phyCfg->extendedCfg、boardPhyCfg->extendedCfg、phyCfg->extendedCfgSize);

    }
    其他
    {
    DebugP_log ("未找到 MAC 端口%u\r\n"、
    Enet_MACPORT_ID (ethPort.macPort));
    EnetAppUtils_assert (false);
    }

    MII->layerType = ethPort.MII.layerType;
    MII->subayerType = ethPort.MII.subayerType;
    MII->variantType = ENET_MAC_variant_forced;
    linkCfg->speed = ENET_SPEED_AUTO;
    linkCfg->duplexity = ENET_DUPLEX;

    IF (enet_isCpswFamily (ENET_CPSW_3G))
    {
    CpswMacPort_Cfg * macCfg =(CpswMacPort_Cfg *) linkArgs->macCfg;

    IF (EnetMacPort_isSgmii (MII)|| EnetMacPort_isQsgmii (MII))
    {
    macCfg->sgmiiMode = ENET_MAC_SGMIIMODE_SGMII_WIT_PHY;
    }
    其他
    {
    macCfg->sgmiiMode = ENET_MAC_SGMIIMODE_INVALID;
    }
    }
    }

    void enetApp_getEnetInstInfo (enet_Type * enetType、
    uint32_t * instId、
    Enet_MacPort macPortList[]、
    uint8_t * numMacPorts)
    {
    *enetType = Board_getEthType();
    *instId = 0;
    *numMacPorts = 1;
    macPortList[0]= ENET_MAC_PORT_1;
    }

    int enet_lwip_example (void * args)
    {
    Enet_Type enetType;
    uint32_t instId;
    Enet_MacPort macPortList[1];
    uint8_t numMacPorts;

    drivers_open();
    Board_driversOpen();

    Board_cpswMuxSel();

    DebugP_log ("======================================================== \r\n");
    DebugP_log (" ENET LWIP App \r\n");
    DebugP_log ("======================================================== \r\n");
    DebugP_log ("portTIk_RATE_MS =%d\r\n"、portTIk_RATE_MS);
    DebugP_log ("CONFIGMAX_Priorities =%d\r\n"、CONFIGMAX_Priorities);

    EnetApp_getEnetInstInfo (&enetType、
    instId (&I)、
    macPortList、
    numMacPorts (&N);
    EnetAppUtils_enableClocks (enetType、instId);

    #if 0
    /*信号量生成*/
    // err_t err;
    // err = sys_sem_new (&gThreadSem、0);
    // gThreadSem = xSemaphoreCreateBinaryStatic (&gThreadSemObj);
    // configASBERT (gThreadSem!= NULL);
    // vQueueAddToRegistry (gThreadSem、"Thread Sem");//这使得信号量在 CCS IDE 内的 ROV 中可见*/
    #endif

    /*启动计时器*/
    gTimerCount = 0;
    gTimerCountISR = 0;
    TimerP_START (gTimerBaseAddr[CONFIG_TIMER0]);

    /*请不要进行 stdio 缓冲! *
    //setvbuf (stdout、NULL、_IONBF、0);
    MAIN_LOOP (NULL);
    返回0;
    }

    /*定期计时器 */
    空 timer0_ISR (空)
    {
    // DebugP_log ("timer0_isr ()\r\n");
    // sys_sem_signal (&gThreadSem);
    basetype_t doTaskSwitch = 0;

    xSemaphoreGiveFromISR (gThreadSem、&doTaskSwitch);/*唤醒 pong 任务*/
    portYIELD_FER_ISR( doTaskSwitch );

    gTimerCountISR++;
    }

    /*周期性线程*/
    void FreeRTOS_thread (void *args)
    {
    DebugP_log ("======================================================== \r\n");
    DebugP_log (" freertos_thread ()\r\n");
    DebugP_log ("======================================================== \r\n");
    while (1){
    // sys_sem_wait (&gThreadSem);
    xSemaphoreTake (gThreadSem、portMAX_DELAY);
    gTimerCount++;
    }
    }

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好  

    从您共享的代码中、我看到一个任务"FreeRTOS_THREE"永远运行。 因此、这不应超过100usec 窗口。 您是否正在运行任何其他可能会消耗100usec 窗口的高优先级任务?

    您能否使用计数信标尝试相同的代码? 这样、即使 ISR 在任务之前、任务也不会错过任何信标发布。 我建议 计数信标值至少为10。 我认为这应该解决这个问题。

    此致

    Sri Vidya

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好  

    在我结束时、我无法重现一个任务一直运行、一个计时器 ISR 的问题。 我对代码进行了如下细微更改:

    SysConfig 中的计时器配置-这是否与您的相同?

    void TimerP_isr0(void *args)
    {
    void timer0_ISR(void *args);

    timer0_ISR(args);
    TimerP_clearOverflowInt(gTimerBaseAddr[CONFIG_TIMER0]);
    HwiP_clearInt(CONFIG_TIMER0_INT_NUM);
    }

    /* Periodic timer */
    void timer0_ISR(void)
    {
    // DebugP_log("timer0_ISR()\r\n");
    // sys_sem_signal(&gThreadSem);
    BaseType_t doTaskSwitch = 0;

    xSemaphoreGiveFromISR( gThreadSem, &doTaskSwitch); /* wake up pong task */
    portYIELD_FROM_ISR( doTaskSwitch );

    gTimerCountISR++;
    }

    /* Periodic threads */
    void freertos_thread(void *args)
    {
    DebugP_log("==========================\r\n");
    DebugP_log(" freertos_thread() \r\n");
    DebugP_log("==========================\r\n");
    static int startTimer = 1;
    while (1) {
    // sys_sem_wait(&gThreadSem);
    if(startTimer == 1)
    {
    TimerP_start(gTimerBaseAddr[CONFIG_TIMER0]);
    startTimer = 0;
    }
    xSemaphoreTake(gThreadSem, portMAX_DELAY);
    gTimerCount++;
    if(gTimerCount < gTimerCountISR)
    {
    DebugP_log("Error");
    }}}

    我的计数器值:

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    优先级设置似乎是错误的、因此我将对其进行更改并使其正常工作。

    此致

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    你(们)好  

    您能否告诉我您是否需要有关此方面的更多支持、或者我们是否可以关闭此主题?

    此致

    Sri Vidya

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    您可能需要关闭此主题。

    如果出现其他问题、请再次询问。

    此致