![]() |
|
|||
File indexing completed on 2025-05-11 08:23:58
0001 /* 0002 * (c) 1999, Eric Valette valette@crf.canon.fr 0003 * 0004 * Modified and partially rewritten by Till Straumann, 2007 0005 * 0006 * Modified by Sebastian Huber <sebastian.huber@embedded-brains.de>, 2008. 0007 * 0008 * Low-level assembly code for PPC exceptions. 0009 * 0010 * This file was written with the goal to eliminate 0011 * ALL #ifdef <cpu_flavor> conditionals -- please do not 0012 * reintroduce such statements. 0013 */ 0014 0015 /* Load macro definitions */ 0016 #include <rtems/asm.h> 0017 #include <rtems/score/percpu.h> 0018 0019 /* 0020 * This code uses the small-data area which is not available in the 64-bit 0021 * PowerPC ELFv2 ABI. 0022 */ 0023 #ifndef __powerpc64__ 0024 0025 #include "ppc_exc_asm_macros.h" 0026 0027 /******************************************************/ 0028 /* PROLOGUES */ 0029 /******************************************************/ 0030 0031 /* 0032 * Expand prologue snippets for classic, ppc405-critical, bookE-critical 0033 * and E500 machine-check, synchronous and asynchronous exceptions 0034 */ 0035 PPC_EXC_MIN_PROLOG_SYNC _NAME=tmpl_std _VEC=0 _PRI=std _FLVR=std 0036 PPC_EXC_MIN_PROLOG_SYNC _NAME=tmpl_p405_crit _VEC=0 _PRI=crit _FLVR=p405_crit 0037 PPC_EXC_MIN_PROLOG_SYNC _NAME=tmpl_bookE_crit _VEC=0 _PRI=crit _FLVR=bookE_crit 0038 PPC_EXC_MIN_PROLOG_SYNC _NAME=tmpl_e500_mchk _VEC=0 _PRI=mchk _FLVR=e500_mchk 0039 0040 PPC_EXC_MIN_PROLOG_ASYNC _NAME=tmpl_std _VEC=0 _PRI=std _FLVR=std 0041 PPC_EXC_MIN_PROLOG_ASYNC _NAME=tmpl_p405_crit _VEC=0 _PRI=crit _FLVR=p405_crit 0042 PPC_EXC_MIN_PROLOG_ASYNC _NAME=tmpl_bookE_crit _VEC=0 _PRI=crit _FLVR=bookE_crit 0043 PPC_EXC_MIN_PROLOG_ASYNC _NAME=tmpl_e500_mchk _VEC=0 _PRI=mchk _FLVR=e500_mchk 0044 0045 .global ppc_exc_min_prolog_size 0046 ppc_exc_min_prolog_size = 4 * 4 0047 0048 /* Special prologue for 603e-style CPUs. 0049 * 0050 * 603e shadows GPR0..GPR3 for certain exceptions. We must switch 0051 * that off before we can use the stack pointer. Note that this is 0052 * ONLY safe if the shadowing is actually active -- otherwise, r1 0053 * is destroyed. We deliberately use r1 so problems become obvious 0054 * if this is misused! 0055 */ 0056 .global ppc_exc_tgpr_clr_prolog 0057 ppc_exc_tgpr_clr_prolog: 0058 mfmsr r1 0059 rlwinm r1,r1,0,15,13 0060 mtmsr r1 0061 isync 0062 /* FALL THRU TO 'auto' PROLOG */ 0063 0064 /* Determine vector dynamically/automatically 0065 * 0066 * BUT: - only standard exceptions (no critical ones) 0067 * - vector offset must be on 256 Byte boundary. 0068 */ 0069 .global ppc_exc_min_prolog_auto 0070 ppc_exc_min_prolog_auto: 0071 stwu r1, -EXCEPTION_FRAME_END(r1) 0072 stw VECTOR_REGISTER, VECTOR_OFFSET(r1) 0073 mflr VECTOR_REGISTER 0074 0075 /* 0076 * We store the absolute branch target address here. It will be used 0077 * to generate the branch operation in ppc_exc_make_prologue(). 0078 * 0079 * We add one to request the link in the generated branch instruction. 0080 */ 0081 .int ppc_exc_wrap_auto + 1 0082 0083 .global ppc_exc_tgpr_clr_prolog_size 0084 ppc_exc_tgpr_clr_prolog_size = . - ppc_exc_tgpr_clr_prolog 0085 0086 /* 0087 * Automatic vector, asynchronous exception; however, 0088 * automatic vector calculation is less efficient than 0089 * using an explicit vector in a minimal prolog snippet. 0090 * The latter method is preferable since there usually 0091 * are few asynchronous exceptions. 0092 * 0093 * For generic exceptions (which are the bulk) using 0094 * the 'auto' prologue is OK since performance is not 0095 * really an issue. 0096 */ 0097 .global ppc_exc_min_prolog_auto_async 0098 ppc_exc_min_prolog_auto_async: 0099 stw r1, ppc_exc_lock_std@sdarel(r13) 0100 stw VECTOR_REGISTER, ppc_exc_vector_register_std@sdarel(r13) 0101 mflr VECTOR_REGISTER 0102 0103 /* 0104 * We store the absolute branch target address here. It will be used 0105 * to generate the branch operation in ppc_exc_make_prologue(). 0106 * 0107 * We add one to request the link in the generated branch instruction. 0108 */ 0109 .int ppc_exc_wrap_auto_async + 1 0110 0111 /******************************************************/ 0112 /* WRAPPERS */ 0113 /******************************************************/ 0114 0115 /* Tag start and end of the wrappers. 0116 * If exceptions are installed farther removed 0117 * from the text area than 32M then the wrappers 0118 * must be moved to an area that is reachable 0119 * from where the prologues reside. Branches into 0120 * C-code are far. 0121 */ 0122 0123 .global __ppc_exc_wrappers_start 0124 __ppc_exc_wrappers_start = . 0125 0126 /* Expand wrappers for different exception flavors */ 0127 0128 /* Standard/classic powerpc */ 0129 WRAP _FLVR=std _PRI=std _SRR0=srr0 _SRR1=srr1 _RFI=rfi 0130 0131 /* ppc405 has a critical exception using srr2/srr3 */ 0132 WRAP _FLVR=p405_crit _PRI=crit _SRR0=srr2 _SRR1=srr3 _RFI=rfci 0133 0134 /* bookE has critical exception using csrr0 cssr1 */ 0135 WRAP _FLVR=bookE_crit _PRI=crit _SRR0=csrr0 _SRR1=csrr1 _RFI=rfci 0136 0137 /* e500 has machine-check exception using mcsrr0 mcssr1 */ 0138 WRAP _FLVR=e500_mchk _PRI=mchk _SRR0=mcsrr0 _SRR1=mcsrr1 _RFI=rfmci 0139 0140 /* LR holds vector, VECTOR_REGISTER holds orig. LR */ 0141 .global ppc_exc_wrap_auto 0142 ppc_exc_wrap_auto: 0143 stw FRAME_REGISTER, FRAME_OFFSET(r1) 0144 0145 /* Find address where we jumped from */ 0146 mflr FRAME_REGISTER 0147 0148 /* Restore LR */ 0149 mtlr VECTOR_REGISTER 0150 0151 /* Compute vector into R3 */ 0152 rlwinm VECTOR_REGISTER, FRAME_REGISTER, 24, 26, 31 0153 0154 /* 0155 * We're now in almost the same state as if called by 0156 * min_prolog_std but we must skip saving FRAME_REGISTER 0157 * since that's done already 0158 */ 0159 b wrap_no_save_frame_register_std 0160 0161 .global ppc_exc_wrap_auto_async 0162 ppc_exc_wrap_auto_async: 0163 stwu r1, -EXCEPTION_FRAME_END(r1) 0164 stw FRAME_REGISTER, FRAME_OFFSET(r1) 0165 /* find address where we jumped from */ 0166 mflr FRAME_REGISTER 0167 /* restore LR */ 0168 mtlr VECTOR_REGISTER 0169 /* set upper bits to indicate that non-volatile 0170 * registers should not be saved/restored. 0171 */ 0172 li VECTOR_REGISTER, 0xffff8000 0173 /* compute vector into R3 */ 0174 rlwimi VECTOR_REGISTER, FRAME_REGISTER, 24, 26, 31 0175 /* we're now in almost the same state as if called by 0176 * min_prolog_std but we must skip saving FRAME_REGISTER 0177 * since that's done already 0178 */ 0179 b wrap_no_save_frame_register_std 0180 0181 .global __ppc_exc_wrappers_end 0182 __ppc_exc_wrappers_end = . 0183 0184 #endif /* !__powerpc64__ */
[ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |
![]() ![]() |