aboutsummaryrefslogtreecommitdiffstats
path: root/libmaple
diff options
context:
space:
mode:
authorPerry Hung <iperry@alum.mit.edu>2010-08-04 08:52:30 -0400
committerPerry Hung <iperry@alum.mit.edu>2010-08-04 08:52:30 -0400
commitd2494611156c4ba477a1bbd1b07ba0cfc14b29e4 (patch)
tree48782014152efa392ac0689c4098e089da52c82c /libmaple
parent2b7a1b40c96525cd4c6324f6e9d53845fb07a55f (diff)
downloadlibrambutan-d2494611156c4ba477a1bbd1b07ba0cfc14b29e4.tar.gz
librambutan-d2494611156c4ba477a1bbd1b07ba0cfc14b29e4.zip
Cleaned up wirish/time, some interrupt handling refactoring:
Fixed millis(), it was just wrong, before. Added micros(), not extensively tested. New implementation of delayMicroseconds(). Should be more consistent now. Added a handful of nvic routines to enable/disable interrupts. Cleaned up systick
Diffstat (limited to 'libmaple')
-rw-r--r--libmaple/nvic.c26
-rw-r--r--libmaple/nvic.h21
-rw-r--r--libmaple/systick.c18
-rw-r--r--libmaple/systick.h25
-rw-r--r--libmaple/timers.c9
-rw-r--r--libmaple/usart.c2
-rw-r--r--libmaple/util.h2
7 files changed, 42 insertions, 61 deletions
diff --git a/libmaple/nvic.c b/libmaple/nvic.c
index d8745a4..56b9940 100644
--- a/libmaple/nvic.c
+++ b/libmaple/nvic.c
@@ -32,16 +32,6 @@
#include "nvic.h"
#include "systick.h"
-void nvic_disable_interrupts(void) {
- /* Turn off all interrupts */
- REG_SET(NVIC_ICER0, 0xFFFFFFFF);
- REG_SET(NVIC_ICER1, 0xFFFFFFFF);
-
- /* Turn off systick exception */
- REG_CLEAR_BIT(SYSTICK_CSR, 0);
-}
-
-
void nvic_set_vector_table(uint32 addr, uint32 offset) {
__write(SCB_VTOR, (uint32)addr | (offset & 0x1FFFFF80));
}
@@ -49,13 +39,9 @@ void nvic_set_vector_table(uint32 addr, uint32 offset) {
/**
* @brief turn on interrupt number n
- * @param[in] n interrupt number
+ * @param n interrupt number
*/
-void nvic_enable_interrupt(uint32 n) {
- if (n >= NVIC_NR_INTERRUPTS) {
- return;
- }
-
+void nvic_irq_enable(uint32 n) {
if (n < 32) {
REG_SET_BIT(NVIC_ISER0, n);
} else {
@@ -65,13 +51,9 @@ void nvic_enable_interrupt(uint32 n) {
/**
* @brief turn off interrupt number n
- * @param[in] n interrupt number
+ * @param n interrupt number
*/
-void nvic_disable_interrupt(uint32 n) {
- if (n >= NVIC_NR_INTERRUPTS) {
- return;
- }
-
+void nvic_irq_disable(uint32 n) {
if (n < 32) {
REG_SET_BIT(NVIC_ICER0, n);
} else {
diff --git a/libmaple/nvic.h b/libmaple/nvic.h
index 6cad48d..d256610 100644
--- a/libmaple/nvic.h
+++ b/libmaple/nvic.h
@@ -52,8 +52,6 @@
#define NVIC_VectTab_RAM ((u32)0x20000000)
#define NVIC_VectTab_FLASH ((u32)0x08000000)
-#define NVIC_NR_INTERRUPTS 60
-
/* Where to put code */
#define USER_ADDR_ROM 0x08005000
#define USER_ADDR_RAM 0x20000C00
@@ -63,15 +61,22 @@ extern "C"{
#endif
enum {
- NVIC_USART1 = 37,
- NVIC_USART2 = 38,
- NVIC_USART3 = 39,
+ NVIC_TIMER1 = 27,
+ NVIC_TIMER2 = 28,
+ NVIC_TIMER3 = 29,
+ NVIC_TIMER4 = 30,
+ NVIC_USART1 = 37,
+ NVIC_USART2 = 38,
+ NVIC_USART3 = 39,
};
+
+#define nvic_globalirq_enable() asm volatile("cpsid i")
+#define nvic_globalirq_disable() asm volatile("cpsie i")
+
void nvic_init(void);
-void nvic_disable_interrupts(void);
-void nvic_enable_interrupt(uint32 device);
-void nvic_disable_interrupt(uint32 device);
+void nvic_irq_enable(uint32 device);
+void nvic_irq_disable(uint32 device);
#ifdef __cplusplus
}
diff --git a/libmaple/systick.c b/libmaple/systick.c
index a333528..8b0d92a 100644
--- a/libmaple/systick.c
+++ b/libmaple/systick.c
@@ -31,23 +31,25 @@
#include "libmaple.h"
#include "systick.h"
-#define MILLIS_INC 1
+#define SYSTICK_RELOAD 0xE000E014 // Reload value register
+#define SYSTICK_CNT 0xE000E018 // Current value register
+#define SYSTICK_CALIB 0xE000E01C // Calibration value register
+
+#define SYSTICK_SRC_HCLK BIT(2) // Use core clock
+#define SYSTICK_TICKINT BIT(1) // Interrupt on systick countdown
+#define SYSTICK_ENABLE BIT(0) // Turn on the counter
volatile uint32 systick_timer_millis = 0;
-void systick_init(void) {
+void systick_init(uint32 reload_val) {
/* Set the reload counter to tick every 1ms */
- REG_SET_MASK(SYSTICK_RELOAD, MAPLE_RELOAD_VAL);
-// SYSTICK_RELOAD = MAPLE_RELOAD_VAL;
+ __write(SYSTICK_RELOAD, reload_val);
/* Clock the system timer with the core clock
* and turn it on, interrrupt every 1ms to keep track of millis()*/
- REG_SET(SYSTICK_CSR, SYSTICK_SRC_HCLK |
+ __write(SYSTICK_CSR, SYSTICK_SRC_HCLK |
SYSTICK_ENABLE |
SYSTICK_TICKINT);
-// SYSTICK_CSR = SYSTICK_SRC_HCLK |
-// SYSTICK_ENABLE |
-// SYSTICK_TICKINT;
}
void SysTickHandler(void) {
diff --git a/libmaple/systick.h b/libmaple/systick.h
index d0a623f..57b724a 100644
--- a/libmaple/systick.h
+++ b/libmaple/systick.h
@@ -33,30 +33,23 @@
#include "libmaple.h"
-/* To the ARM technical manual... there's nearly nothing on the systick
- * timer in the stm32 manual */
+#define SYSTICK_CSR 0xE000E010 // Control and status register
+#define SYSTICK_CNT 0xE000E018 // Current value register
-#define SYSTICK_CSR 0xE000E010 // Control and status register
-#define SYSTICK_RELOAD 0xE000E014 // Reload value register
-#define SYSTICK_CNT 0xE000E018 // Current value register
-#define SYSTICK_CALIB 0xE000E01C // Calibration value register
-
-#define SYSTICK_SRC_HCLK BIT(2) // Use core clock
-#define SYSTICK_TICKINT BIT(1) // Interrupt on systick countdown
-#define SYSTICK_ENABLE BIT(0) // Turn on the counter
-
-/* We use the systick timer to tick once
- * every millisecond */
-#define MAPLE_RELOAD_VAL 72000
+#define SYSTICK_CSR_COUNTFLAG BIT(16)
#ifdef __cplusplus
extern "C"{
#endif
-void systick_init(void);
+void systick_init(uint32 reload_val);
static inline uint32 systick_get_count(void) {
- return (uint32)*(volatile uint32*)SYSTICK_CNT;
+ return __read(SYSTICK_CNT);
+}
+
+static inline uint32 systick_check_underflow(void) {
+ return (__read(SYSTICK_CSR) & SYSTICK_CSR_COUNTFLAG);
}
#ifdef __cplusplus
diff --git a/libmaple/timers.c b/libmaple/timers.c
index a3890d4..6e6653c 100644
--- a/libmaple/timers.c
+++ b/libmaple/timers.c
@@ -30,6 +30,7 @@
#include "libmaple.h"
#include "rcc.h"
+#include "nvic.h"
#include "timers.h"
typedef struct {
@@ -476,25 +477,25 @@ void timer_attach_interrupt(uint8 timer_num, uint8 compare_num, voidFuncPtr hand
case 1:
timer = (Timer*)TIMER1_BASE;
timer1_handlers[compare_num-1] = handler;
- nvic_enable_interrupt(27);
+ nvic_irq_enable(NVIC_TIMER1);
timer->DIER |= (1 << compare_num); // 1-indexed compare nums
break;
case 2:
timer = (Timer*)TIMER2_BASE;
timer2_handlers[compare_num-1] = handler;
- nvic_enable_interrupt(28);
+ nvic_irq_enable(NVIC_TIMER2);
timer->DIER |= (1 << compare_num); // 1-indexed compare nums
break;
case 3:
timer = (Timer*)TIMER3_BASE;
timer3_handlers[compare_num-1] = handler;
- nvic_enable_interrupt(29);
+ nvic_irq_enable(NVIC_TIMER3);
timer->DIER |= (1 << compare_num); // 1-indexed compare nums
break;
case 4:
timer = (Timer*)TIMER4_BASE;
timer4_handlers[compare_num-1] = handler;
- nvic_enable_interrupt(30);
+ nvic_irq_enable(NVIC_TIMER4);
timer->DIER |= (1 << compare_num); // 1-indexed compare nums
break;
}
diff --git a/libmaple/usart.c b/libmaple/usart.c
index 53a6150..296a1fb 100644
--- a/libmaple/usart.c
+++ b/libmaple/usart.c
@@ -93,7 +93,7 @@ void usart_init(uint8 usart_num, uint32 baud) {
port = usart_dev_table[usart_num].base;
rcc_clk_enable(usart_dev_table[usart_num].rcc_dev_num);
- nvic_enable_interrupt(usart_dev_table[usart_num].nvic_dev_num);
+ nvic_irq_enable(usart_dev_table[usart_num].nvic_dev_num);
/* usart1 is mad fast */
clk_speed = (usart_num == USART1) ? 72000000UL : 36000000UL;
diff --git a/libmaple/util.h b/libmaple/util.h
index 8cfc60c..c336e21 100644
--- a/libmaple/util.h
+++ b/libmaple/util.h
@@ -48,8 +48,6 @@
#define BITBAND_PERI_BASE 0x42000000
#define BITBAND_PERI(a,b) ((BITBAND_PERI_BASE + (a-BITBAND_PERI_REF)*32 + (b*4))) // Convert PERI address
-#define COUNTFLAG *((volatile unsigned char*) (BITBAND_PERI(SYSTICK_CSR,2)))
-
#define REG_SET(reg, val) (*(volatile uint32*)(reg) = (val))
#define REG_SET_BIT(reg, bit) (*(volatile uint32*)(reg) |= BIT(bit))
#define REG_CLEAR_BIT(reg, bit) (*(volatile uint32*)(reg) &= ~BIT(bit))