diff options
Diffstat (limited to 'arch/ia64/kernel/pal.S')
-rw-r--r-- | arch/ia64/kernel/pal.S | 58 |
1 files changed, 27 insertions, 31 deletions
diff --git a/arch/ia64/kernel/pal.S b/arch/ia64/kernel/pal.S index ebaf1e685f5e..0b533441c3c9 100644 --- a/arch/ia64/kernel/pal.S +++ b/arch/ia64/kernel/pal.S | |||
@@ -21,11 +21,12 @@ pal_entry_point: | |||
21 | .text | 21 | .text |
22 | 22 | ||
23 | /* | 23 | /* |
24 | * Set the PAL entry point address. This could be written in C code, but we do it here | 24 | * Set the PAL entry point address. This could be written in C code, but we |
25 | * to keep it all in one module (besides, it's so trivial that it's | 25 | * do it here to keep it all in one module (besides, it's so trivial that it's |
26 | * not a big deal). | 26 | * not a big deal). |
27 | * | 27 | * |
28 | * in0 Address of the PAL entry point (text address, NOT a function descriptor). | 28 | * in0 Address of the PAL entry point (text address, NOT a function |
29 | * descriptor). | ||
29 | */ | 30 | */ |
30 | GLOBAL_ENTRY(ia64_pal_handler_init) | 31 | GLOBAL_ENTRY(ia64_pal_handler_init) |
31 | alloc r3=ar.pfs,1,0,0,0 | 32 | alloc r3=ar.pfs,1,0,0,0 |
@@ -36,9 +37,9 @@ GLOBAL_ENTRY(ia64_pal_handler_init) | |||
36 | END(ia64_pal_handler_init) | 37 | END(ia64_pal_handler_init) |
37 | 38 | ||
38 | /* | 39 | /* |
39 | * Default PAL call handler. This needs to be coded in assembly because it uses | 40 | * Default PAL call handler. This needs to be coded in assembly because it |
40 | * the static calling convention, i.e., the RSE may not be used and calls are | 41 | * uses the static calling convention, i.e., the RSE may not be used and |
41 | * done via "br.cond" (not "br.call"). | 42 | * calls are done via "br.cond" (not "br.call"). |
42 | */ | 43 | */ |
43 | GLOBAL_ENTRY(ia64_pal_default_handler) | 44 | GLOBAL_ENTRY(ia64_pal_default_handler) |
44 | mov r8=-1 | 45 | mov r8=-1 |
@@ -50,12 +51,10 @@ END(ia64_pal_default_handler) | |||
50 | * | 51 | * |
51 | * in0 Index of PAL service | 52 | * in0 Index of PAL service |
52 | * in1 - in3 Remaining PAL arguments | 53 | * in1 - in3 Remaining PAL arguments |
53 | * in4 1 ==> clear psr.ic, 0 ==> don't clear psr.ic | ||
54 | * | ||
55 | */ | 54 | */ |
56 | GLOBAL_ENTRY(ia64_pal_call_static) | 55 | GLOBAL_ENTRY(ia64_pal_call_static) |
57 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(5) | 56 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(4) |
58 | alloc loc1 = ar.pfs,5,5,0,0 | 57 | alloc loc1 = ar.pfs,4,5,0,0 |
59 | movl loc2 = pal_entry_point | 58 | movl loc2 = pal_entry_point |
60 | 1: { | 59 | 1: { |
61 | mov r28 = in0 | 60 | mov r28 = in0 |
@@ -64,7 +63,6 @@ GLOBAL_ENTRY(ia64_pal_call_static) | |||
64 | } | 63 | } |
65 | ;; | 64 | ;; |
66 | ld8 loc2 = [loc2] // loc2 <- entry point | 65 | ld8 loc2 = [loc2] // loc2 <- entry point |
67 | tbit.nz p6,p7 = in4, 0 | ||
68 | adds r8 = 1f-1b,r8 | 66 | adds r8 = 1f-1b,r8 |
69 | mov loc4=ar.rsc // save RSE configuration | 67 | mov loc4=ar.rsc // save RSE configuration |
70 | ;; | 68 | ;; |
@@ -74,13 +72,11 @@ GLOBAL_ENTRY(ia64_pal_call_static) | |||
74 | .body | 72 | .body |
75 | mov r30 = in2 | 73 | mov r30 = in2 |
76 | 74 | ||
77 | (p6) rsm psr.i | psr.ic | ||
78 | mov r31 = in3 | 75 | mov r31 = in3 |
79 | mov b7 = loc2 | 76 | mov b7 = loc2 |
80 | 77 | ||
81 | (p7) rsm psr.i | 78 | rsm psr.i |
82 | ;; | 79 | ;; |
83 | (p6) srlz.i | ||
84 | mov rp = r8 | 80 | mov rp = r8 |
85 | br.cond.sptk.many b7 | 81 | br.cond.sptk.many b7 |
86 | 1: mov psr.l = loc3 | 82 | 1: mov psr.l = loc3 |
@@ -96,8 +92,8 @@ END(ia64_pal_call_static) | |||
96 | * Make a PAL call using the stacked registers calling convention. | 92 | * Make a PAL call using the stacked registers calling convention. |
97 | * | 93 | * |
98 | * Inputs: | 94 | * Inputs: |
99 | * in0 Index of PAL service | 95 | * in0 Index of PAL service |
100 | * in2 - in3 Remaning PAL arguments | 96 | * in2 - in3 Remaining PAL arguments |
101 | */ | 97 | */ |
102 | GLOBAL_ENTRY(ia64_pal_call_stacked) | 98 | GLOBAL_ENTRY(ia64_pal_call_stacked) |
103 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(4) | 99 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(4) |
@@ -131,18 +127,18 @@ END(ia64_pal_call_stacked) | |||
131 | * Make a physical mode PAL call using the static registers calling convention. | 127 | * Make a physical mode PAL call using the static registers calling convention. |
132 | * | 128 | * |
133 | * Inputs: | 129 | * Inputs: |
134 | * in0 Index of PAL service | 130 | * in0 Index of PAL service |
135 | * in2 - in3 Remaning PAL arguments | 131 | * in2 - in3 Remaining PAL arguments |
136 | * | 132 | * |
137 | * PSR_LP, PSR_TB, PSR_ID, PSR_DA are never set by the kernel. | 133 | * PSR_LP, PSR_TB, PSR_ID, PSR_DA are never set by the kernel. |
138 | * So we don't need to clear them. | 134 | * So we don't need to clear them. |
139 | */ | 135 | */ |
140 | #define PAL_PSR_BITS_TO_CLEAR \ | 136 | #define PAL_PSR_BITS_TO_CLEAR \ |
141 | (IA64_PSR_I | IA64_PSR_IT | IA64_PSR_DT | IA64_PSR_DB | IA64_PSR_RT | \ | 137 | (IA64_PSR_I | IA64_PSR_IT | IA64_PSR_DT | IA64_PSR_DB | IA64_PSR_RT |\ |
142 | IA64_PSR_DD | IA64_PSR_SS | IA64_PSR_RI | IA64_PSR_ED | \ | 138 | IA64_PSR_DD | IA64_PSR_SS | IA64_PSR_RI | IA64_PSR_ED | \ |
143 | IA64_PSR_DFL | IA64_PSR_DFH) | 139 | IA64_PSR_DFL | IA64_PSR_DFH) |
144 | 140 | ||
145 | #define PAL_PSR_BITS_TO_SET \ | 141 | #define PAL_PSR_BITS_TO_SET \ |
146 | (IA64_PSR_BN) | 142 | (IA64_PSR_BN) |
147 | 143 | ||
148 | 144 | ||
@@ -178,7 +174,7 @@ GLOBAL_ENTRY(ia64_pal_call_phys_static) | |||
178 | ;; | 174 | ;; |
179 | andcm r16=loc3,r16 // removes bits to clear from psr | 175 | andcm r16=loc3,r16 // removes bits to clear from psr |
180 | br.call.sptk.many rp=ia64_switch_mode_phys | 176 | br.call.sptk.many rp=ia64_switch_mode_phys |
181 | .ret1: mov rp = r8 // install return address (physical) | 177 | mov rp = r8 // install return address (physical) |
182 | mov loc5 = r19 | 178 | mov loc5 = r19 |
183 | mov loc6 = r20 | 179 | mov loc6 = r20 |
184 | br.cond.sptk.many b7 | 180 | br.cond.sptk.many b7 |
@@ -188,7 +184,6 @@ GLOBAL_ENTRY(ia64_pal_call_phys_static) | |||
188 | mov r19=loc5 | 184 | mov r19=loc5 |
189 | mov r20=loc6 | 185 | mov r20=loc6 |
190 | br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode | 186 | br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode |
191 | .ret2: | ||
192 | mov psr.l = loc3 // restore init PSR | 187 | mov psr.l = loc3 // restore init PSR |
193 | 188 | ||
194 | mov ar.pfs = loc1 | 189 | mov ar.pfs = loc1 |
@@ -203,8 +198,8 @@ END(ia64_pal_call_phys_static) | |||
203 | * Make a PAL call using the stacked registers in physical mode. | 198 | * Make a PAL call using the stacked registers in physical mode. |
204 | * | 199 | * |
205 | * Inputs: | 200 | * Inputs: |
206 | * in0 Index of PAL service | 201 | * in0 Index of PAL service |
207 | * in2 - in3 Remaning PAL arguments | 202 | * in2 - in3 Remaining PAL arguments |
208 | */ | 203 | */ |
209 | GLOBAL_ENTRY(ia64_pal_call_phys_stacked) | 204 | GLOBAL_ENTRY(ia64_pal_call_phys_stacked) |
210 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(5) | 205 | .prologue ASM_UNW_PRLG_RP|ASM_UNW_PRLG_PFS, ASM_UNW_PRLG_GRSAVE(5) |
@@ -212,7 +207,7 @@ GLOBAL_ENTRY(ia64_pal_call_phys_stacked) | |||
212 | movl loc2 = pal_entry_point | 207 | movl loc2 = pal_entry_point |
213 | 1: { | 208 | 1: { |
214 | mov r28 = in0 // copy procedure index | 209 | mov r28 = in0 // copy procedure index |
215 | mov loc0 = rp // save rp | 210 | mov loc0 = rp // save rp |
216 | } | 211 | } |
217 | .body | 212 | .body |
218 | ;; | 213 | ;; |
@@ -245,7 +240,7 @@ GLOBAL_ENTRY(ia64_pal_call_phys_stacked) | |||
245 | mov r16=loc3 // r16= original psr | 240 | mov r16=loc3 // r16= original psr |
246 | mov r19=loc5 | 241 | mov r19=loc5 |
247 | mov r20=loc6 | 242 | mov r20=loc6 |
248 | br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode | 243 | br.call.sptk.many rp=ia64_switch_mode_virt // return to virtual mode |
249 | 244 | ||
250 | mov psr.l = loc3 // restore init PSR | 245 | mov psr.l = loc3 // restore init PSR |
251 | mov ar.pfs = loc1 | 246 | mov ar.pfs = loc1 |
@@ -257,10 +252,11 @@ GLOBAL_ENTRY(ia64_pal_call_phys_stacked) | |||
257 | END(ia64_pal_call_phys_stacked) | 252 | END(ia64_pal_call_phys_stacked) |
258 | 253 | ||
259 | /* | 254 | /* |
260 | * Save scratch fp scratch regs which aren't saved in pt_regs already (fp10-fp15). | 255 | * Save scratch fp scratch regs which aren't saved in pt_regs already |
256 | * (fp10-fp15). | ||
261 | * | 257 | * |
262 | * NOTE: We need to do this since firmware (SAL and PAL) may use any of the scratch | 258 | * NOTE: We need to do this since firmware (SAL and PAL) may use any of the |
263 | * regs fp-low partition. | 259 | * scratch regs fp-low partition. |
264 | * | 260 | * |
265 | * Inputs: | 261 | * Inputs: |
266 | * in0 Address of stack storage for fp regs | 262 | * in0 Address of stack storage for fp regs |