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.

AM2432: Sigma delta ISR entrance moment jitter in R5F

Part Number: AM2432

Hi TI Experts,

Few month ago my colleague asked about this, AM2432: Sigma delta ISR entrance moment jitter in R5F - Arm-based microcontrollers forum - Arm-based microcontrollers - TI E2E support forums 

I have further looked into the issue. It seems there are codes in the SDK that they would disable the interrupt. 

For example, in function bsp_send_command_to_firmware(), which is called by various EtherCAT related functions.

void bsp_send_command_to_firmware(PRUICSS_Handle pruIcssHandle,
                                  uint32_t command,
                                  uint16_t param1, uint16_t param2)
{
    volatile t_host_interface *pHost2PruIntfc = (volatile t_host_interface *)
            ((((PRUICSS_HwAttrs *)(pruIcssHandle->hwAttrs))->baseAddr) +
             PRUICSS_DATARAM(0));
    {
#ifdef ENABLE_PDI_TASK
        SemaphoreP_pend(&semcmdlow_object, SystemP_WAIT_FOREVER);
#else
        uintptr_t key1 = HwiP_disable();
#endif
        bsp_pruss_cmd_intfc_write_word(command, &pHost2PruIntfc->cmdlow);
        bsp_pruss_cmd_intfc_write_word(param1, &pHost2PruIntfc->param1low);
        bsp_pruss_cmd_intfc_write_word(param2, &pHost2PruIntfc->param2low);
#ifdef SUPPORT_CMDACK_POLL_MODE
        bsp_pruss_cmd_intfc_write_word(1, &pHost2PruIntfc->cmdlow_ack);
#endif
        PRUICSS_sendEvent((g_bsp_params.pruicss_handle), ARM_PRU_EVENT1);
        ASSERT_DMB();
        ASSERT_DSB();
        {
#ifdef SUPPORT_CMDACK_POLL_MODE
            volatile uint16_t ack;

            do
            {
                ack = bsp_pruss_cmd_intfc_read_word(&pHost2PruIntfc->cmdlow_ack);
            }
            while(ack);
#ifndef ENABLE_PDI_TASK
            HwiP_restore(key1);
#endif
#else
            uint32_t evtoutNum = HOST_CMD_LOW_ACK_EVENT - 20;
#ifndef ENABLE_PDI_TASK
            HwiP_restore(key1);
#endif
            PRUICSS_waitEvent((PRUICSS_Handle)(g_bsp_params.pruicss_handle), evtoutNum);
#endif
        }
        bsp_pruss_cmd_intfc_write_word(0xFF,    &pHost2PruIntfc->cmdlow);
#ifdef ENABLE_PDI_TASK
        SemaphoreP_post(&semcmdlow_object);
#endif
    }
}

When I uses SDFM 3-channel example from SDK, the jitter from ISR is reduced to 300 ns. So I believe the the cause that jitter goes to 4 us.

I'll try to locate all code sections that cause the issue, as I searched hwiP_disable, there are quite some matches,

HwiP_disable_matches.png

SPI and UART are used, they might also be the cause.

For the test I have down is that I first comment out some functions, the frequncy is improved from

SD_4us_jitter.png

to

SD_4us_jitter_somefunction.png

 

I'll update the thread every time I locate a code section that we use and disables interrupt. And want to know if it is necessary to keep the implementation. 

  • For example, in function bsp_send_command_to_firmware(), which is called by various EtherCAT related functions.

    So the first question is for EtherCAT, I am thinking moving everything into ECAT main and leaves only PDO data handling in interrupts. Would it be safe to remove 

    HwiP_disable(); in bsp_send_command_to_firmware?
    Thanks
  • Hi Jianyu,

    The section between the HwiP_disable and HwiP_restore is considered to be critical as we don't want to update the fields of the PRUICSS input words partially, and switch to a different context, which would result in undesired behavior.

    To get a better clarity on your query, disabling all peripheral intervals is the issue in your case? Is it fine if only PDI and SYNC interrupts are disabled rather than global IRQ disable?

    I'm referring to the below APIs which can replace HwiP_disable and HwiP_restore:

    void bsp_global_mutex_lock(void)
    {
        //escGlobalIArg = GateAll_enter (escGlobalGateHandle);
        //Disable PDI and SYNC0 ISR at ARM INTC (rather than global IRQ disable)
        HwiP_disableInt(HOST_AL_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
        HwiP_disableInt(HOST_SYNC0_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
        HwiP_disableInt(HOST_SYNC1_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
    }
    
    void bsp_global_mutex_unlock(void)
    {
        //GateAll_leave (escGlobalGateHandle, escGlobalIArg);
        //Enable back PDI and SYNC0 ISR at ARM INTC
        HwiP_enableInt(HOST_AL_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
        HwiP_enableInt(HOST_SYNC0_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
        HwiP_enableInt(HOST_SYNC1_EVENT + g_bsp_params.interrupt_offset - PRUICSS_INTERRUPT_OFFSET_ADJUSTMENT);
    } 

    Regards,
    Aaron

  • Is it fine if only PDI and SYNC interrupts are disabled rather than global IRQ disable?

    That would be great. Yes, our key request is that SD isr is stable, while not affecting the rest functions.

  • Hi Aaron,

    I want a clarification that, I am goint to move PDO read/write, that calls HW_EscWriteIsr and HW_EscReadIsr, into SD isr. Would those function also disrupt function bsp_send_command_to_firmware?

    Thanks.

  • Hi Jianyu,

    If HW_EscWriteIsr() or HW_EscReadIsr() is called from your SD ISR context, it can be interrupted by EtherCAT ISRs (like the PDI ISR or SYNC ISRs), which could potentially cause race conditions when accessing the shared buffer state machine in bsp_get_process_data_address() and bsp_process_data_access_complete().