diff options
Diffstat (limited to 'arch/sh/kernel/entry-common.S')
-rw-r--r-- | arch/sh/kernel/entry-common.S | 103 |
1 files changed, 47 insertions, 56 deletions
diff --git a/arch/sh/kernel/entry-common.S b/arch/sh/kernel/entry-common.S index d62359cfbbe2..68d9223b145e 100644 --- a/arch/sh/kernel/entry-common.S +++ b/arch/sh/kernel/entry-common.S | |||
@@ -43,9 +43,10 @@ | |||
43 | * syscall # | 43 | * syscall # |
44 | * | 44 | * |
45 | */ | 45 | */ |
46 | #include <asm/dwarf.h> | ||
46 | 47 | ||
47 | #if defined(CONFIG_PREEMPT) | 48 | #if defined(CONFIG_PREEMPT) |
48 | # define preempt_stop() cli | 49 | # define preempt_stop() cli ; TRACE_IRQS_OFF |
49 | #else | 50 | #else |
50 | # define preempt_stop() | 51 | # define preempt_stop() |
51 | # define resume_kernel __restore_all | 52 | # define resume_kernel __restore_all |
@@ -55,11 +56,7 @@ | |||
55 | .align 2 | 56 | .align 2 |
56 | ENTRY(exception_error) | 57 | ENTRY(exception_error) |
57 | ! | 58 | ! |
58 | #ifdef CONFIG_TRACE_IRQFLAGS | 59 | TRACE_IRQS_ON |
59 | mov.l 2f, r0 | ||
60 | jsr @r0 | ||
61 | nop | ||
62 | #endif | ||
63 | sti | 60 | sti |
64 | mov.l 1f, r0 | 61 | mov.l 1f, r0 |
65 | jmp @r0 | 62 | jmp @r0 |
@@ -67,18 +64,15 @@ ENTRY(exception_error) | |||
67 | 64 | ||
68 | .align 2 | 65 | .align 2 |
69 | 1: .long do_exception_error | 66 | 1: .long do_exception_error |
70 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
71 | 2: .long trace_hardirqs_on | ||
72 | #endif | ||
73 | 67 | ||
74 | .align 2 | 68 | .align 2 |
75 | ret_from_exception: | 69 | ret_from_exception: |
70 | CFI_STARTPROC simple | ||
71 | CFI_DEF_CFA r14, 0 | ||
72 | CFI_REL_OFFSET 17, 64 | ||
73 | CFI_REL_OFFSET 15, 0 | ||
74 | CFI_REL_OFFSET 14, 56 | ||
76 | preempt_stop() | 75 | preempt_stop() |
77 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
78 | mov.l 4f, r0 | ||
79 | jsr @r0 | ||
80 | nop | ||
81 | #endif | ||
82 | ENTRY(ret_from_irq) | 76 | ENTRY(ret_from_irq) |
83 | ! | 77 | ! |
84 | mov #OFF_SR, r0 | 78 | mov #OFF_SR, r0 |
@@ -93,6 +87,7 @@ ENTRY(ret_from_irq) | |||
93 | nop | 87 | nop |
94 | ENTRY(resume_kernel) | 88 | ENTRY(resume_kernel) |
95 | cli | 89 | cli |
90 | TRACE_IRQS_OFF | ||
96 | mov.l @(TI_PRE_COUNT,r8), r0 ! current_thread_info->preempt_count | 91 | mov.l @(TI_PRE_COUNT,r8), r0 ! current_thread_info->preempt_count |
97 | tst r0, r0 | 92 | tst r0, r0 |
98 | bf noresched | 93 | bf noresched |
@@ -103,8 +98,9 @@ need_resched: | |||
103 | 98 | ||
104 | mov #OFF_SR, r0 | 99 | mov #OFF_SR, r0 |
105 | mov.l @(r0,r15), r0 ! get status register | 100 | mov.l @(r0,r15), r0 ! get status register |
106 | and #0xf0, r0 ! interrupts off (exception path)? | 101 | shlr r0 |
107 | cmp/eq #0xf0, r0 | 102 | and #(0xf0>>1), r0 ! interrupts off (exception path)? |
103 | cmp/eq #(0xf0>>1), r0 | ||
108 | bt noresched | 104 | bt noresched |
109 | mov.l 3f, r0 | 105 | mov.l 3f, r0 |
110 | jsr @r0 ! call preempt_schedule_irq | 106 | jsr @r0 ! call preempt_schedule_irq |
@@ -125,13 +121,9 @@ noresched: | |||
125 | ENTRY(resume_userspace) | 121 | ENTRY(resume_userspace) |
126 | ! r8: current_thread_info | 122 | ! r8: current_thread_info |
127 | cli | 123 | cli |
128 | #ifdef CONFIG_TRACE_IRQFLAGS | 124 | TRACE_IRQS_OfF |
129 | mov.l 5f, r0 | ||
130 | jsr @r0 | ||
131 | nop | ||
132 | #endif | ||
133 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags | 125 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags |
134 | tst #_TIF_WORK_MASK, r0 | 126 | tst #(_TIF_WORK_MASK & 0xff), r0 |
135 | bt/s __restore_all | 127 | bt/s __restore_all |
136 | tst #_TIF_NEED_RESCHED, r0 | 128 | tst #_TIF_NEED_RESCHED, r0 |
137 | 129 | ||
@@ -156,14 +148,10 @@ work_resched: | |||
156 | jsr @r1 ! schedule | 148 | jsr @r1 ! schedule |
157 | nop | 149 | nop |
158 | cli | 150 | cli |
159 | #ifdef CONFIG_TRACE_IRQFLAGS | 151 | TRACE_IRQS_OFF |
160 | mov.l 5f, r0 | ||
161 | jsr @r0 | ||
162 | nop | ||
163 | #endif | ||
164 | ! | 152 | ! |
165 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags | 153 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags |
166 | tst #_TIF_WORK_MASK, r0 | 154 | tst #(_TIF_WORK_MASK & 0xff), r0 |
167 | bt __restore_all | 155 | bt __restore_all |
168 | bra work_pending | 156 | bra work_pending |
169 | tst #_TIF_NEED_RESCHED, r0 | 157 | tst #_TIF_NEED_RESCHED, r0 |
@@ -172,23 +160,15 @@ work_resched: | |||
172 | 1: .long schedule | 160 | 1: .long schedule |
173 | 2: .long do_notify_resume | 161 | 2: .long do_notify_resume |
174 | 3: .long resume_userspace | 162 | 3: .long resume_userspace |
175 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
176 | 4: .long trace_hardirqs_on | ||
177 | 5: .long trace_hardirqs_off | ||
178 | #endif | ||
179 | 163 | ||
180 | .align 2 | 164 | .align 2 |
181 | syscall_exit_work: | 165 | syscall_exit_work: |
182 | ! r0: current_thread_info->flags | 166 | ! r0: current_thread_info->flags |
183 | ! r8: current_thread_info | 167 | ! r8: current_thread_info |
184 | tst #_TIF_WORK_SYSCALL_MASK, r0 | 168 | tst #(_TIF_WORK_SYSCALL_MASK & 0xff), r0 |
185 | bt/s work_pending | 169 | bt/s work_pending |
186 | tst #_TIF_NEED_RESCHED, r0 | 170 | tst #_TIF_NEED_RESCHED, r0 |
187 | #ifdef CONFIG_TRACE_IRQFLAGS | 171 | TRACE_IRQS_ON |
188 | mov.l 5f, r0 | ||
189 | jsr @r0 | ||
190 | nop | ||
191 | #endif | ||
192 | sti | 172 | sti |
193 | mov r15, r4 | 173 | mov r15, r4 |
194 | mov.l 8f, r0 ! do_syscall_trace_leave | 174 | mov.l 8f, r0 ! do_syscall_trace_leave |
@@ -226,12 +206,25 @@ syscall_trace_entry: | |||
226 | mov.l r0, @(OFF_R0,r15) ! Return value | 206 | mov.l r0, @(OFF_R0,r15) ! Return value |
227 | 207 | ||
228 | __restore_all: | 208 | __restore_all: |
229 | mov.l 1f, r0 | 209 | mov #OFF_SR, r0 |
210 | mov.l @(r0,r15), r0 ! get status register | ||
211 | |||
212 | shlr2 r0 | ||
213 | and #0x3c, r0 | ||
214 | cmp/eq #0x3c, r0 | ||
215 | bt 1f | ||
216 | TRACE_IRQS_ON | ||
217 | bra 2f | ||
218 | nop | ||
219 | 1: | ||
220 | TRACE_IRQS_OFF | ||
221 | 2: | ||
222 | mov.l 3f, r0 | ||
230 | jmp @r0 | 223 | jmp @r0 |
231 | nop | 224 | nop |
232 | 225 | ||
233 | .align 2 | 226 | .align 2 |
234 | 1: .long restore_all | 227 | 3: .long restore_all |
235 | 228 | ||
236 | .align 2 | 229 | .align 2 |
237 | syscall_badsys: ! Bad syscall number | 230 | syscall_badsys: ! Bad syscall number |
@@ -259,6 +252,7 @@ debug_trap: | |||
259 | nop | 252 | nop |
260 | bra __restore_all | 253 | bra __restore_all |
261 | nop | 254 | nop |
255 | CFI_ENDPROC | ||
262 | 256 | ||
263 | .align 2 | 257 | .align 2 |
264 | 1: .long debug_trap_table | 258 | 1: .long debug_trap_table |
@@ -304,6 +298,7 @@ ret_from_fork: | |||
304 | * system calls and debug traps through their respective jump tables. | 298 | * system calls and debug traps through their respective jump tables. |
305 | */ | 299 | */ |
306 | ENTRY(system_call) | 300 | ENTRY(system_call) |
301 | setup_frame_reg | ||
307 | #if !defined(CONFIG_CPU_SH2) | 302 | #if !defined(CONFIG_CPU_SH2) |
308 | mov.l 1f, r9 | 303 | mov.l 1f, r9 |
309 | mov.l @r9, r8 ! Read from TRA (Trap Address) Register | 304 | mov.l @r9, r8 ! Read from TRA (Trap Address) Register |
@@ -321,18 +316,18 @@ ENTRY(system_call) | |||
321 | bt/s debug_trap ! it's a debug trap.. | 316 | bt/s debug_trap ! it's a debug trap.. |
322 | nop | 317 | nop |
323 | 318 | ||
324 | #ifdef CONFIG_TRACE_IRQFLAGS | 319 | TRACE_IRQS_ON |
325 | mov.l 5f, r10 | ||
326 | jsr @r10 | ||
327 | nop | ||
328 | #endif | ||
329 | sti | 320 | sti |
330 | 321 | ||
331 | ! | 322 | ! |
332 | get_current_thread_info r8, r10 | 323 | get_current_thread_info r8, r10 |
333 | mov.l @(TI_FLAGS,r8), r8 | 324 | mov.l @(TI_FLAGS,r8), r8 |
334 | mov #_TIF_WORK_SYSCALL_MASK, r10 | 325 | mov #(_TIF_WORK_SYSCALL_MASK & 0xff), r10 |
326 | mov #(_TIF_WORK_SYSCALL_MASK >> 8), r9 | ||
335 | tst r10, r8 | 327 | tst r10, r8 |
328 | shll8 r9 | ||
329 | bf syscall_trace_entry | ||
330 | tst r9, r8 | ||
336 | bf syscall_trace_entry | 331 | bf syscall_trace_entry |
337 | ! | 332 | ! |
338 | mov.l 2f, r8 ! Number of syscalls | 333 | mov.l 2f, r8 ! Number of syscalls |
@@ -351,15 +346,15 @@ syscall_call: | |||
351 | ! | 346 | ! |
352 | syscall_exit: | 347 | syscall_exit: |
353 | cli | 348 | cli |
354 | #ifdef CONFIG_TRACE_IRQFLAGS | 349 | TRACE_IRQS_OFF |
355 | mov.l 6f, r0 | ||
356 | jsr @r0 | ||
357 | nop | ||
358 | #endif | ||
359 | ! | 350 | ! |
360 | get_current_thread_info r8, r0 | 351 | get_current_thread_info r8, r0 |
361 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags | 352 | mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags |
362 | tst #_TIF_ALLWORK_MASK, r0 | 353 | tst #(_TIF_ALLWORK_MASK & 0xff), r0 |
354 | mov #(_TIF_ALLWORK_MASK >> 8), r1 | ||
355 | bf syscall_exit_work | ||
356 | shlr8 r0 | ||
357 | tst r0, r1 | ||
363 | bf syscall_exit_work | 358 | bf syscall_exit_work |
364 | bra __restore_all | 359 | bra __restore_all |
365 | nop | 360 | nop |
@@ -369,9 +364,5 @@ syscall_exit: | |||
369 | #endif | 364 | #endif |
370 | 2: .long NR_syscalls | 365 | 2: .long NR_syscalls |
371 | 3: .long sys_call_table | 366 | 3: .long sys_call_table |
372 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
373 | 5: .long trace_hardirqs_on | ||
374 | 6: .long trace_hardirqs_off | ||
375 | #endif | ||
376 | 7: .long do_syscall_trace_enter | 367 | 7: .long do_syscall_trace_enter |
377 | 8: .long do_syscall_trace_leave | 368 | 8: .long do_syscall_trace_leave |