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.

[Sysdelay] DMTimer7 usage - cannot be enabled

Hello,

I am developing a bare-metal application on Beaglebone Rev6A using Starterware 02.00.01.01 and I am facing the following problem:

When using the Sysdelay function after having used the SysDelayTimerSetup the application hangs.
Studying the source code(platform/beaglebone/sysdelay.c)) the Sysdelay function  uses the DMTimer7. 

Debugging the code I show that the Counter Register (TCRR) of the  DMTimer7 receives the proper value show
that after x milisecs it will overflow. But when the DMTimerEnable(SOC_DMTIMER_7_REGS) is invoked instead of setting the TCLR _ST bit of the TCLR register, the value of the TCRR is cleared and the value of TCLR remains zero. 

This results in never starting the timer and the Sysdelay function to get stuck at the  
while(FALSE == flagIsr) ;
As the Timer  never started and now overflow occurs to trigger an interrupt.

Since the TCRR receives the proper value , I assume that the timer is configured properly. 
Then what is the problem?

Thank you. 

  • I copied the implementation of Sysdelay and replaced DMTimer7 with DMTimer3 and the problem persists. 

  • The problem was that when clicking on the Debug Icon at CCS the target configuration file was not loaded properly and besides by setting the correct file the AM335x_EVM_initialization script needed to executed.

    So I changed to the starterware to call the AM335x_EVM_initialization script on target connect.

    Finally the 

    IntMasterIRQEnable();

    needed to be called before using the delay capabities

  • akarapatis said:

    The problem was that when clicking on the Debug Icon at CCS the target configuration file was not loaded properly and besides by setting the correct file the AM335x_EVM_initialization script needed to executed.

    So I changed to the starterware to call the AM335x_EVM_initialization script on target connect.

    Finally the 

    IntMasterIRQEnable();

    needed to be called before using the delay capabities

    akarapatis,
    Now, 4 years later, I am having the same problem.  However your solution didn't solve it.  And thank TI for dropping support for StarterWare in favor of the "all encompassing" SYS/BIOS, which is missing a boatload of functionality.
    The code is all of this:
    int main(void) {
    
        SysDelayTimerSetup();
        IntMasterIRQEnable();
        Sysdelay(60000);
    
        printf("Completed\n");
    return 0; }

    Same thing.  Delay just hangs.  Stepping into the libraries, it is the same loop ( while(FALSE == flagIsr)  ).  The timer is expiring, I can see it in the JTAG debugging.  But the ISR never seems to fire.

    Did you do anything else to solve it?  Priority levels? Interrupt enabling?  Any additional advice is appreciated.

    -CSW

  • CSW,

    Do you have the ARM int controller initialized?
    e2e.ti.com/.../448904

    IntAINTCInit();

    Lali
  • Lalindra Jayatilleke said:
    CSW,

    Do you have the ARM int controller initialized?
    e2e.ti.com/.../448904

    IntAINTCInit();

    Lali

    Lali,

    Thanks for the followup.  Yes.  I tried executing the following code, which contains   IntAINTCInit()...  to no avail.

    #include <stdio.h>
    
    #include "cpu.h"
    #include "delay.h"
    #include "interrupt.h"
    
    #include "beaglebone.h"     /* GPIO1ModuleClkConfig, DMTimer7ModuleClkConfig, etc... */
    #include "gpio_v2.h"        /* GPIO directions,  GPIOxxxxx(..)  functions */
    #include "hw_types.h"       /* HWREG MACROS plus simple types (T/F, boolean, ..) */
    
    #include "soc_AM335x.h"      /*  Hardware addresses for this Sitara */
    
    int main(void) {
        DMTimer7ModuleClkConfig();
    
        IntMasterIRQEnable();
    
        IntAINTCInit();     /*  Sets ALL ISR Vectors to the default handler */
    
        SysDelayTimerSetup();   /*  Sets up TMR7, and sets the ISR to it's handler */
    
        Sysdelay(6000);
    
        while (1) {
    
            ;
    
        }
    	return 0;
    }
    

    Because "SysDelayTimerSetup" and "Sysdelay" user timer 7, I added extra calls to enable the interrupts.  Still didn't work.

    Also, in an effort to further resolve this issue (which is still failing) was to import the example project from StarterWare for using the timers.  Here is code, as supplied directly from the example

    #include "consoleUtils.h"
    #include "soc_AM335x.h"
    #include "beaglebone.h"
    #include "interrupt.h"
    #include "dmtimer.h"
    #include "error.h"
    
    /******************************************************************************
    **                      INTERNAL MACRO DEFINITIONS
    *******************************************************************************/
    #define TIMER_INITIAL_COUNT             (0xFF000000u)
    #define TIMER_RLD_COUNT                 (0xFF000000u)
    
    /******************************************************************************
    **                      INTERNAL FUNCTION PROTOTYPES
    *******************************************************************************/
    static void DMTimerAintcConfigure(void);
    static void DMTimerSetUp(void);
    static void DMTimerIsr(void);
    
    /******************************************************************************
    **                      INTERNAL VARIABLE DEFINITIONS
    *******************************************************************************/
    static volatile unsigned int cntValue = 10;
    static volatile unsigned int flagIsr = 0;
    
    /******************************************************************************
    **                          FUNCTION DEFINITIONS
    *******************************************************************************/
    int main(void)
    {
        /* This function will enable clocks for the DMTimer2 instance */
        DMTimer2ModuleClkConfig();
    
        /* Initialize the UART console */
    //    ConsoleUtilsInit();
    
        /* Select the console type based on compile time check */
    //    ConsoleUtilsSetType(CONSOLE_UART);
    
        /* Enable IRQ in CPSR */
        IntMasterIRQEnable();
    
        /* Register DMTimer2 interrupts on to AINTC */
        DMTimerAintcConfigure();
    
        /* Perform the necessary configurations for DMTimer */
        DMTimerSetUp();
    
        /* Enable the DMTimer interrupts */
        DMTimerIntEnable(SOC_DMTIMER_2_REGS, DMTIMER_INT_OVF_EN_FLAG);
    
    //    ConsoleUtilsPrintf("Tencounter: ");
    
        /* Start the DMTimer */
        DMTimerEnable(SOC_DMTIMER_2_REGS);
    
        while(cntValue)
        {
            if(flagIsr == 1)
            {
    //            ConsoleUtilsPrintf("\b%d",(cntValue - 1));
                cntValue--;
                flagIsr = 0;
            }
        }
    
        /* Stop the DMTimer */
        DMTimerDisable(SOC_DMTIMER_2_REGS);
    
    //    PRINT_STATUS(S_PASS);
    
        /* Halt the program */
        while(1);
    }
    
    /*
    ** Do the necessary DMTimer configurations on to AINTC.
    */
    static void DMTimerAintcConfigure(void)
    {
        /* Initialize the ARM interrupt control */
        IntAINTCInit();
    
        /* Registering DMTimerIsr */
        IntRegister(SYS_INT_TINT2, DMTimerIsr);
    
        /* Set the priority */
        IntPrioritySet(SYS_INT_TINT2, 0, AINTC_HOSTINT_ROUTE_IRQ);
    
        /* Enable the system interrupt */
        IntSystemEnable(SYS_INT_TINT2);
    }
    
    /*
    ** Setup the timer for one-shot and compare mode.
    */
    static void DMTimerSetUp(void)
    {
        /* Load the counter with the initial count value */
        DMTimerCounterSet(SOC_DMTIMER_2_REGS, TIMER_INITIAL_COUNT);
    
        /* Load the load register with the reload count value */
        DMTimerReloadSet(SOC_DMTIMER_2_REGS, TIMER_RLD_COUNT);
    
        /* Configure the DMTimer for Auto-reload and compare mode */
        DMTimerModeConfigure(SOC_DMTIMER_2_REGS, DMTIMER_AUTORLD_NOCMP_ENABLE);
        //DMTimerModeConfigure(SOC_DMTIMER_2_REGS, DMTIMER_ONESHOT_NOCMP_ENABLE);
    
    }
    
    /*
    ** DMTimer interrupt service routine. This will send a character to serial
    ** console.
    */
    static void DMTimerIsr(void)
    {
        /* Disable the DMTimer interrupts */
        DMTimerIntDisable(SOC_DMTIMER_2_REGS, DMTIMER_INT_OVF_EN_FLAG);
    
        /* Clear the status of the interrupt flags */
        DMTimerIntStatusClear(SOC_DMTIMER_2_REGS, DMTIMER_INT_OVF_IT_FLAG);
    
        flagIsr = 1;
        //DMTimerDisable(SOC_DMTIMER_2_REGS);
    
        /* Enable the DMTimer interrupts */
        DMTimerIntEnable(SOC_DMTIMER_2_REGS, DMTIMER_INT_OVF_EN_FLAG);
    }

    (I removed the console calls, as I didn't include the library to resolve those).

    So I am still digging...

    -CSW