Hi All,
LM4F timer module ‘wait-for-trigger’ daisy-chain mode.
I am using the Stellaris LM4F120 LaunchPad Evaluation Board (EK-LM4F120XL).
I cannot get a timer to wait on the trigger reliably - sometimes it does, sometimes not. First, some relevant issues/posts I have found:
#1 There is a LM3S post on daisy-chaining timers (http://e2e.ti.com/support/microcontrollers/stellaris_arm/f/471/p/168248/663408.aspx#663408) and an LM3S Errata (wait-on-Trigger does not assert unless the TnOTE bit is set in the GPTMCTL register). I tried this fix but no luck – maybe not relevant for the LM4F.
#2 There is a post on daisy-chaining timers (http://e2e.ti.com/support/microcontrollers/tiva_arm/f/908/t/237672.aspx) for an LM4F232 which did not resolve my issues here.
#3 There is a known issue with PWM mode in the Errata: GPTM#04 — “Wait-for-Trigger Mode is not Available for PWM Mode”.
Here is my simple example. I am trying to have a one-shot timer2 trigger a periodic timer3. The timers run slowly for easy debugging :-
// [In startup, clk=80MHz]
SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER3) ;
SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER2) ;
// ...
// Repeat from here
TimerConfigure(TIMER3_BASE, TIMER_CFG_A_PERIODIC) ;
TimerConfigure(TIMER2_BASE, TIMER_CFG_A_ONE_SHOT) ;
// Period 5 seconds
unsigned long uT = SysCtlClockGet() * 5 ;
TimerLoadSet(TIMER3_BASE, TIMER_A, uT) ;
TimerLoadSet(TIMER2_BASE, TIMER_A, uT) ;
// [Clears Raw Interrupt Status TATORIS, time-out interrupt occurred]
TimerIntClear(TIMER3_BASE, TIMER_TIMA_TIMEOUT) ;
TimerIntClear(TIMER2_BASE, TIMER_TIMA_TIMEOUT) ;
// Once enabled, T3 should wait on T2 to timeout
TimerControlWaitOnTrigger(TIMER3_BASE, TIMER_A, true) ;
// Display timer values every 1sec
for(i = 0 ; i < 15 ; i++)
{
UARTprintf("[%02d] T2=%09u, T3=%09u\n",
i,
HWREG(TIMER2_BASE + TIMER_O_TAV),
HWREG(TIMER3_BASE + TIMER_O_TAV)
) ;
Delay(1.0f) ;
if (i == 0)
TimerEnable(TIMER2_BASE, TIMER_A) ;
else
if (i == 2)
{
DumpRegisters(TIMER2_BASE) ;
DumpRegisters(TIMER3_BASE) ;
TimerEnable(TIMER3_BASE, TIMER_A) ;
}
}
TimerDisable(TIMER2_BASE, TIMER_A) ;
TimerDisable(TIMER3_BASE, TIMER_A) ;
After a board ‘reset’ I get the following results :-
On the first run, timer T3 is enabled at t=2s, and it waits correctly on T2 to timeout at t=5s :-
[00] T2=400000000, T3=400000000 [Enable T2]
[01] T2=399999477, T3=400000000
[02] T2=319990121, T3=400000000 [Enable T3]
[03] T2=196295683, T3=400000000
[04] T2=116285767, T3=400000000
[05] T2=036275937, T3=400000000
[06] T2=400000000, T3=356266393 << Correct, T3 starts
[07] T2=400000000, T3=276256355
[08] T2=400000000, T3=196246361
[09] T2=400000000, T3=116236443
[10] T2=400000000, T3=036226611
[11] T2=400000000, T3=356217008
[12] T2=400000000, T3=276206896
[13] T2=400000000, T3=196196822
[14] T2=400000000, T3=116186828
But on the second run T3 starts immediately without waiting:-
[00] T2=400000000, T3=400000000 [Enable T2]
[01] T2=399999477, T3=400000000
[02] T2=319990121, T3=400000000 [Enable T3]
[03] T2=196295687, T3=399999310 << Not correct
[04] T2=116285769, T3=319989392
[05] T2=036275981, T3=239979604
[06] T2=400000000, T3=159970138 << T3 should start here instead
[07] T2=400000000, T3=079960276
[08] T2=400000000, T3=399950613
[09] T2=400000000, T3=319940577
[10] T2=400000000, T3=239930583
[11] T2=400000000, T3=159920565
[12] T2=400000000, T3=079910625
[13] T2=400000000, T3=399900884
[14] T2=400000000, T3=319890770
Running instead in the debugger, sometimes the result is reversed, i.e. the first time around, T3 does not wait, the second time it does, sometimes neither. This is curious. But from a ‘reset’ on the board it always gives the same result as shown.
There is a dump, see below, of all the registers (just before timer 3 enable) for timers 2 and 3, but there are no obvious relevant differences between the two runs. Only the precise timer values differ by just a few ticks (as we would expect). The mode, control and interrupt registers are identical.
I tried clearing bits not needed in registers GPTM Timer A/B Mode. Timer 2 requires only GPTM Timer A Mode = 0x1 (TAMR=one-shot), and timer 3 needs only GPTM Timer A Mode = TAWOT (wait-on-trigger) and TAMR=0x2 (periodic), GPTM Timer B Mode = 0 for both. But the result is exactly the same.
I tried different timers, and wide timers too (in 32-bit mode), again same result. I removed all other code except that needed for UARTprintf(), Delay() and DumpRegisters(). I switched out the DumpRegisters() call (just in case this was corrupting something), same result. I tried different combinations of one-shot and periodic modes. Interestingly, the one-shot to one-shot case works most of the time, but it sometimes fails. I have looked for any other code that might be corrupting the timers.
I moved the timer3 enable call (TimerEnable()) to before the timer2 enable (as suggested in post #2 above), but, same behaviour – sometimes timer3 waits, sometimes not.
So my questions are:
- Has anyone out there used timer daisy-chaining on the LM4F or equivalent? A ‘yes, it works for such-and-such’ would be very helpful to know.
- If timers 2 & 3 are in the same state (just before enabling timer 3) for both runs (see below), what could be changing the timer behaviour? Are there some other registers which control timer behaviour?
Thanks for any help ...
Jim
---
Device info: ID’s are DID0: 0x18050003, DID1: 0x1004602c, device part marking: 980 YF LX4F120H5QRFIGA3 29C1ZFW G4.
[The ‘X’ in LX4F120H5QR stands for ‘experimental’ release (significant?), ‘A3’ is the revision.]
Stellaris Firmware Development Package, revision 9453.
Code Composer Studio, Version: 5.2.1.00018.
These are the timer module registers just before enabling timer 3 (see code above, DumpRegisters()) :-
-------------
First run
-------------
TIMER2_BASE [0x40032000]
Value Value (binary) Offset Register Name
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x000] GPTM Configuration
0x00000221, 0000 0000 0000 0000 0000 0010 0010 0001, [0x004] GPTM Timer A Mode
0x00000200, 0000 0000 0000 0000 0000 0010 0000 0000, [0x008] GPTM Timer B Mode
0x00000001, 0000 0000 0000 0000 0000 0000 0000 0001, [0x00c] GPTM Control
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x010] GPTM Synchronize
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x018] GPTM Interrupt Mask
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x01c] GPTM Raw Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x020] GPTM Masked Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x024] GPTM Interrupt Clear
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x028] GPTM Timer A Interval Load
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x02c] GPTM Timer B Interval Load
0xffffffff, 1111 1111 1111 1111 1111 1111 1111 1111, [0x030] GPTM Timer A Match
0x0000ffff, 0000 0000 0000 0000 1111 1111 1111 1111, [0x034] GPTM Timer B Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x038] GPTM Timer A Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x03c] GPTM Timer B Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x040] GPTM TimerA Prescale Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x044] GPTM TimerB Prescale Match
0x0d7be6f3, 0000 1101 0111 1011 1110 0110 1111 0011, [0x048] GPTM Timer A
0x00000d6f, 0000 0000 0000 0000 0000 1101 0110 1111, [0x04c] GPTM Timer B
0x0d6338f7, 0000 1101 0110 0011 0011 1000 1111 0111, [0x050] GPTM Timer A Value
0x00000d56, 0000 0000 0000 0000 0000 1101 0101 0110, [0x054] GPTM Timer B Value
0x00007fff, 0000 0000 0000 0000 0111 1111 1111 1111, [0x058] GPTM RTC Predivide
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x05c] GPTM Timer A Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x060] GPTM Timer B Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x064] GPTM Timer A Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x068] GPTM Timer B Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0xfc0] GPTM Peripheral Properties
TIMER3_BASE [0x40033000]
Value Value (binary) Offset Register Name
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x000] GPTM Configuration
0x00000262, 0000 0000 0000 0000 0000 0010 0110 0010, [0x004] GPTM Timer A Mode
0x00000200, 0000 0000 0000 0000 0000 0010 0000 0000, [0x008] GPTM Timer B Mode
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x00c] GPTM Control
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x010] GPTM Synchronize
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x018] GPTM Interrupt Mask
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x01c] GPTM Raw Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x020] GPTM Masked Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x024] GPTM Interrupt Clear
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x028] GPTM Timer A Interval Load
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x02c] GPTM Timer B Interval Load
0xffffffff, 1111 1111 1111 1111 1111 1111 1111 1111, [0x030] GPTM Timer A Match
0x0000ffff, 0000 0000 0000 0000 1111 1111 1111 1111, [0x034] GPTM Timer B Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x038] GPTM Timer A Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x03c] GPTM Timer B Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x040] GPTM TimerA Prescale Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x044] GPTM TimerB Prescale Match
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x048] GPTM Timer A
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x04c] GPTM Timer B
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x050] GPTM Timer A Value
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x054] GPTM Timer B Value
0x00007fff, 0000 0000 0000 0000 0111 1111 1111 1111, [0x058] GPTM RTC Predivide
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x05c] GPTM Timer A Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x060] GPTM Timer B Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x064] GPTM Timer A Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x068] GPTM Timer B Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0xfc0] GPTM Peripheral Properties
-------------
Second run
-------------
TIMER2_BASE [0x40032000]
Value Value (binary) Offset Register Name
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x000] GPTM Configuration
0x00000221, 0000 0000 0000 0000 0000 0010 0010 0001, [0x004] GPTM Timer A Mode
0x00000200, 0000 0000 0000 0000 0000 0010 0000 0000, [0x008] GPTM Timer B Mode
0x00000001, 0000 0000 0000 0000 0000 0000 0000 0001, [0x00c] GPTM Control
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x010] GPTM Synchronize
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x018] GPTM Interrupt Mask
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x01c] GPTM Raw Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x020] GPTM Masked Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x024] GPTM Interrupt Clear
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x028] GPTM Timer A Interval Load
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x02c] GPTM Timer B Interval Load
0xffffffff, 1111 1111 1111 1111 1111 1111 1111 1111, [0x030] GPTM Timer A Match
0x0000ffff, 0000 0000 0000 0000 1111 1111 1111 1111, [0x034] GPTM Timer B Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x038] GPTM Timer A Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x03c] GPTM Timer B Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x040] GPTM TimerA Prescale Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x044] GPTM TimerB Prescale Match
0x0d7be6f7, 0000 1101 0111 1011 1110 0110 1111 0111, [0x048] GPTM Timer A
0x00000d6f, 0000 0000 0000 0000 0000 1101 0110 1111, [0x04c] GPTM Timer B
0x0d6338fb, 0000 1101 0110 0011 0011 1000 1111 1011, [0x050] GPTM Timer A Value
0x00000d56, 0000 0000 0000 0000 0000 1101 0101 0110, [0x054] GPTM Timer B Value
0x00007fff, 0000 0000 0000 0000 0111 1111 1111 1111, [0x058] GPTM RTC Predivide
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x05c] GPTM Timer A Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x060] GPTM Timer B Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x064] GPTM Timer A Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x068] GPTM Timer B Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0xfc0] GPTM Peripheral Properties
TIMER3_BASE [0x40033000]
Value Value (binary) Offset Register Name
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x000] GPTM Configuration
0x00000262, 0000 0000 0000 0000 0000 0010 0110 0010, [0x004] GPTM Timer A Mode
0x00000200, 0000 0000 0000 0000 0000 0010 0000 0000, [0x008] GPTM Timer B Mode
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x00c] GPTM Control
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x010] GPTM Synchronize
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x018] GPTM Interrupt Mask
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x01c] GPTM Raw Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x020] GPTM Masked Interrupt Status
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x024] GPTM Interrupt Clear
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x028] GPTM Timer A Interval Load
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x02c] GPTM Timer B Interval Load
0xffffffff, 1111 1111 1111 1111 1111 1111 1111 1111, [0x030] GPTM Timer A Match
0x0000ffff, 0000 0000 0000 0000 1111 1111 1111 1111, [0x034] GPTM Timer B Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x038] GPTM Timer A Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x03c] GPTM Timer B Prescale
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x040] GPTM TimerA Prescale Match
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x044] GPTM TimerB Prescale Match
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x048] GPTM Timer A
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x04c] GPTM Timer B
0x17d78400, 0001 0111 1101 0111 1000 0100 0000 0000, [0x050] GPTM Timer A Value
0x000017d7, 0000 0000 0000 0000 0001 0111 1101 0111, [0x054] GPTM Timer B Value
0x00007fff, 0000 0000 0000 0000 0111 1111 1111 1111, [0x058] GPTM RTC Predivide
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x05c] GPTM Timer A Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x060] GPTM Timer B Prescale Snapshot
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x064] GPTM Timer A Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0x068] GPTM Timer B Prescale Value
0x00000000, 0000 0000 0000 0000 0000 0000 0000 0000, [0xfc0] GPTM Peripheral Properties