diff options
author | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2009-01-18 13:44:50 +0000 |
---|---|---|
committer | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2009-01-18 13:44:50 +0000 |
commit | 48d08ca9476ca38ba936ec7ff5ae3b79d8b02bd2 (patch) | |
tree | d4127b3644c8d3aa71498cac3439c82217ded90d /ports | |
parent | 140c2d06cdffd63ef06b258064f0065b8ddef140 (diff) | |
download | ChibiOS-48d08ca9476ca38ba936ec7ff5ae3b79d8b02bd2.tar.gz ChibiOS-48d08ca9476ca38ba936ec7ff5ae3b79d8b02bd2.tar.bz2 ChibiOS-48d08ca9476ca38ba936ec7ff5ae3b79d8b02bd2.zip |
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@634 35acf78f-673a-0410-8e92-d51de3d6d3f4
Diffstat (limited to 'ports')
-rw-r--r-- | ports/ARM7/chcore.c | 4 | ||||
-rw-r--r-- | ports/ARM7/port.dox | 5 | ||||
-rw-r--r-- | ports/ARMCM3/chcore.c | 10 | ||||
-rw-r--r-- | ports/ARMCM3/chcore.h | 45 | ||||
-rw-r--r-- | ports/ARMCM3/crt0.s | 21 | ||||
-rw-r--r-- | ports/ARMCM3/nvic.c | 20 | ||||
-rw-r--r-- | ports/ARMCM3/nvic.h | 17 | ||||
-rw-r--r-- | ports/ARMCM3/port.dox | 108 |
8 files changed, 207 insertions, 23 deletions
diff --git a/ports/ARM7/chcore.c b/ports/ARM7/chcore.c index d7d51c85b..9ffe94ac5 100644 --- a/ports/ARM7/chcore.c +++ b/ports/ARM7/chcore.c @@ -28,14 +28,18 @@ * Prints a message on the system console. * @param msg pointer to the message */
+/** @cond never */
__attribute__((weak))
+/** @endcond */
void port_puts(char *msg) {
}
/**
* Halts the system. */
+/** @cond never */
__attribute__((weak))
+/** @endcond */
void port_halt(void) {
port_disable();
diff --git a/ports/ARM7/port.dox b/ports/ARM7/port.dox index cf3532f96..9a9f319a6 100644 --- a/ports/ARM7/port.dox +++ b/ports/ARM7/port.dox @@ -105,7 +105,7 @@ /** @} */
/**
- * @defgroup ARM7CONF Configuration Options
+ * @defgroup ARM7_CONF Configuration Options
* @{
* @brief ARM7 specific configuration options.
* @details The ARM7 port allows some architecture-specific configurations
@@ -133,7 +133,8 @@ * @brief ARM7 specific port code, structures and macros.
*
* @ingroup ARM7
- * @file ports/ARM7/chcore.h Port related structures and macros.
* @file ports/ARM7/chtypes.h Port types.
+ * @file ports/ARM7/chcore.h Port related structures and macros.
+ * @file ports/ARM7/chcore.c Port related code.
*/
/** @} */
diff --git a/ports/ARMCM3/chcore.c b/ports/ARMCM3/chcore.c index acbc97d9b..3432a6577 100644 --- a/ports/ARMCM3/chcore.c +++ b/ports/ARMCM3/chcore.c @@ -32,7 +32,9 @@ * it in your application code. * @param msg pointer to the message string */
+/** @cond never */
__attribute__((weak))
+/** @endcond */
void port_puts(char *msg) {
}
@@ -41,7 +43,9 @@ void port_puts(char *msg) { * @note The function is declared as a weak symbol, it is possible to redefine
* it in your application code.
*/
+/** @cond never */
__attribute__((weak))
+/** @endcond */
void port_halt(void) {
port_disable();
@@ -53,7 +57,9 @@ void port_halt(void) { * Start a thread by invoking its work function.
* If the work function returns @p chThdExit() is automatically invoked.
*/
+/** @cond never */
__attribute__((naked, weak))
+/** @endcond */
void threadstart(void) {
asm volatile ("blx r1 \n\t" \
@@ -79,7 +85,9 @@ CH_IRQ_HANDLER void SysTickVector(void) { /**
* The SVC vector is used for commanded context switch.
*/
+/** @cond never */
__attribute__((naked))
+/** @endcond */
void SVCallVector(Thread *otp, Thread *ntp) {
/* { r0 = otp, r1 = ntp } */
/* get the BASEPRI in r3 */
@@ -146,7 +154,9 @@ void SVCallVector(Thread *otp, Thread *ntp) { /**
* Preemption invoked context switch.
*/
+/** @cond never */
__attribute__((naked))
+/** @endcond */
void PendSVVector(void) {
Thread *otp;
register struct intctx *sp_thd asm("r12");
diff --git a/ports/ARMCM3/chcore.h b/ports/ARMCM3/chcore.h index 831e03527..4ac271c79 100644 --- a/ports/ARMCM3/chcore.h +++ b/ports/ARMCM3/chcore.h @@ -28,16 +28,51 @@ /*
* Port-related configuration parameters.
*/
+
+/** Enables the use of the WFI ins. */
+#ifndef ENABLE_WFI_IDLE
+#define ENABLE_WFI_IDLE 0
+#endif
+
+/** BASEPRI user level, 0 = disabled. */
#ifndef BASEPRI_USER
-#define BASEPRI_USER 0 /* User level BASEPRI, 0 = disabled. */
+#define BASEPRI_USER 0
#endif
+/**
+ * BASEPRI level within kernel lock.
+ * Priority levels higher than this one (lower values) are unaffected by
+ * the OS activity and can be classified as fast interrupt sources, see
+ * @ref interrupt_classes.
+ */
#ifndef BASEPRI_KERNEL
-#define BASEPRI_KERNEL 0x10 /* BASEPRI level within kernel lock. */
+#define BASEPRI_KERNEL 0x40
#endif
-#ifndef ENABLE_WFI_IDLE
-#define ENABLE_WFI_IDLE 0 /* Enables the use of the WFI ins. */
+/**
+ * SVCALL handler priority.
+ * @note This priority must always be one level above the @p BASEPRI_KERNEL
+ * value.
+ * @note It is recommended to leave this priority level for this handler alone.
+ */
+#ifndef PRIORITY_SVCALL
+#define PRIORITY_SVCALL (BASEPRI_KERNEL - 0x10)
+#endif
+
+/** SYSTICK handler priority. */
+#ifndef PRIORITY_SYSTICK
+#define PRIORITY_SYSTICK 0x80
+#endif
+
+/**
+ * PENDSV handler priority.
+ * @note It is recommended to leave this priority level for this handler alone.
+ * @note This is a reserved handler and its priority must always be the
+ * lowest priority in the system in order to be always executed last
+ * in the interrupt servicing chain.
+ */
+#ifndef PRIORITY_PENDSV
+#define PRIORITY_PENDSV 0xF0
#endif
/**
@@ -233,7 +268,7 @@ typedef struct { /**
* This port function is implemented as inlined code for performance reasons.
*/
-#define port_switch(otp, ntp) { \
+#define port_switch(otp, ntp) { \
register Thread *_otp asm ("r0") = (otp); \
register Thread *_ntp asm ("r1") = (ntp); \
asm volatile ("svc #0" : : "r" (_otp), "r" (_ntp)); \
diff --git a/ports/ARMCM3/crt0.s b/ports/ARMCM3/crt0.s index a7ebb59be..d31b36475 100644 --- a/ports/ARMCM3/crt0.s +++ b/ports/ARMCM3/crt0.s @@ -37,6 +37,8 @@ .thumb_func .global ResetHandler ResetHandler: + /* Interrupts globally masked. */ + cpsid i /* * Stack pointers initialization. */ @@ -47,9 +49,7 @@ ResetHandler: msr PSP, r0 // ldr r1, =__process_stack_size__ // sub r0, r0, r1 - /* - * Early initialization. - */ + /* Early initialization. */ bl hwinit0 /* * Data initialization. @@ -76,22 +76,13 @@ bloop: itt lo strlo r0, [r1], #4 blo bloop - /* - * Switches to the Process Stack and disables the interrupts globally. - */ + /* Switches to the Process Stack. */ movs r0, #CONTROL_MODE_PRIVILEGED | CONTROL_USE_PSP msr CONTROL, r0 isb - movs r0, #0x10 - msr BASEPRI, r0 - cpsie i - /* - * Late initialization. - */ + /* Late initialization. */ bl hwinit1 - /* - * main(0, NULL). - */ + /* main(0, NULL). */ movs r0, #0 mov r1, r0 bl main diff --git a/ports/ARMCM3/nvic.c b/ports/ARMCM3/nvic.c index dbb4935c0..a054ed163 100644 --- a/ports/ARMCM3/nvic.c +++ b/ports/ARMCM3/nvic.c @@ -20,9 +20,27 @@ #include <ch.h>
#include <nvic.h>
+/**
+ * Sets the priority of an interrupt handler and enables it.
+ * @param n the interrupt number
+ * @param prio the interrupt priority
+ * @note The parameters are not tested for correctness.
+ */
void NVICEnableVector(uint32_t n, uint32_t prio) {
- int sh = (n & 3) << 3;
+ unsigned sh = (n & 3) << 3;
NVIC_IPR(n >> 2) = (NVIC_IPR(n >> 2) & ~(0xFF << sh)) | (prio << sh);
NVIC_ISER(n >> 5) = 1 << (n & 0x1F);
}
+
+/**
+ * Changes the priority of a system handler. + * @param handler the system handler number + * @param prio the system handler priority
+ * @note The parameters are not tested for correctness. + */
+void NVICSetSystemHandlerPriority(uint32_t handler, uint32_t prio) {
+ unsigned sh = (handler & 3) * 8;
+
+ SCB_SHPR(handler >> 2) = (SCB_SHPR(handler >> 2) & ~(0xFF << sh)) | (prio << sh);
+}
diff --git a/ports/ARMCM3/nvic.h b/ports/ARMCM3/nvic.h index 13a04fe78..3876410e5 100644 --- a/ports/ARMCM3/nvic.h +++ b/ports/ARMCM3/nvic.h @@ -20,6 +20,22 @@ #ifndef _NVIC_H_
#define _NVIC_H_
+/*
+ * System vector constants for @p NVICSetSystemHandlerPriority(). + */
+#define HANDLER_MEM_MANAGE 0
+#define HANDLER_BUS_FAULT 1
+#define HANDLER_USAGE_FAULT 2
+#define HANDLER_RESERVED_3 3
+#define HANDLER_RESERVED_4 4
+#define HANDLER_RESERVED_5 5
+#define HANDLER_RESERVED_6 6
+#define HANDLER_SVCALL 7
+#define HANDLER_DEBUG_MONITOR 8
+#define HANDLER_RESERVED_9 9
+#define HANDLER_PENDSV 10
+#define HANDLER_SYSTICK 11
+
typedef volatile unsigned char IOREG8;
typedef volatile unsigned int IOREG32;
@@ -132,6 +148,7 @@ typedef struct { extern "C" {
#endif
void NVICEnableVector(uint32_t n, uint32_t prio);
+ void NVICSetSystemHandlerPriority(uint32_t handler, uint32_t prio);
#ifdef __cplusplus
}
#endif
diff --git a/ports/ARMCM3/port.dox b/ports/ARMCM3/port.dox new file mode 100644 index 000000000..28372e399 --- /dev/null +++ b/ports/ARMCM3/port.dox @@ -0,0 +1,108 @@ +/**
+ * @defgroup ARMCM3 ARM Cortex-M3
+ * @{
+ * @details The ARM Cortex-M3 architecture is quite complex for a
+ * microcontroller and some explanations are required about the port choices.
+ *
+ * @section ARMCM3_STATES Mapping of the System States in the ARM Cortex-M3 port
+ * The ChibiOS/RT logical @ref system_states are mapped as follow in the ARM
+ * Cortex-M3 port:
+ * - <b>Initialization</b>. This state is represented by the startup code and
+ * the initialization code before @p chSysInit() is executed. It has not a
+ * special hardware state associated.
+ * - <b>Normal</b>. This is the state the system has after executing
+ * @p chSysInit(). In this state the ARM Cortex-M3 has the BASEPRI register
+ * set at @p BASEPRI_USER level, interrupts are not masked. The processor
+ * is running in thread-privileged mode.
+ * - <b>Suspended</b>. In this state the interrupt sources are not globally
+ * masked but the BASEPRI register is set to @p BASEPRI_KERNEL thus masking
+ * any interrupt source with lower or equal priority. The processor
+ * is running in thread-privileged mode.
+ * - <b>Disabled</b>. Interrupt sources are globally masked. The processor
+ * is running in thread-privileged mode.
+ * - <b>Sleep</b>. This state is entered with the execution of the specific
+ * instruction @p <b>wfi</b>.
+ * - <b>S-Locked</b>. In this state the interrupt sources are not globally
+ * masked but the BASEPRI register is set to @p BASEPRI_KERNEL thus masking
+ * any interrupt source with lower or equal priority. The processor
+ * is running in thread-privileged mode.
+ * - <b>I-Locked</b>. In this state the interrupt sources are not globally
+ * masked but the BASEPRI register is set to @p BASEPRI_KERNEL thus masking
+ * any interrupt source with lower or equal priority. The processor
+ * is running in exception-privileged mode.
+ * - <b>Serving Regular Interrupt</b>. In this state the interrupt sources are
+ * not globally masked but only interrupts with higher priority can preempt
+ * the current handler. The processor is running in exception-privileged mode.
+ * - <b>Serving Fast Interrupt</b>. It is basically the same of the SRI state
+ * but it is not possible to switch to the I-Locked state because fast
+ * interrupts can preempt the kernel critical zone.
+ * - <b>Serving Non-Maskable Interrupt</b>. The Cortex-M3 has a specific
+ * asynchronous NMI vector and several synchronous fault vectors that can
+ * be considered to be in this category.
+ * - <b>Halted</b>. Implemented as an infinite loop after globally masking all
+ * the maskable interrupt sources. The ARM state is whatever the processor
+ * was running when @p chSysHalt() was invoked.
+ *
+ * @section ARMCM3_NOTES The ARM Cortex-M3 port notes
+ * The ARM Cortex-M3 port is organized as follow:
+ * - The @p main() function is invoked in thread-privileged mode.
+ * - Each thread has a private process stack, the system has a single main
+ * stack where all the interrupts and exceptions are processed.
+ * - Only the 4 MSb of the priority level are used, the 4 LSb are assumed
+ * to be zero.
+ * - The threads are started in thread-privileged mode with BASEPRI level
+ * 0x00 (disabled).
+ * - The kernel raises its BASEPRI level to @p BASEPRI_KERNEL in order to
+ * protect the kernel data structures.
+ * - Interrupt nesting and the other advanced NVIC features are supported.
+ * - The SVC instruction and vector, with parameter #0, is internally used
+ * for commanded context switching.<br>
+ * It is possible to share the SVC handler at the cost of slower context
+ * switching.
+ * - The PendSV vector is internally used for preemption context switching.
+ *
+ * @ingroup Ports
+ */
+/** @} */
+
+/**
+ * @defgroup ARMCM3_CONF Configuration Options
+ * @{
+ * @brief ARM Cortex-M3 Configuration Options.
+ * The ARMCM3 port allows some architecture-specific configurations settings
+ * that can be specified externally, as example on the compiler command line:
+ * - @p INT_REQUIRED_STACK, this value represent the amount of stack space used
+ * by an interrupt handler between the @p extctx and @p intctx
+ * structures.<br>
+ * In the current implementation this value is guaranteed to be zero so
+ * there is no need to modify this value unless changes are done at the
+ * interrupts handling code.
+ * - @p BASEPRI_USER, this is the @p BASEPRI value for the user threads. The
+ * default value is @p 0 (disabled).<br>
+ * Usually there is no need to change this value, please refer to the
+ * Cortex-M3 technical reference manual for a detailed description.
+ * - @p BASEPRI_KERNEL, this is the @p BASEPRI value for the kernel lock code.
+ * The default value is 0x10.<br>
+ * Code running at higher priority levels must not invoke any OS API.<br>
+ * Usually there is no need to change this value, please refer to the
+ * Cortex-M3 technical reference manual for a detailed description.
+ * - @p ENABLE_WFI_IDLE, if set to @p 1 enables the use of the @p <b>wfi</b>
+ * instruction from within the idle loop. This is defaulted to 0 because
+ * it can create problems with some debuggers. Setting this option to 1
+ * reduces the system power requirements.
+ *
+ * @ingroup ARMCM3
+ */
+/** @} */
+
+/**
+ * @defgroup ARMCM3_CORE ARM Cortex-M3 Core Implementation
+ * @{
+ * @brief ARM Cortex-M3 specific port code, structures and macros.
+ *
+ * @ingroup ARMCM3
+ * @file ports/ARMCM3/chtypes.h Port types.
+ * @file ports/ARMCM3/chcore.h Port related structures and macros.
+ * @file ports/ARMCM3/chcore.c Port related code.
+ */
+/** @} */
|