diff options
Diffstat (limited to 'arch/arc/mm/tlbex.S')
-rw-r--r-- | arch/arc/mm/tlbex.S | 38 |
1 files changed, 38 insertions, 0 deletions
diff --git a/arch/arc/mm/tlbex.S b/arch/arc/mm/tlbex.S index 164b02169498..4b1ad2d905ca 100644 --- a/arch/arc/mm/tlbex.S +++ b/arch/arc/mm/tlbex.S | |||
@@ -57,9 +57,15 @@ | |||
57 | .global ex_saved_reg1 | 57 | .global ex_saved_reg1 |
58 | .align 1 << L1_CACHE_SHIFT ; IMP: Must be Cache Line aligned | 58 | .align 1 << L1_CACHE_SHIFT ; IMP: Must be Cache Line aligned |
59 | .type ex_saved_reg1, @object | 59 | .type ex_saved_reg1, @object |
60 | #ifdef CONFIG_SMP | ||
61 | .size ex_saved_reg1, (CONFIG_NR_CPUS << L1_CACHE_SHIFT) | ||
62 | ex_saved_reg1: | ||
63 | .zero (CONFIG_NR_CPUS << L1_CACHE_SHIFT) | ||
64 | #else | ||
60 | .size ex_saved_reg1, 16 | 65 | .size ex_saved_reg1, 16 |
61 | ex_saved_reg1: | 66 | ex_saved_reg1: |
62 | .zero 16 | 67 | .zero 16 |
68 | #endif | ||
63 | 69 | ||
64 | ;============================================================================ | 70 | ;============================================================================ |
65 | ; Troubleshooting Stuff | 71 | ; Troubleshooting Stuff |
@@ -116,7 +122,13 @@ ex_saved_reg1: | |||
116 | 122 | ||
117 | lr r2, [efa] | 123 | lr r2, [efa] |
118 | 124 | ||
125 | #ifndef CONFIG_SMP | ||
119 | lr r1, [ARC_REG_SCRATCH_DATA0] ; current pgd | 126 | lr r1, [ARC_REG_SCRATCH_DATA0] ; current pgd |
127 | #else | ||
128 | GET_CURR_TASK_ON_CPU r1 | ||
129 | ld r1, [r1, TASK_ACT_MM] | ||
130 | ld r1, [r1, MM_PGD] | ||
131 | #endif | ||
120 | 132 | ||
121 | lsr r0, r2, PGDIR_SHIFT ; Bits for indexing into PGD | 133 | lsr r0, r2, PGDIR_SHIFT ; Bits for indexing into PGD |
122 | ld.as r1, [r1, r0] ; PGD entry corresp to faulting addr | 134 | ld.as r1, [r1, r0] ; PGD entry corresp to faulting addr |
@@ -192,12 +204,28 @@ ex_saved_reg1: | |||
192 | ; ".size ex_saved_reg1, 16" | 204 | ; ".size ex_saved_reg1, 16" |
193 | ; [All of this dance is to avoid stack switching for each TLB Miss, since we | 205 | ; [All of this dance is to avoid stack switching for each TLB Miss, since we |
194 | ; only need to save only a handful of regs, as opposed to complete reg file] | 206 | ; only need to save only a handful of regs, as opposed to complete reg file] |
207 | ; | ||
208 | ; For ARC700 SMP, the "global" obviously can't be used for free up the FIRST | ||
209 | ; core reg as it will not be SMP safe. | ||
210 | ; Thus scratch AUX reg is used (and no longer used to cache task PGD). | ||
211 | ; To save the rest of 3 regs - per cpu, the global is made "per-cpu". | ||
212 | ; Epilogue thus has to locate the "per-cpu" storage for regs. | ||
213 | ; To avoid cache line bouncing the per-cpu global is aligned/sized per | ||
214 | ; L1_CACHE_SHIFT, despite fundamentally needing to be 12 bytes only. Hence | ||
215 | ; ".size ex_saved_reg1, (CONFIG_NR_CPUS << L1_CACHE_SHIFT)" | ||
195 | 216 | ||
196 | ; As simple as that.... | 217 | ; As simple as that.... |
197 | 218 | ||
198 | .macro TLBMISS_FREEUP_REGS | 219 | .macro TLBMISS_FREEUP_REGS |
220 | #ifdef CONFIG_SMP | ||
221 | sr r0, [ARC_REG_SCRATCH_DATA0] ; freeup r0 to code with | ||
222 | GET_CPU_ID r0 ; get to per cpu scratch mem, | ||
223 | lsl r0, r0, L1_CACHE_SHIFT ; cache line wide per cpu | ||
224 | add r0, @ex_saved_reg1, r0 | ||
225 | #else | ||
199 | st r0, [@ex_saved_reg1] | 226 | st r0, [@ex_saved_reg1] |
200 | mov_s r0, @ex_saved_reg1 | 227 | mov_s r0, @ex_saved_reg1 |
228 | #endif | ||
201 | st_s r1, [r0, 4] | 229 | st_s r1, [r0, 4] |
202 | st_s r2, [r0, 8] | 230 | st_s r2, [r0, 8] |
203 | st_s r3, [r0, 12] | 231 | st_s r3, [r0, 12] |
@@ -210,11 +238,21 @@ ex_saved_reg1: | |||
210 | 238 | ||
211 | ;----------------------------------------------------------------- | 239 | ;----------------------------------------------------------------- |
212 | .macro TLBMISS_RESTORE_REGS | 240 | .macro TLBMISS_RESTORE_REGS |
241 | #ifdef CONFIG_SMP | ||
242 | GET_CPU_ID r0 ; get to per cpu scratch mem | ||
243 | lsl r0, r0, L1_CACHE_SHIFT ; each is cache line wide | ||
244 | add r0, @ex_saved_reg1, r0 | ||
245 | ld_s r3, [r0,12] | ||
246 | ld_s r2, [r0, 8] | ||
247 | ld_s r1, [r0, 4] | ||
248 | lr r0, [ARC_REG_SCRATCH_DATA0] | ||
249 | #else | ||
213 | mov_s r0, @ex_saved_reg1 | 250 | mov_s r0, @ex_saved_reg1 |
214 | ld_s r3, [r0,12] | 251 | ld_s r3, [r0,12] |
215 | ld_s r2, [r0, 8] | 252 | ld_s r2, [r0, 8] |
216 | ld_s r1, [r0, 4] | 253 | ld_s r1, [r0, 4] |
217 | ld_s r0, [r0] | 254 | ld_s r0, [r0] |
255 | #endif | ||
218 | .endm | 256 | .endm |
219 | 257 | ||
220 | .section .text, "ax",@progbits ;Fast Path Code, candidate for ICCM | 258 | .section .text, "ax",@progbits ;Fast Path Code, candidate for ICCM |