Using Systick Timer with TM4C123GH6PM Launchpad

From EdWiki

Revision as of 09:40, 1 September 2017 by Jshankar (Talk | contribs)

Using Systick Timer with TM4C123GH6PM Launchpad

So far we have learned that how to program general purpose input output(GPIO) of ARM Cortex M-4. But we have not generated the delay in micro controller. In this section we will generate delay using different methods and blink on board LEDs. There are two types of delays that can be generated by our program:

  1. Software delay
  2. Hardware delay
  • Software delay
This type of delay is nothing but making the controller busy, doing the task which will occupy a certain duration. For example if we want our friend to wait for us then instead of telling him to wait we can simply engage him in other task. But the generated time may or may not be so accurate.

Example: In C code if we can use this for loop for generating a delay of 1 second.

void delay_1sec(void)
   for( unsigned long i = 0; i <= 3000000; i++ )

This method doesn’t generate the accurate time delay, but approximate. For generation of accurate delay in microsecond we prefer hardware delay.

  • Hardware delay
The hardware delay is most precise method to generate delay. In this method we use timer which is the most popular and useful feature of microcontrollers. Generally delay with timer is like waiting a bucket to be empty if we make a small hole to leak its filled liquid more the liquid more time it will take to empty the bucket. In this article, we are going to use a special timer called systick timer. In our micro controller we have six 64 bit and six 32 bit timer excluding systick timer. This timer is very useful and plays very important role in RTOS design. We will see other timers later. In our micro controller, Systick timer is 24 bit wide. For the generation of delay, at first we need to make sure that our controller is working on the clock frequency as we are expecting. This step is required to select the clock source only at external crystal without PLL.

As we learned earlier that modifying registers are the key for configuration and desired functionality. Hence systick timer can be used by modifying these registers.

  1. Systick Reload value (STRELOAD)
  2. Systick Control and Status Register (STCTRL)
  3. Systick Current Value (STCURRENT)

Systick Reload Value Register

This register acts like a bucket filled with a liquid that will be empty after some time duration and we will get acknowledgement by a change in flag bit in STCTRL Register. This register is 24 bit wide.

Tm4c123 systic streload.png

since this register is 24 bit wide it can store upto 0xFFFFFF or 16777215. when we load any value into this register and trigger the timer it starts to count down and when the value reaches to 0 it sets the COUNT FLAG. We will see how to reload and check flag bit in the next few steps.

Delay time calculation:

Since we are working with external clock i.e. 16 MHz, each pulse generated by the clock source will have

1/XTAL frequency = 1/(16*10^6)=2.5 ns

time period. so if we load 253 into the RELOAD register it and trigger the counter it will count down with next pulse and will take 2.5ns to change its value from 253 to 252. Hence, In order to generate the delay, we can calculate the approximate value that has to be loaded into this register by the formula-

Reload Value = XTAL*Time delay

one extra clock delay is already included to set the flag for rollover, hence we get one extra clock delay. By subtracting by one will give exact time delay.

Reload Value = (XTAL*Time Delay)-1

Remember that in one shoot, it can only take 0xFFFFFF maximum value. Therefore in one shoot, we can only generate maximum of Time delay

TimeDelay = (ReloadValue +1)/XTAL= 16777215+(1/(16*10^6))
TimeDelay = 1.048 sec.

Systick control and Status register

This register is shown in the following figure

Tm4c123 systic stctrl.png

we need to set our main clock to external by setting CLK_SRC to 1. And we don’t want interrupt method so INTEN bit will be 0. Now we are going to trigger our timer by writing ENABLE bit 1 so writing 0x5 will trigger our timer at the same time it will also set the configuration. Now the loaded value will be started to count down. When the timer gets rollover the bit 16 will set to one. hence we need to monitor 16th bit.

Example: For generating 1 sec of delay the value that has to be load into the RELOAD Register

= (XTAL*Time delay)-1
= (16*10^6*1)-1
= 15999999

So our code for generating delay of one second will looks like

  1. //
  2. #include <stdint.h>
  3. #include "inc/tm4c123gh6pm.h"
  5. #define  LED_RED    (GPIO_PORTF_DATA_R=0x02)
  6. #define  LED_BLUE   (GPIO_PORTF_DATA_R=0x04)
  7. #define  LED_GREEN  (GPIO_PORTF_DATA_R=0x08)
  8. #define  LED_WHITE  (GPIO_PORTF_DATA_R=0x0E)
  9. #define  LED_DARK   (GPIO_PORTF_DATA_R=0x00)
  10. #define  LED_YELLOW (GPIO_PORTF_DATA_R=0x0A)
  11. #define  LED_SKYBLUE (GPIO_PORTF_DATA_R=0x0C)
  12. //
  13. void One_Second_Delay(void);
  14. void Init_PortF(void);
  16. /**
  17.  * main.c
  18.  */
  19. int main(void)
  20. {
  21.     Init_PortF();               // Onboard LEDs and swithes from gpio.h
  23.     while(1){
  24.         LED_RED;                // Red color
  25.         One_Second_Delay();     // delay of 1 sec
  26.         LED_GREEN;              // Green color
  27.         One_Second_Delay();     // delay of 1 sec
  28.         LED_BLUE;               // Blue color
  29.         One_Second_Delay();     // delay of 1 sec
  30.         LED_YELLOW;             // Yellow color
  31.         One_Second_Delay();     // delay of 1 sec
  32.         LED_SKYBLUE;            // Sky blue color
  33.         One_Second_Delay();     // delay of 1 sec
  34.         LED_WHITE;              // White color
  35.         One_Second_Delay();     // delay of 1 sec
  36.     }
  37.     return 0;
  38. }
  40. void One_Second_Delay(void)
  41. {
  42.     NVIC_ST_RELOAD_R = 15999999;    // Reload Value goes here
  43.     NVIC_ST_CTRL_R |= 0x5;          // Triggering with external clock
  44.     while( (NVIC_ST_CTRL_R & (1<<16) ) == 0)
  45.         ;                           // Monitoring bit 16 to be set
  46.     NVIC_ST_CTRL_R = 0;             //Disabling SysTick Timer
  47. }
  49. // This function initializes the Switches and led connected to PORTF
  50. void Init_PortF(void)
  51. {
  52.     volatile unsigned long delay;
  54.     SYSCTL_RCGC2_R |= 0x00000020;     // 1) activate clock for Port F
  55.     delay = SYSCTL_RCGC2_R;           // allow time for clock to start
  57.     GPIO_PORTF_LOCK_R = 0x4C4F434B;   // 2) unlock GPIO Port F
  58.     GPIO_PORTF_CR_R = 0x1F;           // allow changes to PF4-0
  59.     GPIO_PORTF_AMSEL_R = 0x00;        // 3) disable analog on PF
  60.     GPIO_PORTF_PCTL_R = 0x00000000;   // 4) PCTL GPIO on PF4-0
  61.     GPIO_PORTF_DIR_R = 0x0E;          // 5) PF4,PF0 in, PF3-1 out
  62.     GPIO_PORTF_AFSEL_R = 0x00;        // 6) disable alt funct on PF7-0
  63.     GPIO_PORTF_PUR_R = 0x11;          // enable pull-up on PF0 and PF4
  64.     GPIO_PORTF_DEN_R = 0x1F;          // 7) enable digital I/O on PF4-0
  65.  }