From fdda5cf665b802b31be27ca55a849a5732620f6b Mon Sep 17 00:00:00 2001 From: Matt Mullins Date: Sat, 22 Dec 2012 21:59:45 -0800 Subject: [PATCH] Use SysTick instead of a busy loop to blink the LED once per second --- isr_table.c | 2 +- led_blink.c | 34 +++++++++++++++++++++++++++++++--- led_blink.h | 1 + 3 files changed, 33 insertions(+), 4 deletions(-) diff --git a/isr_table.c b/isr_table.c index e013b40..33306c8 100644 --- a/isr_table.c +++ b/isr_table.c @@ -19,7 +19,7 @@ void (*reset_vectors[])() = { infinite_loop_isr, infinite_loop_isr, infinite_loop_isr, - infinite_loop_isr, + systick_isr, infinite_loop_isr, infinite_loop_isr, infinite_loop_isr, diff --git a/led_blink.c b/led_blink.c index 657255a..ddf5325 100644 --- a/led_blink.c +++ b/led_blink.c @@ -3,6 +3,12 @@ static void spin(int); +// Since SysTick is only 24-bits, we'll need to divide it by 4 to produce a +// 2Hz value from the 80MHz system clock. +// Yes, I know I can just run the system clock slower, but this is more fun. +static const int initial_systick_count = 3; +static int systick_count; + __attribute__((isr)) void main_isr() { // Power on the PLL, set to 16MHz XTAL @@ -44,13 +50,24 @@ void main_isr() { GPIO_PORTF_DEN_R = 0xE; // Set RGB pins to 1 - *(GPIO_PORTF_DATA_BITS_R + 0xE) = 0x2; + *(GPIO_PORTF_DATA_BITS_R + 0xE) = 0xF; + + // Initialize our SysTick prescaler + systick_count = initial_systick_count; + + // Initialize the SysTick module + NVIC_ST_RELOAD_R = 10000000; // produce 8Hz from 80MHz clock + NVIC_ST_CURRENT_R = 0; + NVIC_ST_CTRL_R |= 0x7; // infinite loop for (;;) { - *(GPIO_PORTF_DATA_BITS_R + 0xC) ^= 0xC; + asm("wfi"); - spin(1000000); + // flip the green LED on every WFI, as an experiment to see if the + // CPU is really sleeping. + // Answer: it is. + // *(GPIO_PORTF_DATA_BITS_R + 0x8) ^= 0xFF; } } @@ -61,3 +78,14 @@ void spin(int cycles) { asm(""); } } + +__attribute__((isr)) +void systick_isr() { + if (systick_count) { + systick_count--; + return; + } + + systick_count = initial_systick_count; + *(GPIO_PORTF_DATA_BITS_R + 0xE) ^= 0xF; +} diff --git a/led_blink.h b/led_blink.h index 24c4feb..ed70066 100644 --- a/led_blink.h +++ b/led_blink.h @@ -2,5 +2,6 @@ #define __led_blink_H__ extern void main_isr(); +extern void systick_isr(); #endif -- 2.11.0