1
\$\begingroup\$

I wanted to use timers in TM4C123GH6PM (in TIVA C series TM4C123G Launchpad evaluation kit). So I decided to use GPTM TimerA0 in periodic timer mode. I defined the address of the registers of GPTM and followed the steps given in the section 11.4.1 One-Shot/Periodic Timer Mode of the datasheet in page 722. I want a LED to blink after every 3 seconds (connected to PORT F-pin 1). But the LED is always ON. Are the address of the registers to which I am referring wrong? Or something else is the issue with the code?

//TIMER Registers
#define RCGCTIMER        (*((volatile unsigned long *)0x400FE604))
#define GPTMCTL                  (*((volatile unsigned long *)0x4003000C)) //timer zero
#define GPTMCFG                  (*((volatile unsigned long *)0x40030000))
#define GPTMTAMR                 (*((volatile unsigned long *)0x40030004))  
#define GPTMTAILR                (*((volatile unsigned long *)0x40030028))
#define GPTMRIS                (*((volatile unsigned long *)0x4003001C))
#define GPTMICR                (*((volatile unsigned long *)0x40030024))

//PORT F Registers
#define GPIO_PORTF_DATA_R       (*((volatile unsigned long*)0x400253FC))
#define GPIO_PORTF_DIR_R        (*((volatile unsigned long *)0x40025400))
#define GPIO_PORTF_AFSEL_R      (*((volatile unsigned long *)0x40025420))
#define GPIO_PORTF_DEN_R        (*((volatile unsigned long *)0x4002551C))
#define SYSCTL_RCGC2_R          (*((volatile unsigned long *)0x400FE108))
#define SYSCTL_RCGC2_GPIOF      0x00000020  // port F Clock Gating Control 



void initializeTimer()
{
    RCGCTIMER |= 0x00000001; //To use a GPTM, the appropriate TIMERn bit must be set in the RCGCTIMER. Here it is TIMER0


    //Periodic timer mode

    GPTMCTL &=0xFFFFFFFE; //TAEN is set 0. Timer A is disabled.
    GPTMCFG = 0x00000000; //Write the GPTM Configuration Register (GPTMCFG) with a value of 0x0000.0000
    GPTMTAMR |=0x00000002; GPTMTAMR &=0xFFFFFFFE; //TAMR is set 0x2. Periodic Timer mode is used (first bit1 is set 1 and then bit0 is set 0 in two statements)
    GPTMTAMR &= 0xFFFFFFEF; //TACDIR is set 0. The timer counts down.
    GPTMTAILR = 0x02DC6C00; //TAILR is set to 48,000,000 Hz
    GPTMCTL |=0x00000001; //TAEN is set 1. Timer A is enabled.
}

void initializePORTF()
{
  volatile unsigned long delay;
  SYSCTL_RCGC2_R |= 0x00000020;     // 1) F clock
  delay = SYSCTL_RCGC2_R;           // delay   
  GPIO_PORTF_DIR_R |= 0x02;         // PF1 output  
  GPIO_PORTF_AFSEL_R &= 0x00;       // No alternate function// 1) F clock
  GPIO_PORTF_DEN_R |= 0x02;         // Enable digital pins PF1  
  GPIO_PORTF_DATA_R |= 0x02;        //PF1 Set to 1. LED is ON
}


int main()
{
    initializeTimer();
    initializePORTF();

    while(1)
    {
        //did TATORIS in GPTMRIS become 1??
        if((GPTMRIS | 0x00000001) == 1)
        {
            GPTMICR |= 0x00000001; //Set 1 to TATOCINT. Writing a 1 to this bit clears the TATORIS bit in the GPTMRIS register and the TATOMIS bit in the GPTMMIS register. 
            GPIO_PORTF_DATA_R ^= 0x02; //Toggle PF1. Toggle LED
        }
    }
}
\$\endgroup\$
  • \$\begingroup\$ @Mahendra Gunawardena Pin1 of port F (red LED on the board) \$\endgroup\$ – user3219492 Jan 6 '17 at 9:47
  • 2
    \$\begingroup\$ Just a heads-up; If you intend on using the controllers of this series (or indeed manufacturer), check the Silicon Errata Sheet. Which comes separately. Because for many of the 123's it's 110+ pages. \$\endgroup\$ – Asmyldof Jan 6 '17 at 10:09
  • \$\begingroup\$ I have posted a potential solution. Also I have always used interrupts with times. I don't see you enabling interrupts. \$\endgroup\$ – Mahendra Gunawardena Jan 6 '17 at 10:41
  • \$\begingroup\$ @Asmyldof +100. Especially for TM4C123 you need to be extra careful when designing your own board. One single little issue in errata can be a reason to add dozens of additional components to your PCB (see GPIO#10 for instance)... \$\endgroup\$ – GAttuso Jan 6 '17 at 14:53
  • \$\begingroup\$ @GAttuso if TI's "modern" Processor Design branch goes bankrupt tomorrow, I won't loose much sleep over it. \$\endgroup\$ – Asmyldof Jan 6 '17 at 17:06
1
\$\begingroup\$

Also here is some example code for TIVA Timer setup. You might be able look at this and get some idea

#define TIMER0_CFG_R            (*((volatile unsigned long *)0x40030000))
#define TIMER0_TAMR_R           (*((volatile unsigned long *)0x40030004))
#define TIMER0_CTL_R            (*((volatile unsigned long *)0x4003000C))
#define TIMER0_IMR_R            (*((volatile unsigned long *)0x40030018))
#define TIMER0_MIS_R            (*((volatile unsigned long *)0x40030020))
#define TIMER0_ICR_R            (*((volatile unsigned long *)0x40030024))
#define TIMER0_TAILR_R          (*((volatile unsigned long *)0x40030028))
#define TIMER0_TAPR_R           (*((volatile unsigned long *)0x40030038))
#define TIMER0_TAR_R            (*((volatile unsigned long *)0x40030048))
#define TIMER_CFG_16_BIT        0x00000004  // 16-bit timer configuration,
                                            // function is controlled by bits
                                            // 1:0 of GPTMTAMR and GPTMTBMR
#define TIMER_TAMR_TAMR_PERIOD  0x00000002  // Periodic Timer mode
#define TIMER_CTL_TAEN          0x00000001  // GPTM TimerA Enable
#define TIMER_IMR_TATOIM        0x00000001  // GPTM TimerA Time-Out Interrupt
                                            // Mask
#define TIMER_ICR_TATOCINT      0x00000001  // GPTM TimerA Time-Out Raw
                                            // Interrupt
#define TIMER_TAILR_TAILRL_M    0x0000FFFF  // GPTM TimerA Interval Load
                                            // Register Low
#define SYSCTL_RCGC1_R          (*((volatile unsigned long *)0x400FE104))
#define SYSCTL_RCGC1_TIMER0     0x00010000  // timer 0 Clock Gating Control

void DisableInterrupts(void); // Disable interrupts
void EnableInterrupts(void);  // Enable interrupts
long StartCritical (void);    // previous I bit, disable interrupts
void EndCritical(long sr);    // restore I bit to previous value
void WaitForInterrupt(void);  // low power mode
void (*PeriodicTask)(void);  // user function
// ***************** Timer0A_Init ****************
// Activate Timer0A interrupts to run user task periodically
// Inputs:  task is a pointer to a user function
//          period in usec
// Outputs: none
void Timer0A_Init(void(*task)(void), unsigned short period){ 
  SYSCTL_RCGC1_R |= SYSCTL_RCGC1_TIMER0; // 0) activate timer0
  PeriodicTask = task;             // user function 
  TIMER0_CTL_R &= ~0x00000001;     // 1) disable timer0A during setup
  TIMER0_CFG_R = 0x00000004;       // 2) configure for 16-bit timer mode
  TIMER0_TAMR_R = 0x00000002;      // 3) configure for periodic mode
  TIMER0_TAILR_R = period;         // 4) reload value
  TIMER0_TAPR_R = 49;              // 5) 1us timer0A
  TIMER0_ICR_R = 0x00000001;       // 6) clear timer0A timeout flag
  TIMER0_IMR_R |= 0x00000001;      // 7) arm timeout interrupt
  NVIC_PRI4_R = (NVIC_PRI4_R&0x00FFFFFF)|0x40000000; // 8) priority 2
  NVIC_EN0_R |= NVIC_EN0_INT19;    // 9) enable interrupt 19 in NVIC
  TIMER0_CTL_R |= 0x00000001;      // 10) enable timer0A
  EnableInterrupts();
}
void Timer0A_Handler(void){
  TIMER0_ICR_R = TIMER_ICR_TATOCINT;// acknowledge timer0A timeout
  (*PeriodicTask)();                // execute user task
}

On the TIVA, TM4C123GH6PM micro controller Port F is a special port. PF0 on TIVA need to be unlock.

enter image description here
Click on image for a larger version of the image.

Below is example code.

void PortF_Init(void){ volatile unsigned long delay;
  SYSCTL_RCGC2_R |= 0x00000020;     // 1) activate clock for Port F
  delay = SYSCTL_RCGC2_R;           // allow time for clock to start
  GPIO_PORTF_LOCK_R = 0x4C4F434B;   // 2) unlock GPIO Port F
  GPIO_PORTF_CR_R = 0x1F;           // allow changes to PF4-0
  // only PF0 needs to be unlocked, other bits can't be locked
  GPIO_PORTF_AMSEL_R = 0x00;        // 3) disable analog on PF
  GPIO_PORTF_PCTL_R = 0x00000000;   // 4) PCTL GPIO on PF4-0
  GPIO_PORTF_DIR_R = 0x0E;          // 5) PF4,PF0 in, PF3-1 out
  GPIO_PORTF_AFSEL_R = 0x00;        // 6) disable alt funct on PF7-0
  GPIO_PORTF_PUR_R = 0x11;          // enable pull-up on PF0 and PF4
  GPIO_PORTF_DEN_R = 0x1F;          // 7) enable digital I/O on PF4-0
}

Please take note of

GPIO_PORTF_LOCK_R = 0x4C4F434B; // 2) unlock GPIO Port F

Also I suggest you sign up for Embedded Systems - Shape The World. They use TIVA and it is great semi self-paced course.

References

\$\endgroup\$
  • \$\begingroup\$ Thank you for the reply. Unfortunately, UNLOCKING the PORT F made no difference. I also made use of the registers you provided (except that I chose to Poll instead of interrupt) and again the red LED is always ON. Thank you so much for the reference links (especially users.ece.utexas.edu/~valvano/arm) \$\endgroup\$ – user3219492 Jan 6 '17 at 19:50
  • \$\begingroup\$ @user3219492 Your are most welcome, I usually follow the course each year for fun. So identify yourself in the forums. Good luck. Also I notice that you are trying to use Pin 1, not Pin 0, only pin 0 in port F is locked. \$\endgroup\$ – Mahendra Gunawardena Jan 6 '17 at 23:30
  • \$\begingroup\$ Okay. I have posted the question in TI Community forums. Let's wait for that. So the unlocking statement in not going to make any effect as I am not using PF0. \$\endgroup\$ – user3219492 Jan 7 '17 at 5:45

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.