summaryrefslogtreecommitdiffstats
path: root/c
diff options
context:
space:
mode:
authorTill Straumann <strauman@slac.stanford.edu>2005-12-02 02:47:23 +0000
committerTill Straumann <strauman@slac.stanford.edu>2005-12-02 02:47:23 +0000
commitd8ada5b617c70f3b94a3c6117958b62e8e0cb9e4 (patch)
treec3f1eda21f8ba34740ee482fb6a03beba3c725fa /c
parent2005-11-29 Till Straumann <strauman@slac.stanford.edu> (diff)
downloadrtems-d8ada5b617c70f3b94a3c6117958b62e8e0cb9e4.tar.bz2
2005-12-01 Till Straumann <strauman@slac.stanford.edu>
* shared/vectors/vectors.h, shared/vectors/vectors.S, shared/vectors/vectors_init.c: Reduced size of default prologue (some exceptions, e.g., altivec unavail.) are only 0x20 bytes apart. Also introduced a modified prologue that switches r0..r3 shadowing off (r0..r3 undefined on certain 603e variants when incurring a TLB miss).
Diffstat (limited to 'c')
-rw-r--r--c/src/lib/libbsp/powerpc/ChangeLog8
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors.S65
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors.h2
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c23
4 files changed, 72 insertions, 26 deletions
diff --git a/c/src/lib/libbsp/powerpc/ChangeLog b/c/src/lib/libbsp/powerpc/ChangeLog
index d1351984fa..f90411188e 100644
--- a/c/src/lib/libbsp/powerpc/ChangeLog
+++ b/c/src/lib/libbsp/powerpc/ChangeLog
@@ -1,3 +1,11 @@
+2005-12-01 Till Straumann <strauman@slac.stanford.edu>
+ * shared/vectors/vectors.h, shared/vectors/vectors.S,
+ shared/vectors/vectors_init.c: Reduced size of default
+ prologue (some exceptions, e.g., altivec unavail.) are only
+ 0x20 bytes apart. Also introduced a modified prologue
+ that switches r0..r3 shadowing off (r0..r3 undefined
+ on certain 603e variants when incurring a TLB miss).
+
2005-11-29 Till Straumann <strauman@slac.stanford.edu>
* shared/irq/irq_asm.S, shared/vectors/vectors.S: Clear
CR[6] before invoking high-level handler to make sure no
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
index 8dba3a3926..96a4be5386 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
@@ -11,6 +11,7 @@
#include <rtems/asm.h>
#include <rtems/score/cpu.h>
#include <bsp/vectors.h>
+#include <libcpu/raw_exception.h>
#define SYNC \
sync; \
@@ -28,50 +29,68 @@ SYM (__rtems_start):
* end of special Entry point section
*/
.text
- .p2align 5
-
+ /* 603e shadows GPR0..GPR3 for certain exceptions. We must switch
+ * that off before we can use the stack pointer. Note that this is
+ * ONLY safe if the shadowing is actually active -- otherwise, r1
+ * is destroyed. We deliberately use r1 so problems become obvious
+ * if this is abused!
+ */
+PUBLIC_VAR(tgpr_clr_exception_vector_code_prolog)
+SYM (tgpr_clr_exception_vector_code_prolog):
+ mfmsr r1
+ rlwinm r1,r1,0,15,13
+ mtmsr r1
+ isync
+ /* fall thru */
PUBLIC_VAR(default_exception_vector_code_prolog)
SYM (default_exception_vector_code_prolog):
/*
* let room for exception frame
*/
- stwu r1, - (EXCEPTION_FRAME_END)(r1)
- stw r3, GPR3_OFFSET(r1)
- /* R2 should never change (EABI: pointer to .sdata2) - we
- * save it nevertheless..
- */
- stw r2, GPR2_OFFSET(r1)
- mflr r3
- stw r3, EXC_LR_OFFSET(r1)
- bl 0f
-0: /*
- * r3 = exception vector entry point
- * (256 * vector number) + few instructions
- */
+ stw r3, GPR3_OFFSET-EXCEPTION_FRAME_END(r1)
mflr r3
- /*
- * r3 = r3 >> 8 = vector
+ stw r3, EXC_LR_OFFSET-EXCEPTION_FRAME_END(r1)
+ bla push_normalized_frame
+
+ /* IMPORTANT: prologue size MUST be < 32 bytes; 'altivec unavailable' exception
+ * is already at 0xf20 :-(
*/
- srwi r3,r3,8
- ba push_normalized_frame
PUBLIC_VAR (default_exception_vector_code_prolog_size)
+ PUBLIC_VAR (tgpr_clr_exception_vector_code_prolog_size)
- default_exception_vector_code_prolog_size= . - default_exception_vector_code_prolog
+ default_exception_vector_code_prolog_size = . - default_exception_vector_code_prolog
+ tgpr_clr_exception_vector_code_prolog_size= . - tgpr_clr_exception_vector_code_prolog
.p2align 5
PUBLIC_VAR (push_normalized_frame)
SYM (push_normalized_frame):
+ stwu r1, - (EXCEPTION_FRAME_END)(r1)
+ mfcr r3
+ stw r3, EXC_CR_OFFSET(r1)
+ /*
+ * r3 = exception vector entry point
+ * (256 * vector number) + few instructions
+ */
+ mflr r3
+ /*
+ * r3 = r3 >> 8 = vector
+ */
+ srwi r3,r3,8
stw r3, EXCEPTION_NUMBER_OFFSET(r1)
stw r0, GPR0_OFFSET(r1)
+ /* R2 should never change (EABI: pointer to .sdata2) - we
+ * save it nevertheless..
+ */
+ stw r2, GPR2_OFFSET(r1)
mfsrr0 r3
stw r3, SRR0_FRAME_OFFSET(r1)
mfsrr1 r3
stw r3, SRR1_FRAME_OFFSET(r1)
/*
* Save general purpose registers
- * Already saved in prolog : R1, R2, R3, LR.
- * Saved a few line above : R0
+ * Already saved in prolog : R1, R3, LR.
+ * Saved a few line above : R0, R2
*
* Manual says that "stmw" instruction may be slower than
* series of individual "stw" but who cares about performance
@@ -79,8 +98,6 @@ SYM (push_normalized_frame):
*/
stmw r4, GPR4_OFFSET(r1) /* save R4->R31 */
- mfcr r31
- stw r31, EXC_CR_OFFSET(r1)
mfctr r30
stw r30, EXC_CTR_OFFSET(r1)
mfxer r28
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
index 4e5ce04d41..55823893ce 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
@@ -75,11 +75,13 @@
*/
extern void default_exception_vector_code_prolog();
+extern void tgpr_clr_exception_vector_code_prolog();
/* This symbol is generated by the linker; prevent it from
* being accessed in one of the short data areas by declaring
* it as an array
*/
extern int default_exception_vector_code_prolog_size[];
+extern int tgpr_clr_exception_vector_code_prolog_size[];
/* codemove is like memmove, but it also gets the cache line size
* as 4th parameter to synchronize them. If this last parameter is
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c b/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
index 873e1c08ca..75f57898c3 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
@@ -12,12 +12,15 @@
*
* $Id$
*/
+#include <rtems.h>
+#include <bsp.h>
+
#include <rtems/bspIo.h>
#include <bsp/vectors.h>
#include <libcpu/raw_exception.h>
#include <libcpu/spr.h>
-#include <bsp.h>
+#include <libcpu/cpuIdent.h>
static rtems_raw_except_global_settings exception_config;
static rtems_raw_except_connect_data exception_table[LAST_VALID_EXC + 1];
@@ -143,6 +146,7 @@ int mpc60x_vector_is_valid(rtems_vector vector);
void initialize_exceptions()
{
int i;
+ int has_shadowed_gprs = 0;
/*
* Initialize pointer used by low level execption handling
@@ -162,12 +166,27 @@ void initialize_exceptions()
* is not a bug as it is defined a .set directly in asm...
*/
exception_config.defaultRawEntry.hdl.raw_hdl_size = (unsigned) default_exception_vector_code_prolog_size;
+
+ switch ( get_ppc_cpu_type() ) {
+ case PPC_603e:
+ case PPC_8240:
+ has_shadowed_gprs = 1;
+ default: break;
+ }
for (i=0; i <= exception_config.exceptSize; i++) {
if (!mpc60x_vector_is_valid (i)) {
continue;
}
exception_table[i].exceptIndex = i;
- exception_table[i].hdl = exception_config.defaultRawEntry.hdl;
+ if ( has_shadowed_gprs
+ && ( ASM_IMISS_VECTOR == i
+ || ASM_DLMISS_VECTOR == i
+ || ASM_DSMISS_VECTOR == i ) ) {
+ exception_table[i].hdl.raw_hdl = tgpr_clr_exception_vector_code_prolog;
+ exception_table[i].hdl.raw_hdl_size = (unsigned)tgpr_clr_exception_vector_code_prolog_size;
+ } else {
+ exception_table[i].hdl = exception_config.defaultRawEntry.hdl;
+ }
exception_table[i].hdl.vector = i;
exception_table[i].on = nop_except_enable;
exception_table[i].off = nop_except_enable;