From 64f8ae44ccb651e550fe5d7369feda6b3f21fcb6 Mon Sep 17 00:00:00 2001 From: Joel Sherrill Date: Tue, 18 Mar 2003 19:20:55 +0000 Subject: 2003-03-18 Till Straumann PR 356/bsps This patch makes RTEMS/powerpc/shared EABI compliant. * irq/irq_init.c, start/Makefile.am, start/start.S, startup/bspstart.c, startup/pgtbl_setup.c, vectors/vectors.h, vectors/vectors_init.c: zero_bss() should clear not only bss but sbss and sbss2 also (this is probably a bugfix, as sbss/sbss2 are probably used even if -msdata=eabi is not specified). * start/rtems_crti.S: New file which must be linked immediately after ecrti.o. rtems_crti.o contains a code snippet who lets __init() return immediately. Also, a new entry point '_init' to the C++ Ctors is generated for use by the RTEMS Thread_Handler. --- c/src/lib/libbsp/powerpc/shared/ChangeLog | 15 ++++++++++ c/src/lib/libbsp/powerpc/shared/irq/irq_init.c | 8 ++--- c/src/lib/libbsp/powerpc/shared/start/Makefile.am | 4 +-- c/src/lib/libbsp/powerpc/shared/start/rtems_crti.S | 35 ++++++++++++++++++++++ c/src/lib/libbsp/powerpc/shared/start/start.S | 4 ++- c/src/lib/libbsp/powerpc/shared/startup/bspstart.c | 24 +++++++++------ .../libbsp/powerpc/shared/startup/pgtbl_setup.c | 8 ++--- c/src/lib/libbsp/powerpc/shared/vectors/vectors.h | 6 +++- .../libbsp/powerpc/shared/vectors/vectors_init.c | 2 +- 9 files changed, 84 insertions(+), 22 deletions(-) create mode 100644 c/src/lib/libbsp/powerpc/shared/start/rtems_crti.S (limited to 'c') diff --git a/c/src/lib/libbsp/powerpc/shared/ChangeLog b/c/src/lib/libbsp/powerpc/shared/ChangeLog index e91d328de9..7eb50ee3c4 100644 --- a/c/src/lib/libbsp/powerpc/shared/ChangeLog +++ b/c/src/lib/libbsp/powerpc/shared/ChangeLog @@ -1,3 +1,18 @@ +2003-03-18 Till Straumann + + PR 356/bsps + This patch makes RTEMS/powerpc/shared EABI compliant. + * irq/irq_init.c, start/Makefile.am, start/start.S, startup/bspstart.c, + startup/pgtbl_setup.c, vectors/vectors.h, vectors/vectors_init.c: + zero_bss() should clear not only bss but sbss and sbss2 + also (this is probably a bugfix, as sbss/sbss2 are + probably used even if -msdata=eabi is not specified). + * start/rtems_crti.S: New file which must + be linked immediately after ecrti.o. rtems_crti.o contains + a code snippet who lets __init() return immediately. Also, + a new entry point '_init' to the C++ Ctors is generated + for use by the RTEMS Thread_Handler. + 2003-02-20 Till Straumann PR 349/bsps diff --git a/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c b/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c index 4ae88cc8b7..5dfb5a5fd6 100644 --- a/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c +++ b/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c @@ -43,9 +43,9 @@ typedef struct { pci_isa_bridge_device* via_82c586 = 0; static pci_isa_bridge_device bridge; -extern unsigned int external_exception_vector_prolog_code_size; +extern unsigned int external_exception_vector_prolog_code_size[]; extern void external_exception_vector_prolog_code(); -extern unsigned int decrementer_exception_vector_prolog_code_size; +extern unsigned int decrementer_exception_vector_prolog_code_size[]; extern void decrementer_exception_vector_prolog_code(); /* @@ -296,7 +296,7 @@ void BSP_rtems_irq_mng_init(unsigned cpuId) vectorDesc.exceptIndex = ASM_DEC_VECTOR; vectorDesc.hdl.vector = ASM_DEC_VECTOR; vectorDesc.hdl.raw_hdl = decrementer_exception_vector_prolog_code; - vectorDesc.hdl.raw_hdl_size = (unsigned) &decrementer_exception_vector_prolog_code_size; + vectorDesc.hdl.raw_hdl_size = (unsigned) decrementer_exception_vector_prolog_code_size; vectorDesc.on = nop_func; vectorDesc.off = nop_func; vectorDesc.isOn = connected; @@ -306,7 +306,7 @@ void BSP_rtems_irq_mng_init(unsigned cpuId) vectorDesc.exceptIndex = ASM_EXT_VECTOR; vectorDesc.hdl.vector = ASM_EXT_VECTOR; vectorDesc.hdl.raw_hdl = external_exception_vector_prolog_code; - vectorDesc.hdl.raw_hdl_size = (unsigned) &external_exception_vector_prolog_code_size; + vectorDesc.hdl.raw_hdl_size = (unsigned) external_exception_vector_prolog_code_size; if (!mpc60x_set_exception (&vectorDesc)) { BSP_panic("Unable to initialize RTEMS external raw exception\n"); } diff --git a/c/src/lib/libbsp/powerpc/shared/start/Makefile.am b/c/src/lib/libbsp/powerpc/shared/start/Makefile.am index 52836016ed..0ba9486deb 100644 --- a/c/src/lib/libbsp/powerpc/shared/start/Makefile.am +++ b/c/src/lib/libbsp/powerpc/shared/start/Makefile.am @@ -3,8 +3,8 @@ ## -S_FILES = start.S +S_FILES = start.S rtems_crti.S -EXTRA_DIST = start.S +EXTRA_DIST = start.S rtems_crti.S include $(top_srcdir)/../../../../../automake/local.am diff --git a/c/src/lib/libbsp/powerpc/shared/start/rtems_crti.S b/c/src/lib/libbsp/powerpc/shared/start/rtems_crti.S new file mode 100644 index 0000000000..0b606663c3 --- /dev/null +++ b/c/src/lib/libbsp/powerpc/shared/start/rtems_crti.S @@ -0,0 +1,35 @@ +/* rtems_crti.S */ +#include +#include +#include + + /* terminate the __init() function and create + * a new head '_init' for use by RTEMS to + * invoke C++ global constructors + * NOTE: it is essential that this snippet + * is hooked between ecrti and crtbegin + * + * ecrti has the following .init section: + * __init: + * stwu r1,-16(r1) + * mflr r0 + * stw r0,20(r1) + * + * The reason for this is that we want to call + * __eabi() at an early stage but prevent __eabi() + * from branching to __init (C++ exception init + * and global CTORs). Hence we make __init a no-op + * and create a new entry point: + */ + .section ".init","ax" + .align 2 + lwz r0,r20(r1) + mtlr r0 + addi r1,r1,16 + blr + .globl _init + .type _init,@function +_init: + stwu r1,-16(r1) + mflr r0 + stw r0,20(r1) diff --git a/c/src/lib/libbsp/powerpc/shared/start/start.S b/c/src/lib/libbsp/powerpc/shared/start/start.S index 4746ab3a46..1a468ba3f5 100644 --- a/c/src/lib/libbsp/powerpc/shared/start/start.S +++ b/c/src/lib/libbsp/powerpc/shared/start/start.S @@ -27,7 +27,8 @@ mtmsr r10 ; \ li r10,0x63 ; \ sc - + + .text .globl __rtems_entry_point .type __rtems_entry_point,@function @@ -86,6 +87,7 @@ __rtems_entry_point: enter_C_code: bl MMUon + bl __eabi /* setup EABI and SYSV environment */ bl zero_bss /* * restore prep boot params diff --git a/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c b/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c index 8df2994db7..37da84f3a8 100644 --- a/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c +++ b/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c @@ -36,9 +36,7 @@ #include extern void _return_to_ppcbug(); -extern unsigned long __rtems_end; -extern unsigned long _end; -extern unsigned long __bss_start; +extern unsigned long __rtems_end[]; extern void L1_caches_enables(); extern unsigned get_L2CR(); extern void set_L2CR(unsigned); @@ -135,7 +133,7 @@ void bsp_pretasking_hook(void) rtems_unsigned32 heap_start; rtems_unsigned32 heap_size; - heap_start = ((rtems_unsigned32) &__rtems_end) +INIT_STACK_SIZE + INTR_STACK_SIZE; + heap_start = ((rtems_unsigned32) __rtems_end) +INIT_STACK_SIZE + INTR_STACK_SIZE; if (heap_start & (CPU_ALIGNMENT-1)) heap_start = (heap_start + CPU_ALIGNMENT) & ~(CPU_ALIGNMENT-1); @@ -153,7 +151,12 @@ void bsp_pretasking_hook(void) void zero_bss() { - memset(&__bss_start, 0, ((unsigned) (&__rtems_end)) - ((unsigned) &__bss_start)); + /* prevent these from being accessed in the short data areas */ + extern unsigned long __bss_start[], __SBSS_START__[], __SBSS_END__[]; + extern unsigned long __SBSS2_START__[], __SBSS2_END__[]; + memset(__SBSS_START__, 0, ((unsigned) __SBSS_END__) - ((unsigned)__SBSS_START__)); + memset(__SBSS2_START__, 0, ((unsigned) __SBSS2_END__) - ((unsigned)__SBSS2_START__)); + memset(__bss_start, 0, ((unsigned) __rtems_end) - ((unsigned)__bss_start)); } void save_boot_params(RESIDUAL* r3, void *r4, void* r5, char *additional_boot_options) @@ -209,7 +212,7 @@ void bsp_start( void ) * so there is no need to set it in r1 again... It is just for info * so that It can be printed without accessing R1. */ - stack = ((unsigned char*) &__rtems_end) + INIT_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE; + stack = ((unsigned char*) __rtems_end) + INIT_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE; /* tag the bottom (T. Straumann 6/36/2001 ) */ *((unsigned32 *)stack) = 0; @@ -222,9 +225,12 @@ void bsp_start( void ) * This could be done latter (e.g in IRQ_INIT) but it helps to understand * some settings below... */ - intrStack = ((unsigned char*) &__rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE; + intrStack = ((unsigned char*) __rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE; - /* tag the bottom (T. Straumann 6/36/2001 ) */ + /* make sure it's properly aligned */ + (unsigned32)intrStack &= ~(CPU_STACK_ALIGNMENT-1); + + /* tag the bottom (T. Straumann 6/36/2001 ) */ *((unsigned32 *)intrStack) = 0; _write_SPR1((unsigned int)intrStack); @@ -357,7 +363,7 @@ void bsp_start( void ) work_space_start = (unsigned char *)BSP_mem_size - BSP_Configuration.work_space_size; - if ( work_space_start <= ((unsigned char *)&__rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE) { + if ( work_space_start <= ((unsigned char *)__rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE) { printk( "bspstart: Not enough RAM!!!\n" ); bsp_cleanup(); } diff --git a/c/src/lib/libbsp/powerpc/shared/startup/pgtbl_setup.c b/c/src/lib/libbsp/powerpc/shared/startup/pgtbl_setup.c index b36ac47d78..5cd462a65d 100644 --- a/c/src/lib/libbsp/powerpc/shared/startup/pgtbl_setup.c +++ b/c/src/lib/libbsp/powerpc/shared/startup/pgtbl_setup.c @@ -50,14 +50,14 @@ unsigned ldPtSize,tmp; /* get those from the linker script. * NOTE THAT THE CORRECTNESS OF THE LINKER SCRIPT IS CRUCIAL */ - extern unsigned long __DATA_START__, _etext; + extern unsigned long __DATA_START__[], _etext[]; /* map text and RO data read-only */ tmp = triv121PgTblMap( pt, TRIV121_121_VSID, 0, - (PAGE_ALIGN((unsigned long)&_etext) - 0) >> PG_SHIFT, + (PAGE_ALIGN((unsigned long)_etext) - 0) >> PG_SHIFT, 0, /* WIMG */ TRIV121_PP_RO_PAGE); if (TRIV121_MAP_SUCCESS != tmp) { @@ -69,8 +69,8 @@ unsigned ldPtSize,tmp; tmp = triv121PgTblMap( pt, TRIV121_121_VSID, - (unsigned long)&__DATA_START__, - (*pmemsize - (1<> PG_SHIFT, + (unsigned long)__DATA_START__, + (*pmemsize - (1<> PG_SHIFT, 0, /* WIMG */ TRIV121_PP_RW_PAGE); if (TRIV121_MAP_SUCCESS != tmp) { diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h index 15eb7b6bfa..4d0d34d8e5 100644 --- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h +++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h @@ -75,7 +75,11 @@ */ extern void default_exception_vector_code_prolog(); -extern int default_exception_vector_code_prolog_size; +/* 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[]; /* 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 6a49a95a30..90738802a7 100644 --- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c +++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c @@ -160,7 +160,7 @@ void initialize_exceptions() * Note that next line the '&' before default_exception_vector_code_prolog_size * 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; + exception_config.defaultRawEntry.hdl.raw_hdl_size = (unsigned) default_exception_vector_code_prolog_size; for (i=0; i <= exception_config.exceptSize; i++) { if (!mpc60x_vector_is_valid (i)) { continue; -- cgit v1.2.3