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.

TM4C123AH6PM: Timer Synchronization

Expert 2590 points
Part Number: TM4C123AH6PM

I can't synchronize two timer on my mcu. I have tried two methods. First one is the way you would think it would work:

MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_WTIMER0);

// Configure timers to input edge time mode and counting up
MAP_TimerConfigure(WTIMER0_BASE, (TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_CAP_TIME_UP | TIMER_CFG_B_CAP_TIME_UP));


// Configure to capture the rising edge
MAP_TimerControlEvent(WTIMER0_BASE, TIMER_BOTH, TIMER_EVENT_POS_EDGE);

// Enable interrupts
MAP_TimerIntEnable(WTIMER0_BASE, (TIMER_CAPA_EVENT | TIMER_CAPB_EVENT));

MAP_TimerControlStall(WTIMER0_BASE, TIMER_A, true);
MAP_TimerEnable(WTIMER0_BASE, TIMER_BOTH);

MAP_TimerConfigure(WTIMER1_BASE, (TIMER_CFG_SPLIT_PAIR | TIMER_CFG_B_PERIODIC_UP));

// Set period to maximum
MAP_TimerLoadSet(WTIMER1_BASE, TIMER_B, 0xFFFFFFFF);

// Set first match to half period
MAP_TimerMatchSet(WTIMER1_BASE, TIMER_B, START_HALF_PERIOD);

// Enable interrupt
MAP_TimerIntEnable(WTIMER1_BASE, TIMER_TIMB_MATCH);
MAP_TimerControlStall(WTIMER1_BASE, TIMER_B, true);

// Enable timer
MAP_TimerEnable(WTIMER1_BASE, TIMER_B);

// Synchronize the clock 
MAP_TimerSynchronize(WTIMER1_BASE, WTIMER_0A_SYNC | WTIMER_1B_SYNC);

This way nothing happens. The clocks are running but not synchronized. Then I tried the other way with TIMER0_BASE. The code before is the same only the sync part has changed

MAP_SysCtlPeripheralEnable(TIMER0_BASE);
MAP_TimerSynchronize(TIMER0_BASE, WTIMER_0A_SYNC | WTIMER_1B_SYNC);
MAP_TimerSynchronize(TIMER0_BASE, 0);

But then the whole thing crashes on the first synchronize function to exception.

This is what is in exception register: 

SYSEXC_RIS_FPIXCRIS 1 Floating-Point Inexact Exception Raw Interrupt Status

So the question is what am I doing wrong? Or is it not possible to synchronize the clocks?

BR

JHi

  • Hi,
    I will need to do some investigation. My understanding is that if you use WTIMER then you will only apply the configuration to the timerA, not timerB.

    [edit] sorry, I didn't look at your code carefully. I thought you were trying to do 64bit timer. My bad.

  • Hi,
    Did you enable the peripheral for WTIMER1? I only see MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_WTIMER0) but I don't see the same for WTIMER1.
  • Yes it will also be enabled. I copied the code from two different functions and forgot to copy it. The function where the timers are going to be synchronized will be called after the WTIMER0 is configured. Actually the WTIMER1A will be configured the same time as WTIMER0 A and B. The WTIMER1B will be configured afterwards.

    JHi

  • As I said in the first post all my timers are running, but the problem is that they are not synchronizing. The code also crash if I call the MAP_TimerSynchronize(TIMER0_BASE, TIMER_0A_SYNC). It doesn't matter which timer I synchronize if the base is TIMER0_BASE. But if the base is something else, the timers still won't synchronize.
  • Using MAP_TimerSynchronize(TIMER0_BASE, WTIMER_0A_SYNC | WTIMER_1B_SYNC) is the right thing to do as only TIMER0_BASE can be used to synchronize selected timers whether or not TIMER0 itself is used in your application. This means that you should also enable TIMER0 even if you are using it for the purpose of synchronize WTIMER_0A_SYNC and WTIMER_1B_SYNC only.

    Please also go through the below errata pertaining to timer synchronization.

    GPTM#01 GPTMSYNC Bits Require Manual Clearing
    Revision(s) Affected: 6 and 7.
    Description: The GPTM Synchronize (GPTMSYNC) register allows software to synchronize a number
    of timers. The bits in this register should be self-clearing after setting bits to synchronize
    selected timers, but they are not.
    Workaround(s): When bits in the GPTMSYNC register are set, software must clear the bits prior to
    setting them for a subsequent update. When using TivaWare™ APIs, instead of just
    calling the TimerSynchronize() function once, software should call the function a second
    time with 0 as a parameter, as shown below:
    TimerSynchronize(TIMER0_BASE, TIMER_0A_SYNC | TIMER_1A_SYNC);
    TimerSynchronize(TIMER0_BASE, 0);

  • Yes I'm aware of that as you can see from my first post, but the problem is if I do that the program crashes with a exception mentioned also in a first post. I have also enabled the TIMER0 as seen on a first post MAP_SysCtlPeripheralEnable(TIMER0_BASE). The question is why my program crashes on synchronizing the timers? What else needs to be enabled?

    JHi

  • Yes, your code seems fine to me but I don't know why you would get an exception. I'm going through this other post to see if it can explain anything. Can you also take a look too and see if you can synchronize the timers. In this post with what I have said to enable TIMER0 and clear the sync bit will make it work. e2e.ti.com/.../1005030
  • Problem solved. I took my code from the link you posted and it is of course wrong. I should have double check it.
    The right thing to do it is: SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0) instead SysCtlPeripheralEnable(TIMER0_BASE).

    BR
    JHi
  • Glad your problem is solved.
  • JHi said:
    took my code from the link you posted and it is of course wrong.

    That assessment is a bit harsh - is it not?    And - had you considered that (many generations) of vendor's API have arrived/departed - and that code may have been "correct" - at that time!

    Post shows high (tech) competence ... diplomacy not so much...    (most all of the links provided by vendor's Charles are correct - your "of course" is neither factual nor proper!)

  • I'm sorry if you got upset from my post. The choice of words weren't the best I can admit that. And I didn't complain that Charles did something wrong. I'm happy that he tried to help me. I was just actually just angry to my self that I didn't check the code properly. And actually the SysCtlPeripheralEnable(TIMER0_BASE) was never ok, because you have to use system control registers when enabling system control peripherals. But it doesn't matter as the problem is now solved.

    JHi
  • Thank you - vendor agents, "Give & Do their best" they are bombarded w/demands. As (among - if not the longest forum user) I make some effort to assist - as/where/when able. Indeed this forum (due to posters such as you) is "top cabin."

    You are undoubtedly well skilled - the words I highlighted were gratuitous - and unfair to Charles. (and likely NOT your "norm.")

    I can tell you that the code presented DID SUCCEED - several hundred such LX4F boards (operating under StellarisWare) were delivered - and most remain in successful operation through today.