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.

AM6421: Use EXT_REFCLK1 as time source to generate interrupts at 10uS rate

Part Number: AM6421
Other Parts Discussed in Thread: SYSCONFIG

Tool/software:

I followed this forum example to enable the EXT_REFCLK1 input

https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1449750/am6422-processors-forum/5565882?tisearch=e2e-sitesearch&keymatch=EXT_REFCLK1#

This seemed to work, but I only got one interrupt for the timer I set up to give and ISR every 10uS.  I tried the same firmware with the timer clock input form the 25MHz HF_OSC0 and it operated as expected with continuous ticks every 10uS.

I can use either a cascaded pair of timers and count 10uS ticks or use this single timer and ISR method, but both of them require use of EXT_REFCLK1 as my synchronized clock source.

  • Hi Bruce,

    Sorry, I am little bit confused from the above description. I have the following understanding, please confirm the same.

    1. EXT_REFCLK1 is properly configured. (i.e. Pinmux settings are done correctly via Pinmux tool)?

    2. Configured a timer to generate interrupt after every 10us, but only got interrupt for once?

    3. Same firmware but the clock used here is HFOSC(25MHz), and everything works fine?

    Regards,

    Tushar

  • Tushar,

    Your understanding is correct.  After first initializing the timer, I get a single 10uS IRQ and nothing after that when using EXT_REFCLK1(48 MHz) as the timer source clock.  I then only switch the timer source clock to HF_OSC(25MHz) and I get interrupts every 25uS as expected.  I have attached code generated by SysCfg for the timer setup with EXT_REFCLK1, along with code snips of setting up PinMux and my ISR.

    A few more details:  The overall program uses FreeRTOS and is runnign on one of the R%F cores (R5FSS1-0)

    The count value TwoWayTimerTick increments only once when my program executes.  If I ONLY change the clocke sourec to HFOSC, then the count increases normally.

    =======================================================

    Code from Sysconfig generated ti_dpl_config.c

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

    DECODETIMER_TwoWayCallback(args);
    TimerP_clearOverflowInt(gTimerBaseAddr[TWOWAY_TIMER]);
    HwiP_clearInt(TWOWAY_TIMER_INT_NUM);
    }

    void TimerP_init()
    {
    TimerP_Params timerParams;
    HwiP_Params timerHwiParams;
    int32_t status;

    /* set timer clock source */
    SOC_controlModuleUnlockMMR(SOC_DOMAIN_ID_MAIN, 2);
    *(volatile uint32_t*)AddrTranslateP_getLocalAddr(TWOWAY_TIMER_CLOCK_SRC_MUX_ADDR) = TWOWAY_TIMER_CLOCK_SRC_EXT_REFCLK1;
    SOC_controlModuleLockMMR(SOC_DOMAIN_ID_MAIN, 2);

    gTimerBaseAddr[TWOWAY_TIMER] = (uint32_t)AddrTranslateP_getLocalAddr(TWOWAY_TIMER_BASE_ADDR);

    TimerP_Params_init(&timerParams);
    timerParams.inputPreScaler = TWOWAY_TIMER_INPUT_PRE_SCALER;
    timerParams.inputClkHz = TWOWAY_TIMER_INPUT_CLK_HZ;
    timerParams.periodInNsec = TWOWAY_TIMER_NSEC_PER_TICK;
    timerParams.oneshotMode = 0;
    timerParams.enableOverflowInt = 1;
    timerParams.enableDmaTrigger = 0;
    TimerP_setup(gTimerBaseAddr[TWOWAY_TIMER], &timerParams);

    HwiP_Params_init(&timerHwiParams);
    timerHwiParams.intNum = TWOWAY_TIMER_INT_NUM;
    timerHwiParams.callback = TimerP_isr0;
    timerHwiParams.isPulse = 0;
    timerHwiParams.priority = 4;
    status = HwiP_construct(&gTimerHwiObj[TWOWAY_TIMER], &timerHwiParams);
    DebugP_assertNoLog(status==SystemP_SUCCESS);

    TimerP_start( gTimerBaseAddr[TWOWAY_TIMER] );

    }

    ========================================================

    My Pinmux code executed in main() fright after System_init();

    void ExtRefClk1_config()
    {
      Pinmux_PerCfg_t gPinMuxMainDomainCfg[] = {

      /* MySYSTEM1 -> EXT_REFCLK1 -> A19 */
      {  
        PIN_EXT_REFCLK1,
        PIN_MODE(0) | ((PIN_PULL_DISABLE | PIN_INPUT_ENABLE) & (~PIN_PULL_DIRECTION))
        },

        { PINMUX_END, PINMUX_END }
    };

     Pinmux_config(gPinMuxMainDomainCfg, PINMUX_DOMAIN_ID_MAIN);
    }

    =======================================

    My Interrupt service handler that simply counts interrupts:

    void DECODETIMER_TwoWayCallback( void * args )
    {
      TwoWayTimerTick++;
    }

  • Hi,

    Can you please confirm how are you providing external clock to the Timer module? Are all hardware connection properly done?

    It looks like the source clock is not configured properly for the Timer module.

    Regards,

    Tushar

  • I agree that it seems like the clock is not configured correctly.  I checked before starting this question by using an oscilloscope to verify that the 48MHz TCXO was connected to EXT_REFCLK1 and everything seemed correct.  I have been able to verify that the 48MHz is getting to the timer by setting it to free run and looking a the count value with the debugger several times.  I'm still not sure why the interrupt is not working though.

  • Hi Bruce,

    Thanks for the confirmation. If the clock is configured correctly then it should work as expected.

    Please try one more experiment, don't start the timer after configuration.

    Remove the TimerP_start( gTimerBaseAddr[TWOWAY_TIMER] ); line from the TimerP_init() function. If this is generated via Sysconfig then uncheck the Start timer option.

    Start the timer once the pinmuxing is done. (i.e. after ExtRefClk1_config() function call)

    void TimerP_init()
    {
        TimerP_Params timerParams;
        HwiP_Params timerHwiParams;
        int32_t status;
        
        /* set timer clock source */
        SOC_controlModuleUnlockMMR(SOC_DOMAIN_ID_MAIN, 2);
        *(volatile uint32_t*)AddrTranslateP_getLocalAddr(TWOWAY_TIMER_CLOCK_SRC_MUX_ADDR) = TWOWAY_TIMER_CLOCK_SRC_EXT_REFCLK1;
        SOC_controlModuleLockMMR(SOC_DOMAIN_ID_MAIN, 2);
        
        gTimerBaseAddr[TWOWAY_TIMER] = (uint32_t)AddrTranslateP_getLocalAddr(TWOWAY_TIMER_BASE_ADDR);
        
        TimerP_Params_init(&timerParams);
        timerParams.inputPreScaler = TWOWAY_TIMER_INPUT_PRE_SCALER;
        timerParams.inputClkHz = TWOWAY_TIMER_INPUT_CLK_HZ;
        timerParams.periodInNsec = TWOWAY_TIMER_NSEC_PER_TICK;
        timerParams.oneshotMode = 0;
        timerParams.enableOverflowInt = 1;
        timerParams.enableDmaTrigger = 0;
        TimerP_setup(gTimerBaseAddr[TWOWAY_TIMER], &timerParams);
        
        HwiP_Params_init(&timerHwiParams);
        timerHwiParams.intNum = TWOWAY_TIMER_INT_NUM;
        timerHwiParams.callback = TimerP_isr0;
        timerHwiParams.isPulse = 0;
        timerHwiParams.priority = 4;
        status = HwiP_construct(&gTimerHwiObj[TWOWAY_TIMER], &timerHwiParams);
        DebugP_assertNoLog(status==SystemP_SUCCESS);
    
    
    }
    
    void main()
    {
        System_init();
        ExtRefClk1_config();
        TimerP_start( gTimerBaseAddr[TWOWAY_TIMER] );
    }

    Please let us know the results.

    Regards,

    Tushar

  • Tushar,

    Your suggestion worked - By waiting until later in my application code to start the timer, its used the external 48MHz with no issues.  Thanks for your help

  • Hi,

    Thanks for the above confirmation.

    Regards,

    Tushar