diff options
author | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2011-12-17 09:17:15 +0000 |
---|---|---|
committer | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2011-12-17 09:17:15 +0000 |
commit | 590fe7872d776200c5d188c945d673d0bbd4dd48 (patch) | |
tree | 7430220b3279a9fce25fd5659757e990ec8b18f4 | |
parent | af25622db89ab50b7bad608792b1cb5a42b900c5 (diff) | |
download | ChibiOS-590fe7872d776200c5d188c945d673d0bbd4dd48.tar.gz ChibiOS-590fe7872d776200c5d188c945d673d0bbd4dd48.tar.bz2 ChibiOS-590fe7872d776200c5d188c945d673d0bbd4dd48.zip |
CM3 FPU support fix.
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@3622 35acf78f-673a-0410-8e92-d51de3d6d3f4
-rw-r--r-- | docs/reports/STM32F407-168-GCC-FPU.txt | 26 | ||||
-rw-r--r-- | os/ports/GCC/ARMCMx/chcore_v7m.c | 67 |
2 files changed, 41 insertions, 52 deletions
diff --git a/docs/reports/STM32F407-168-GCC-FPU.txt b/docs/reports/STM32F407-168-GCC-FPU.txt index 0f8e9dc91..6605e4d62 100644 --- a/docs/reports/STM32F407-168-GCC-FPU.txt +++ b/docs/reports/STM32F407-168-GCC-FPU.txt @@ -6,7 +6,7 @@ Settings: SYSCLK=168, ACR=0x705 (5 wait states) *** ChibiOS/RT test suite
***
*** Kernel: 2.3.5unstable
-*** Compiled: Dec 12 2011 - 20:40:15
+*** Compiled: Dec 17 2011 - 10:02:17
*** Compiler: GCC 4.6.2
*** Architecture: ARMv7-ME
*** Core Variant: Cortex-M4F
@@ -100,51 +100,51 @@ Settings: SYSCLK=168, ACR=0x705 (5 wait states) --- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.1 (Benchmark, messages #1)
---- Score : 559422 msgs/S, 1118844 ctxswc/S
+--- Score : 559411 msgs/S, 1118822 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.2 (Benchmark, messages #2)
---- Score : 476781 msgs/S, 953562 ctxswc/S
+--- Score : 476772 msgs/S, 953544 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.3 (Benchmark, messages #3)
---- Score : 476781 msgs/S, 953562 ctxswc/S
+--- Score : 476772 msgs/S, 953544 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.4 (Benchmark, context switch)
---- Score : 1639392 ctxswc/S
+--- Score : 1639368 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.5 (Benchmark, threads, full cycle)
---- Score : 371307 threads/S
+--- Score : 371300 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.6 (Benchmark, threads, create only)
---- Score : 496538 threads/S
+--- Score : 496529 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.7 (Benchmark, mass reschedule, 5 threads)
---- Score : 151022 reschedules/S, 906132 ctxswc/S
+--- Score : 151019 reschedules/S, 906114 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.8 (Benchmark, round robin context switching)
---- Score : 1018660 ctxswc/S
+--- Score : 1018648 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.9 (Benchmark, I/O Queues throughput)
---- Score : 1766676 bytes/S
+--- Score : 1766664 bytes/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.10 (Benchmark, virtual timers set/reset)
---- Score : 1998046 timers/S
+--- Score : 1997998 timers/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.11 (Benchmark, semaphores wait/signal)
---- Score : 2602084 wait+signal/S
+--- Score : 2602024 wait+signal/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.12 (Benchmark, mutexes lock/unlock)
---- Score : 1766664 lock+unlock/S
+--- Score : 1766644 lock+unlock/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.13 (Benchmark, RAM footprint)
diff --git a/os/ports/GCC/ARMCMx/chcore_v7m.c b/os/ports/GCC/ARMCMx/chcore_v7m.c index 12932a5ce..71d6faf9b 100644 --- a/os/ports/GCC/ARMCMx/chcore_v7m.c +++ b/os/ports/GCC/ARMCMx/chcore_v7m.c @@ -28,40 +28,6 @@ #include "ch.h"
-/**
- * @brief Internal context stacking.
- */
-#if CORTEX_USE_FPU || defined(__DOXYGEN__)
-#define PUSH_CONTEXT() { \
- asm volatile ("push {r4, r5, r6, r7, r8, r9, r10, r11, lr}" \
- : : : "memory"); \
- asm volatile ("vpush {s16-s31}" \
- : : : "memory"); \
-}
-#else /* !CORTEX_USE_FPU */
-#define PUSH_CONTEXT() { \
- asm volatile ("push {r4, r5, r6, r7, r8, r9, r10, r11, lr}" \
- : : : "memory"); \
-}
-#endif /* !CORTEX_USE_FPU */
-
-/**
- * @brief Internal context unstacking.
- */
-#if CORTEX_USE_FPU || defined(__DOXYGEN__)
-#define POP_CONTEXT() { \
- asm volatile ("vpop {s16-s31}" \
- : : : "memory"); \
- asm volatile ("pop {r4, r5, r6, r7, r8, r9, r10, r11, pc}" \
- : : : "memory"); \
-}
-#else /* !CORTEX_USE_FPU */
-#define POP_CONTEXT() { \
- asm volatile ("pop {r4, r5, r6, r7, r8, r9, r10, r11, pc}" \
- : : : "memory"); \
-}
-#endif /* !CORTEX_USE_FPU */
-
#if !CH_OPTIMIZE_SPEED
void _port_lock(void) {
register uint32_t tmp asm ("r3") = CORTEX_BASEPRI_KERNEL;
@@ -206,8 +172,23 @@ void _port_irq_epilogue(void) { populate it fully.*/
ctxp--;
asm volatile ("msr PSP, %0" : : "r" (ctxp) : "memory");
- ctxp->pc = _port_switch_from_isr;
ctxp->xpsr = (regarm_t)0x01000000;
+
+ /* The exit sequence is different depending on if a preemption is
+ required or not.*/
+ if (chSchIsPreemptionRequired()) {
+ /* Preemption is required we need to trigger a lazy FPU state save
+ and enforce a context switch.*/
+ ctxp->pc = _port_switch_from_isr;
+ asm volatile ("vmrs APSR_nzcv, FPSCR" : : : "memory");
+ }
+ else {
+ /* Preemption not required, we just need to exit the exception
+ atomically.*/
+ void _port_exit_from_isr(void);
+ ctxp->pc = _port_exit_from_isr;
+ }
+
/* Note, returning without unlocking is intentional, this is done in
order to keep the rest of the context switching atomic.*/
return;
@@ -225,9 +206,9 @@ __attribute__((naked)) void _port_switch_from_isr(void) {
dbg_check_lock();
- if (chSchIsPreemptionRequired())
- chSchDoReschedule();
+ chSchDoReschedule();
dbg_check_unlock();
+ asm volatile ("_port_exit_from_isr:" : : : "memory");
#if !CORTEX_SIMPLIFIED_PRIORITY || defined(__DOXYGEN__)
asm volatile ("svc #0");
#else /* CORTEX_SIMPLIFIED_PRIORITY */
@@ -253,12 +234,20 @@ __attribute__((naked)) #endif
void _port_switch(Thread *ntp, Thread *otp) {
- PUSH_CONTEXT();
+ asm volatile ("push {r4, r5, r6, r7, r8, r9, r10, r11, lr}"
+ : : : "memory");
+#if CORTEX_USE_FPU
+ asm volatile ("vpush {s16-s31}" : : : "memory");
+#endif
asm volatile ("str sp, [%1, #12] \n\t"
"ldr sp, [%0, #12]" : : "r" (ntp), "r" (otp));
- POP_CONTEXT();
+#if CORTEX_USE_FPU
+ asm volatile ("vpop {s16-s31}" : : : "memory");
+#endif
+ asm volatile ("pop {r4, r5, r6, r7, r8, r9, r10, r11, pc}"
+ : : : "memory");
}
/**
|