GFS2: Check for glock already held in gfs2_getxattr
[deliverable/linux.git] / arch / arc / include / asm / entry.h
1 /*
2 * Copyright (C) 2004, 2007-2010, 2011-2012 Synopsys, Inc. (www.synopsys.com)
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2 as
6 * published by the Free Software Foundation.
7 *
8 * Vineetg: March 2009 (Supporting 2 levels of Interrupts)
9 * Stack switching code can no longer reliably rely on the fact that
10 * if we are NOT in user mode, stack is switched to kernel mode.
11 * e.g. L2 IRQ interrupted a L1 ISR which had not yet completed
12 * it's prologue including stack switching from user mode
13 *
14 * Vineetg: Aug 28th 2008: Bug #94984
15 * -Zero Overhead Loop Context shd be cleared when entering IRQ/EXcp/Trap
16 * Normally CPU does this automatically, however when doing FAKE rtie,
17 * we also need to explicitly do this. The problem in macros
18 * FAKE_RET_FROM_EXCPN and FAKE_RET_FROM_EXCPN_LOCK_IRQ was that this bit
19 * was being "CLEARED" rather then "SET". Actually "SET" clears ZOL context
20 *
21 * Vineetg: May 5th 2008
22 * -Modified CALLEE_REG save/restore macros to handle the fact that
23 * r25 contains the kernel current task ptr
24 * - Defined Stack Switching Macro to be reused in all intr/excp hdlrs
25 * - Shaved off 11 instructions from RESTORE_ALL_INT1 by using the
26 * address Write back load ld.ab instead of seperate ld/add instn
27 *
28 * Amit Bhor, Sameer Dhavale: Codito Technologies 2004
29 */
30
31 #ifndef __ASM_ARC_ENTRY_H
32 #define __ASM_ARC_ENTRY_H
33
34 #ifdef __ASSEMBLY__
35 #include <asm/unistd.h> /* For NR_syscalls defination */
36 #include <asm/asm-offsets.h>
37 #include <asm/arcregs.h>
38 #include <asm/ptrace.h>
39 #include <asm/processor.h> /* For VMALLOC_START */
40 #include <asm/thread_info.h> /* For THREAD_SIZE */
41
42 /* Note on the LD/ST addr modes with addr reg wback
43 *
44 * LD.a same as LD.aw
45 *
46 * LD.a reg1, [reg2, x] => Pre Incr
47 * Eff Addr for load = [reg2 + x]
48 *
49 * LD.ab reg1, [reg2, x] => Post Incr
50 * Eff Addr for load = [reg2]
51 */
52
53 .macro PUSH reg
54 st.a \reg, [sp, -4]
55 .endm
56
57 .macro PUSHAX aux
58 lr r9, [\aux]
59 PUSH r9
60 .endm
61
62 .macro POP reg
63 ld.ab \reg, [sp, 4]
64 .endm
65
66 .macro POPAX aux
67 POP r9
68 sr r9, [\aux]
69 .endm
70
71 /*--------------------------------------------------------------
72 * Helpers to save/restore Scratch Regs:
73 * used by Interrupt/Exception Prologue/Epilogue
74 *-------------------------------------------------------------*/
75 .macro SAVE_R0_TO_R12
76 PUSH r0
77 PUSH r1
78 PUSH r2
79 PUSH r3
80 PUSH r4
81 PUSH r5
82 PUSH r6
83 PUSH r7
84 PUSH r8
85 PUSH r9
86 PUSH r10
87 PUSH r11
88 PUSH r12
89 .endm
90
91 .macro RESTORE_R12_TO_R0
92 POP r12
93 POP r11
94 POP r10
95 POP r9
96 POP r8
97 POP r7
98 POP r6
99 POP r5
100 POP r4
101 POP r3
102 POP r2
103 POP r1
104 POP r0
105
106 #ifdef CONFIG_ARC_CURR_IN_REG
107 ld r25, [sp, 12]
108 #endif
109 .endm
110
111 /*--------------------------------------------------------------
112 * Helpers to save/restore callee-saved regs:
113 * used by several macros below
114 *-------------------------------------------------------------*/
115 .macro SAVE_R13_TO_R24
116 PUSH r13
117 PUSH r14
118 PUSH r15
119 PUSH r16
120 PUSH r17
121 PUSH r18
122 PUSH r19
123 PUSH r20
124 PUSH r21
125 PUSH r22
126 PUSH r23
127 PUSH r24
128 .endm
129
130 .macro RESTORE_R24_TO_R13
131 POP r24
132 POP r23
133 POP r22
134 POP r21
135 POP r20
136 POP r19
137 POP r18
138 POP r17
139 POP r16
140 POP r15
141 POP r14
142 POP r13
143 .endm
144
145 #define OFF_USER_R25_FROM_R24 (SZ_CALLEE_REGS + SZ_PT_REGS - 8)/4
146
147 /*--------------------------------------------------------------
148 * Collect User Mode callee regs as struct callee_regs - needed by
149 * fork/do_signal/unaligned-access-emulation.
150 * (By default only scratch regs are saved on entry to kernel)
151 *
152 * Special handling for r25 if used for caching Task Pointer.
153 * It would have been saved in task->thread.user_r25 already, but to keep
154 * the interface same it is copied into regular r25 placeholder in
155 * struct callee_regs.
156 *-------------------------------------------------------------*/
157 .macro SAVE_CALLEE_SAVED_USER
158
159 SAVE_R13_TO_R24
160
161 #ifdef CONFIG_ARC_CURR_IN_REG
162 ; Retrieve orig r25 and save it on stack
163 ld.as r12, [sp, OFF_USER_R25_FROM_R24]
164 st.a r12, [sp, -4]
165 #else
166 PUSH r25
167 #endif
168
169 .endm
170
171 /*--------------------------------------------------------------
172 * Save kernel Mode callee regs at the time of Contect Switch.
173 *
174 * Special handling for r25 if used for caching Task Pointer.
175 * Kernel simply skips saving it since it will be loaded with
176 * incoming task pointer anyways
177 *-------------------------------------------------------------*/
178 .macro SAVE_CALLEE_SAVED_KERNEL
179
180 SAVE_R13_TO_R24
181
182 #ifdef CONFIG_ARC_CURR_IN_REG
183 sub sp, sp, 4
184 #else
185 PUSH r25
186 #endif
187 .endm
188
189 /*--------------------------------------------------------------
190 * Opposite of SAVE_CALLEE_SAVED_KERNEL
191 *-------------------------------------------------------------*/
192 .macro RESTORE_CALLEE_SAVED_KERNEL
193
194 #ifdef CONFIG_ARC_CURR_IN_REG
195 add sp, sp, 4 /* skip usual r25 placeholder */
196 #else
197 POP r25
198 #endif
199 RESTORE_R24_TO_R13
200 .endm
201
202 /*--------------------------------------------------------------
203 * Opposite of SAVE_CALLEE_SAVED_USER
204 *
205 * ptrace tracer or unaligned-access fixup might have changed a user mode
206 * callee reg which is saved back to usual r25 storage location
207 *-------------------------------------------------------------*/
208 .macro RESTORE_CALLEE_SAVED_USER
209
210 #ifdef CONFIG_ARC_CURR_IN_REG
211 ld.ab r12, [sp, 4]
212 st.as r12, [sp, OFF_USER_R25_FROM_R24]
213 #else
214 POP r25
215 #endif
216 RESTORE_R24_TO_R13
217 .endm
218
219 /*--------------------------------------------------------------
220 * Super FAST Restore callee saved regs by simply re-adjusting SP
221 *-------------------------------------------------------------*/
222 .macro DISCARD_CALLEE_SAVED_USER
223 add sp, sp, SZ_CALLEE_REGS
224 .endm
225
226 /*-------------------------------------------------------------
227 * given a tsk struct, get to the base of it's kernel mode stack
228 * tsk->thread_info is really a PAGE, whose bottom hoists stack
229 * which grows upwards towards thread_info
230 *------------------------------------------------------------*/
231
232 .macro GET_TSK_STACK_BASE tsk, out
233
234 /* Get task->thread_info (this is essentially start of a PAGE) */
235 ld \out, [\tsk, TASK_THREAD_INFO]
236
237 /* Go to end of page where stack begins (grows upwards) */
238 add2 \out, \out, (THREAD_SIZE)/4
239
240 .endm
241
242 /*--------------------------------------------------------------
243 * Switch to Kernel Mode stack if SP points to User Mode stack
244 *
245 * Entry : r9 contains pre-IRQ/exception/trap status32
246 * Exit : SP is set to kernel mode stack pointer
247 * If CURR_IN_REG, r25 set to "current" task pointer
248 * Clobbers: r9
249 *-------------------------------------------------------------*/
250
251 .macro SWITCH_TO_KERNEL_STK
252
253 /* User Mode when this happened ? Yes: Proceed to switch stack */
254 bbit1 r9, STATUS_U_BIT, 88f
255
256 /* OK we were already in kernel mode when this event happened, thus can
257 * assume SP is kernel mode SP. _NO_ need to do any stack switching
258 */
259
260 #ifdef CONFIG_ARC_COMPACT_IRQ_LEVELS
261 /* However....
262 * If Level 2 Interrupts enabled, we may end up with a corner case:
263 * 1. User Task executing
264 * 2. L1 IRQ taken, ISR starts (CPU auto-switched to KERNEL mode)
265 * 3. But before it could switch SP from USER to KERNEL stack
266 * a L2 IRQ "Interrupts" L1
267 * Thay way although L2 IRQ happened in Kernel mode, stack is still
268 * not switched.
269 * To handle this, we may need to switch stack even if in kernel mode
270 * provided SP has values in range of USER mode stack ( < 0x7000_0000 )
271 */
272 brlo sp, VMALLOC_START, 88f
273
274 /* TODO: vineetg:
275 * We need to be a bit more cautious here. What if a kernel bug in
276 * L1 ISR, caused SP to go whaco (some small value which looks like
277 * USER stk) and then we take L2 ISR.
278 * Above brlo alone would treat it as a valid L1-L2 sceanrio
279 * instead of shouting alound
280 * The only feasible way is to make sure this L2 happened in
281 * L1 prelogue ONLY i.e. ilink2 is less than a pre-set marker in
282 * L1 ISR before it switches stack
283 */
284
285 #endif
286
287 /* Save Pre Intr/Exception KERNEL MODE SP on kernel stack
288 * safe-keeping not really needed, but it keeps the epilogue code
289 * (SP restore) simpler/uniform.
290 */
291 b.d 66f
292 mov r9, sp
293
294 88: /*------Intr/Ecxp happened in user mode, "switch" stack ------ */
295
296 GET_CURR_TASK_ON_CPU r9
297
298 /* With current tsk in r9, get it's kernel mode stack base */
299 GET_TSK_STACK_BASE r9, r9
300
301 66:
302 #ifdef CONFIG_ARC_CURR_IN_REG
303 /*
304 * Treat r25 as scratch reg, save it on stack first
305 * Load it with current task pointer
306 */
307 st r25, [r9, -4]
308 GET_CURR_TASK_ON_CPU r25
309 #endif
310
311 /* Save Pre Intr/Exception User SP on kernel stack */
312 st.a sp, [r9, -16] ; Make room for orig_r0, ECR, user_r25
313
314 /* CAUTION:
315 * SP should be set at the very end when we are done with everything
316 * In case of 2 levels of interrupt we depend on value of SP to assume
317 * that everything else is done (loading r25 etc)
318 */
319
320 /* set SP to point to kernel mode stack */
321 mov sp, r9
322
323 /* ----- Stack Switched to kernel Mode, Now save REG FILE ----- */
324
325 .endm
326
327 /*------------------------------------------------------------
328 * "FAKE" a rtie to return from CPU Exception context
329 * This is to re-enable Exceptions within exception
330 * Look at EV_ProtV to see how this is actually used
331 *-------------------------------------------------------------*/
332
333 .macro FAKE_RET_FROM_EXCPN reg
334
335 ld \reg, [sp, PT_status32]
336 bic \reg, \reg, (STATUS_U_MASK|STATUS_DE_MASK)
337 bset \reg, \reg, STATUS_L_BIT
338 sr \reg, [erstatus]
339 mov \reg, 55f
340 sr \reg, [eret]
341
342 rtie
343 55:
344 .endm
345
346 /*
347 * @reg [OUT] &thread_info of "current"
348 */
349 .macro GET_CURR_THR_INFO_FROM_SP reg
350 bic \reg, sp, (THREAD_SIZE - 1)
351 .endm
352
353 /*
354 * @reg [OUT] thread_info->flags of "current"
355 */
356 .macro GET_CURR_THR_INFO_FLAGS reg
357 GET_CURR_THR_INFO_FROM_SP \reg
358 ld \reg, [\reg, THREAD_INFO_FLAGS]
359 .endm
360
361 /*--------------------------------------------------------------
362 * For early Exception Prologue, a core reg is temporarily needed to
363 * code the rest of prolog (stack switching). This is done by stashing
364 * it to memory (non-SMP case) or SCRATCH0 Aux Reg (SMP).
365 *
366 * Before saving the full regfile - this reg is restored back, only
367 * to be saved again on kernel mode stack, as part of ptregs.
368 *-------------------------------------------------------------*/
369 .macro EXCPN_PROLOG_FREEUP_REG reg
370 #ifdef CONFIG_SMP
371 sr \reg, [ARC_REG_SCRATCH_DATA0]
372 #else
373 st \reg, [@ex_saved_reg1]
374 #endif
375 .endm
376
377 .macro EXCPN_PROLOG_RESTORE_REG reg
378 #ifdef CONFIG_SMP
379 lr \reg, [ARC_REG_SCRATCH_DATA0]
380 #else
381 ld \reg, [@ex_saved_reg1]
382 #endif
383 .endm
384
385 /*--------------------------------------------------------------
386 * Save all registers used by Exceptions (TLB Miss, Prot-V, Mem err etc)
387 * Requires SP to be already switched to kernel mode Stack
388 * sp points to the next free element on the stack at exit of this macro.
389 * Registers are pushed / popped in the order defined in struct ptregs
390 * in asm/ptrace.h
391 * Note that syscalls are implemented via TRAP which is also a exception
392 * from CPU's point of view
393 *-------------------------------------------------------------*/
394 .macro SAVE_ALL_SYS
395
396 lr r9, [ecr]
397 st r9, [sp, 8] /* ECR */
398 st r0, [sp, 4] /* orig_r0, needed only for sys calls */
399
400 /* Restore r9 used to code the early prologue */
401 EXCPN_PROLOG_RESTORE_REG r9
402
403 SAVE_R0_TO_R12
404 PUSH gp
405 PUSH fp
406 PUSH blink
407 PUSHAX eret
408 PUSHAX erstatus
409 PUSH lp_count
410 PUSHAX lp_end
411 PUSHAX lp_start
412 PUSHAX erbta
413 .endm
414
415 /*--------------------------------------------------------------
416 * Restore all registers used by system call or Exceptions
417 * SP should always be pointing to the next free stack element
418 * when entering this macro.
419 *
420 * NOTE:
421 *
422 * It is recommended that lp_count/ilink1/ilink2 not be used as a dest reg
423 * for memory load operations. If used in that way interrupts are deffered
424 * by hardware and that is not good.
425 *-------------------------------------------------------------*/
426 .macro RESTORE_ALL_SYS
427 POPAX erbta
428 POPAX lp_start
429 POPAX lp_end
430
431 POP r9
432 mov lp_count, r9 ;LD to lp_count is not allowed
433
434 POPAX erstatus
435 POPAX eret
436 POP blink
437 POP fp
438 POP gp
439 RESTORE_R12_TO_R0
440
441 ld sp, [sp] /* restore original sp */
442 /* orig_r0, ECR, user_r25 skipped automatically */
443 .endm
444
445
446 /*--------------------------------------------------------------
447 * Save all registers used by interrupt handlers.
448 *-------------------------------------------------------------*/
449 .macro SAVE_ALL_INT1
450
451 /* restore original r9 to be saved as part of reg-file */
452 #ifdef CONFIG_SMP
453 lr r9, [ARC_REG_SCRATCH_DATA0]
454 #else
455 ld r9, [@int1_saved_reg]
456 #endif
457
458 /* now we are ready to save the remaining context :) */
459 st event_IRQ1, [sp, 8] /* Dummy ECR */
460 st 0, [sp, 4] /* orig_r0 , N/A for IRQ */
461
462 SAVE_R0_TO_R12
463 PUSH gp
464 PUSH fp
465 PUSH blink
466 PUSH ilink1
467 PUSHAX status32_l1
468 PUSH lp_count
469 PUSHAX lp_end
470 PUSHAX lp_start
471 PUSHAX bta_l1
472 .endm
473
474 .macro SAVE_ALL_INT2
475
476 /* TODO-vineetg: SMP we can't use global nor can we use
477 * SCRATCH0 as we do for int1 because while int1 is using
478 * it, int2 can come
479 */
480 /* retsore original r9 , saved in sys_saved_r9 */
481 ld r9, [@int2_saved_reg]
482
483 /* now we are ready to save the remaining context :) */
484 st event_IRQ2, [sp, 8] /* Dummy ECR */
485 st 0, [sp, 4] /* orig_r0 , N/A for IRQ */
486
487 SAVE_R0_TO_R12
488 PUSH gp
489 PUSH fp
490 PUSH blink
491 PUSH ilink2
492 PUSHAX status32_l2
493 PUSH lp_count
494 PUSHAX lp_end
495 PUSHAX lp_start
496 PUSHAX bta_l2
497 .endm
498
499 /*--------------------------------------------------------------
500 * Restore all registers used by interrupt handlers.
501 *
502 * NOTE:
503 *
504 * It is recommended that lp_count/ilink1/ilink2 not be used as a dest reg
505 * for memory load operations. If used in that way interrupts are deffered
506 * by hardware and that is not good.
507 *-------------------------------------------------------------*/
508
509 .macro RESTORE_ALL_INT1
510 POPAX bta_l1
511 POPAX lp_start
512 POPAX lp_end
513
514 POP r9
515 mov lp_count, r9 ;LD to lp_count is not allowed
516
517 POPAX status32_l1
518 POP ilink1
519 POP blink
520 POP fp
521 POP gp
522 RESTORE_R12_TO_R0
523
524 ld sp, [sp] /* restore original sp */
525 /* orig_r0, ECR, user_r25 skipped automatically */
526 .endm
527
528 .macro RESTORE_ALL_INT2
529 POPAX bta_l2
530 POPAX lp_start
531 POPAX lp_end
532
533 POP r9
534 mov lp_count, r9 ;LD to lp_count is not allowed
535
536 POPAX status32_l2
537 POP ilink2
538 POP blink
539 POP fp
540 POP gp
541 RESTORE_R12_TO_R0
542
543 ld sp, [sp] /* restore original sp */
544 /* orig_r0, ECR, user_r25 skipped automatically */
545 .endm
546
547
548 /* Get CPU-ID of this core */
549 .macro GET_CPU_ID reg
550 lr \reg, [identity]
551 lsr \reg, \reg, 8
552 bmsk \reg, \reg, 7
553 .endm
554
555 #ifdef CONFIG_SMP
556
557 /*-------------------------------------------------
558 * Retrieve the current running task on this CPU
559 * 1. Determine curr CPU id.
560 * 2. Use it to index into _current_task[ ]
561 */
562 .macro GET_CURR_TASK_ON_CPU reg
563 GET_CPU_ID \reg
564 ld.as \reg, [@_current_task, \reg]
565 .endm
566
567 /*-------------------------------------------------
568 * Save a new task as the "current" task on this CPU
569 * 1. Determine curr CPU id.
570 * 2. Use it to index into _current_task[ ]
571 *
572 * Coded differently than GET_CURR_TASK_ON_CPU (which uses LD.AS)
573 * because ST r0, [r1, offset] can ONLY have s9 @offset
574 * while LD can take s9 (4 byte insn) or LIMM (8 byte insn)
575 */
576
577 .macro SET_CURR_TASK_ON_CPU tsk, tmp
578 GET_CPU_ID \tmp
579 add2 \tmp, @_current_task, \tmp
580 st \tsk, [\tmp]
581 #ifdef CONFIG_ARC_CURR_IN_REG
582 mov r25, \tsk
583 #endif
584
585 .endm
586
587
588 #else /* Uniprocessor implementation of macros */
589
590 .macro GET_CURR_TASK_ON_CPU reg
591 ld \reg, [@_current_task]
592 .endm
593
594 .macro SET_CURR_TASK_ON_CPU tsk, tmp
595 st \tsk, [@_current_task]
596 #ifdef CONFIG_ARC_CURR_IN_REG
597 mov r25, \tsk
598 #endif
599 .endm
600
601 #endif /* SMP / UNI */
602
603 /* ------------------------------------------------------------------
604 * Get the ptr to some field of Current Task at @off in task struct
605 * -Uses r25 for Current task ptr if that is enabled
606 */
607
608 #ifdef CONFIG_ARC_CURR_IN_REG
609
610 .macro GET_CURR_TASK_FIELD_PTR off, reg
611 add \reg, r25, \off
612 .endm
613
614 #else
615
616 .macro GET_CURR_TASK_FIELD_PTR off, reg
617 GET_CURR_TASK_ON_CPU \reg
618 add \reg, \reg, \off
619 .endm
620
621 #endif /* CONFIG_ARC_CURR_IN_REG */
622
623 #endif /* __ASSEMBLY__ */
624
625 #endif /* __ASM_ARC_ENTRY_H */
This page took 0.043732 seconds and 5 git commands to generate.