diff options
author | Martin Schwidefsky <schwidefsky@de.ibm.com> | 2010-05-17 04:00:05 -0400 |
---|---|---|
committer | Martin Schwidefsky <sky@mschwide.boeblingen.de.ibm.com> | 2010-05-17 04:00:15 -0400 |
commit | 86f2552bbd0e17b19bb5e9881042533eaea553c7 (patch) | |
tree | f520909d953f5d8c7db3dd4c4f2582bd7f7473aa /arch/s390/kernel/entry64.S | |
parent | cd3b70f5d4d82f85d1e1d6e822f38ae098cf7c72 (diff) |
[S390] add breaking event address for user space
Copy the last breaking event address from the lowcore to a new
field in the thread_struct on each system entry. Add a new
ptrace request PTRACE_GET_LAST_BREAK and a new utrace regset
REGSET_LAST_BREAK to query the last breaking event.
This is useful for debugging wild branches in user space code.
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'arch/s390/kernel/entry64.S')
-rw-r--r-- | arch/s390/kernel/entry64.S | 270 |
1 files changed, 146 insertions, 124 deletions
diff --git a/arch/s390/kernel/entry64.S b/arch/s390/kernel/entry64.S index 829b759ba1e1..178d92536d90 100644 --- a/arch/s390/kernel/entry64.S +++ b/arch/s390/kernel/entry64.S | |||
@@ -126,31 +126,35 @@ _TIF_SYSCALL = (_TIF_SYSCALL_TRACE>>8 | _TIF_SYSCALL_AUDIT>>8 | \ | |||
126 | * R15 - kernel stack pointer | 126 | * R15 - kernel stack pointer |
127 | */ | 127 | */ |
128 | 128 | ||
129 | .macro SAVE_ALL_BASE savearea | ||
130 | stmg %r12,%r15,\savearea | ||
131 | larl %r13,system_call | ||
132 | .endm | ||
133 | |||
134 | .macro SAVE_ALL_SVC psworg,savearea | 129 | .macro SAVE_ALL_SVC psworg,savearea |
135 | la %r12,\psworg | 130 | stmg %r11,%r15,\savearea |
136 | lg %r15,__LC_KERNEL_STACK # problem state -> load ksp | 131 | lg %r15,__LC_KERNEL_STACK # problem state -> load ksp |
132 | aghi %r15,-SP_SIZE # make room for registers & psw | ||
133 | lg %r11,__LC_LAST_BREAK | ||
137 | .endm | 134 | .endm |
138 | 135 | ||
139 | .macro SAVE_ALL_SYNC psworg,savearea | 136 | .macro SAVE_ALL_PGM psworg,savearea |
140 | la %r12,\psworg | 137 | stmg %r11,%r15,\savearea |
141 | tm \psworg+1,0x01 # test problem state bit | 138 | tm \psworg+1,0x01 # test problem state bit |
142 | jz 2f # skip stack setup save | ||
143 | lg %r15,__LC_KERNEL_STACK # problem state -> load ksp | ||
144 | #ifdef CONFIG_CHECK_STACK | 139 | #ifdef CONFIG_CHECK_STACK |
145 | j 3f | 140 | jnz 1f |
146 | 2: tml %r15,STACK_SIZE - CONFIG_STACK_GUARD | 141 | tml %r15,STACK_SIZE - CONFIG_STACK_GUARD |
147 | jz stack_overflow | 142 | jnz 2f |
148 | 3: | 143 | la %r12,\psworg |
144 | j stack_overflow | ||
145 | #else | ||
146 | jz 2f | ||
149 | #endif | 147 | #endif |
150 | 2: | 148 | 1: lg %r15,__LC_KERNEL_STACK # problem state -> load ksp |
149 | 2: aghi %r15,-SP_SIZE # make room for registers & psw | ||
150 | larl %r13,system_call | ||
151 | lg %r11,__LC_LAST_BREAK | ||
151 | .endm | 152 | .endm |
152 | 153 | ||
153 | .macro SAVE_ALL_ASYNC psworg,savearea | 154 | .macro SAVE_ALL_ASYNC psworg,savearea |
155 | stmg %r11,%r15,\savearea | ||
156 | larl %r13,system_call | ||
157 | lg %r11,__LC_LAST_BREAK | ||
154 | la %r12,\psworg | 158 | la %r12,\psworg |
155 | tm \psworg+1,0x01 # test problem state bit | 159 | tm \psworg+1,0x01 # test problem state bit |
156 | jnz 1f # from user -> load kernel stack | 160 | jnz 1f # from user -> load kernel stack |
@@ -164,27 +168,23 @@ _TIF_SYSCALL = (_TIF_SYSCALL_TRACE>>8 | _TIF_SYSCALL_AUDIT>>8 | \ | |||
164 | 0: lg %r14,__LC_ASYNC_STACK # are we already on the async. stack ? | 168 | 0: lg %r14,__LC_ASYNC_STACK # are we already on the async. stack ? |
165 | slgr %r14,%r15 | 169 | slgr %r14,%r15 |
166 | srag %r14,%r14,STACK_SHIFT | 170 | srag %r14,%r14,STACK_SHIFT |
167 | jz 2f | ||
168 | 1: lg %r15,__LC_ASYNC_STACK # load async stack | ||
169 | #ifdef CONFIG_CHECK_STACK | 171 | #ifdef CONFIG_CHECK_STACK |
170 | j 3f | 172 | jnz 1f |
171 | 2: tml %r15,STACK_SIZE - CONFIG_STACK_GUARD | 173 | tml %r15,STACK_SIZE - CONFIG_STACK_GUARD |
172 | jz stack_overflow | 174 | jnz 2f |
173 | 3: | 175 | j stack_overflow |
176 | #else | ||
177 | jz 2f | ||
174 | #endif | 178 | #endif |
175 | 2: | 179 | 1: lg %r15,__LC_ASYNC_STACK # load async stack |
180 | 2: aghi %r15,-SP_SIZE # make room for registers & psw | ||
176 | .endm | 181 | .endm |
177 | 182 | ||
178 | .macro CREATE_STACK_FRAME psworg,savearea | 183 | .macro CREATE_STACK_FRAME savearea |
179 | aghi %r15,-SP_SIZE # make room for registers & psw | 184 | xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) |
180 | mvc SP_PSW(16,%r15),0(%r12) # move user PSW to stack | ||
181 | stg %r2,SP_ORIG_R2(%r15) # store original content of gpr 2 | 185 | stg %r2,SP_ORIG_R2(%r15) # store original content of gpr 2 |
182 | icm %r12,3,__LC_SVC_ILC | 186 | mvc SP_R11(40,%r15),\savearea # move %r11-%r15 to stack |
183 | stmg %r0,%r11,SP_R0(%r15) # store gprs %r0-%r11 to kernel stack | 187 | stmg %r0,%r10,SP_R0(%r15) # store gprs %r0-%r10 to kernel stack |
184 | st %r12,SP_SVCNR(%r15) | ||
185 | mvc SP_R12(32,%r15),\savearea # move %r12-%r15 to stack | ||
186 | la %r12,0 | ||
187 | stg %r12,__SF_BACKCHAIN(%r15) | ||
188 | .endm | 188 | .endm |
189 | 189 | ||
190 | .macro RESTORE_ALL psworg,sync | 190 | .macro RESTORE_ALL psworg,sync |
@@ -200,6 +200,13 @@ _TIF_SYSCALL = (_TIF_SYSCALL_TRACE>>8 | _TIF_SYSCALL_AUDIT>>8 | \ | |||
200 | lpswe \psworg # back to caller | 200 | lpswe \psworg # back to caller |
201 | .endm | 201 | .endm |
202 | 202 | ||
203 | .macro LAST_BREAK | ||
204 | srag %r10,%r11,23 | ||
205 | jz 0f | ||
206 | stg %r11,__TI_last_break(%r12) | ||
207 | 0: | ||
208 | .endm | ||
209 | |||
203 | /* | 210 | /* |
204 | * Scheduler resume function, called by switch_to | 211 | * Scheduler resume function, called by switch_to |
205 | * gpr2 = (task_struct *) prev | 212 | * gpr2 = (task_struct *) prev |
@@ -245,37 +252,38 @@ __critical_start: | |||
245 | system_call: | 252 | system_call: |
246 | stpt __LC_SYNC_ENTER_TIMER | 253 | stpt __LC_SYNC_ENTER_TIMER |
247 | sysc_saveall: | 254 | sysc_saveall: |
248 | SAVE_ALL_BASE __LC_SAVE_AREA | ||
249 | SAVE_ALL_SVC __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 255 | SAVE_ALL_SVC __LC_SVC_OLD_PSW,__LC_SAVE_AREA |
250 | CREATE_STACK_FRAME __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 256 | CREATE_STACK_FRAME __LC_SAVE_AREA |
251 | llgh %r7,__LC_SVC_INT_CODE # get svc number from lowcore | 257 | mvc SP_PSW(16,%r15),__LC_SVC_OLD_PSW |
258 | mvc SP_ILC(4,%r15),__LC_SVC_ILC | ||
259 | stg %r7,SP_ARGS(%r15) | ||
260 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
252 | sysc_vtime: | 261 | sysc_vtime: |
253 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER | 262 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER |
254 | sysc_stime: | 263 | sysc_stime: |
255 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 264 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
256 | sysc_update: | 265 | sysc_update: |
257 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 266 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
267 | LAST_BREAK | ||
258 | sysc_do_svc: | 268 | sysc_do_svc: |
259 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 269 | llgh %r7,SP_SVCNR(%r15) |
260 | ltgr %r7,%r7 # test for svc 0 | 270 | slag %r7,%r7,2 # shift and test for svc 0 |
261 | jnz sysc_nr_ok | 271 | jnz sysc_nr_ok |
262 | # svc 0: system call number in %r1 | 272 | # svc 0: system call number in %r1 |
263 | cl %r1,BASED(.Lnr_syscalls) | 273 | llgfr %r1,%r1 # clear high word in r1 |
274 | cghi %r1,NR_syscalls | ||
264 | jnl sysc_nr_ok | 275 | jnl sysc_nr_ok |
265 | lgfr %r7,%r1 # clear high word in r1 | 276 | sth %r1,SP_SVCNR(%r15) |
277 | slag %r7,%r1,2 # shift and test for svc 0 | ||
266 | sysc_nr_ok: | 278 | sysc_nr_ok: |
267 | mvc SP_ARGS(8,%r15),SP_R7(%r15) | ||
268 | sysc_do_restart: | ||
269 | sth %r7,SP_SVCNR(%r15) | ||
270 | sllg %r7,%r7,2 # svc number * 4 | ||
271 | larl %r10,sys_call_table | 279 | larl %r10,sys_call_table |
272 | #ifdef CONFIG_COMPAT | 280 | #ifdef CONFIG_COMPAT |
273 | tm __TI_flags+5(%r9),(_TIF_31BIT>>16) # running in 31 bit mode ? | 281 | tm __TI_flags+5(%r12),(_TIF_31BIT>>16) # running in 31 bit mode ? |
274 | jno sysc_noemu | 282 | jno sysc_noemu |
275 | larl %r10,sys_call_table_emu # use 31 bit emulation system calls | 283 | larl %r10,sys_call_table_emu # use 31 bit emulation system calls |
276 | sysc_noemu: | 284 | sysc_noemu: |
277 | #endif | 285 | #endif |
278 | tm __TI_flags+6(%r9),_TIF_SYSCALL | 286 | tm __TI_flags+6(%r12),_TIF_SYSCALL |
279 | lgf %r8,0(%r7,%r10) # load address of system call routine | 287 | lgf %r8,0(%r7,%r10) # load address of system call routine |
280 | jnz sysc_tracesys | 288 | jnz sysc_tracesys |
281 | basr %r14,%r8 # call sys_xxxx | 289 | basr %r14,%r8 # call sys_xxxx |
@@ -284,7 +292,7 @@ sysc_noemu: | |||
284 | sysc_return: | 292 | sysc_return: |
285 | LOCKDEP_SYS_EXIT | 293 | LOCKDEP_SYS_EXIT |
286 | sysc_tif: | 294 | sysc_tif: |
287 | tm __TI_flags+7(%r9),_TIF_WORK_SVC | 295 | tm __TI_flags+7(%r12),_TIF_WORK_SVC |
288 | jnz sysc_work # there is work to do (signals etc.) | 296 | jnz sysc_work # there is work to do (signals etc.) |
289 | sysc_restore: | 297 | sysc_restore: |
290 | RESTORE_ALL __LC_RETURN_PSW,1 | 298 | RESTORE_ALL __LC_RETURN_PSW,1 |
@@ -301,17 +309,17 @@ sysc_work: | |||
301 | # One of the work bits is on. Find out which one. | 309 | # One of the work bits is on. Find out which one. |
302 | # | 310 | # |
303 | sysc_work_tif: | 311 | sysc_work_tif: |
304 | tm __TI_flags+7(%r9),_TIF_MCCK_PENDING | 312 | tm __TI_flags+7(%r12),_TIF_MCCK_PENDING |
305 | jo sysc_mcck_pending | 313 | jo sysc_mcck_pending |
306 | tm __TI_flags+7(%r9),_TIF_NEED_RESCHED | 314 | tm __TI_flags+7(%r12),_TIF_NEED_RESCHED |
307 | jo sysc_reschedule | 315 | jo sysc_reschedule |
308 | tm __TI_flags+7(%r9),_TIF_SIGPENDING | 316 | tm __TI_flags+7(%r12),_TIF_SIGPENDING |
309 | jo sysc_sigpending | 317 | jo sysc_sigpending |
310 | tm __TI_flags+7(%r9),_TIF_NOTIFY_RESUME | 318 | tm __TI_flags+7(%r12),_TIF_NOTIFY_RESUME |
311 | jo sysc_notify_resume | 319 | jo sysc_notify_resume |
312 | tm __TI_flags+7(%r9),_TIF_RESTART_SVC | 320 | tm __TI_flags+7(%r12),_TIF_RESTART_SVC |
313 | jo sysc_restart | 321 | jo sysc_restart |
314 | tm __TI_flags+7(%r9),_TIF_SINGLE_STEP | 322 | tm __TI_flags+7(%r12),_TIF_SINGLE_STEP |
315 | jo sysc_singlestep | 323 | jo sysc_singlestep |
316 | j sysc_return # beware of critical section cleanup | 324 | j sysc_return # beware of critical section cleanup |
317 | 325 | ||
@@ -333,12 +341,12 @@ sysc_mcck_pending: | |||
333 | # _TIF_SIGPENDING is set, call do_signal | 341 | # _TIF_SIGPENDING is set, call do_signal |
334 | # | 342 | # |
335 | sysc_sigpending: | 343 | sysc_sigpending: |
336 | ni __TI_flags+7(%r9),255-_TIF_SINGLE_STEP # clear TIF_SINGLE_STEP | 344 | ni __TI_flags+7(%r12),255-_TIF_SINGLE_STEP # clear TIF_SINGLE_STEP |
337 | la %r2,SP_PTREGS(%r15) # load pt_regs | 345 | la %r2,SP_PTREGS(%r15) # load pt_regs |
338 | brasl %r14,do_signal # call do_signal | 346 | brasl %r14,do_signal # call do_signal |
339 | tm __TI_flags+7(%r9),_TIF_RESTART_SVC | 347 | tm __TI_flags+7(%r12),_TIF_RESTART_SVC |
340 | jo sysc_restart | 348 | jo sysc_restart |
341 | tm __TI_flags+7(%r9),_TIF_SINGLE_STEP | 349 | tm __TI_flags+7(%r12),_TIF_SINGLE_STEP |
342 | jo sysc_singlestep | 350 | jo sysc_singlestep |
343 | j sysc_return | 351 | j sysc_return |
344 | 352 | ||
@@ -354,17 +362,19 @@ sysc_notify_resume: | |||
354 | # _TIF_RESTART_SVC is set, set up registers and restart svc | 362 | # _TIF_RESTART_SVC is set, set up registers and restart svc |
355 | # | 363 | # |
356 | sysc_restart: | 364 | sysc_restart: |
357 | ni __TI_flags+7(%r9),255-_TIF_RESTART_SVC # clear TIF_RESTART_SVC | 365 | ni __TI_flags+7(%r12),255-_TIF_RESTART_SVC # clear TIF_RESTART_SVC |
358 | lg %r7,SP_R2(%r15) # load new svc number | 366 | lg %r7,SP_R2(%r15) # load new svc number |
359 | mvc SP_R2(8,%r15),SP_ORIG_R2(%r15) # restore first argument | 367 | mvc SP_R2(8,%r15),SP_ORIG_R2(%r15) # restore first argument |
360 | lmg %r2,%r6,SP_R2(%r15) # load svc arguments | 368 | lmg %r2,%r6,SP_R2(%r15) # load svc arguments |
361 | j sysc_do_restart # restart svc | 369 | sth %r7,SP_SVCNR(%r15) |
370 | slag %r7,%r7,2 | ||
371 | j sysc_nr_ok # restart svc | ||
362 | 372 | ||
363 | # | 373 | # |
364 | # _TIF_SINGLE_STEP is set, call do_single_step | 374 | # _TIF_SINGLE_STEP is set, call do_single_step |
365 | # | 375 | # |
366 | sysc_singlestep: | 376 | sysc_singlestep: |
367 | ni __TI_flags+7(%r9),255-_TIF_SINGLE_STEP # clear TIF_SINGLE_STEP | 377 | ni __TI_flags+7(%r12),255-_TIF_SINGLE_STEP # clear TIF_SINGLE_STEP |
368 | xc SP_SVCNR(2,%r15),SP_SVCNR(%r15) # clear svc number | 378 | xc SP_SVCNR(2,%r15),SP_SVCNR(%r15) # clear svc number |
369 | la %r2,SP_PTREGS(%r15) # address of register-save area | 379 | la %r2,SP_PTREGS(%r15) # address of register-save area |
370 | larl %r14,sysc_return # load adr. of system return | 380 | larl %r14,sysc_return # load adr. of system return |
@@ -377,8 +387,8 @@ sysc_singlestep: | |||
377 | sysc_tracesys: | 387 | sysc_tracesys: |
378 | la %r2,SP_PTREGS(%r15) # load pt_regs | 388 | la %r2,SP_PTREGS(%r15) # load pt_regs |
379 | la %r3,0 | 389 | la %r3,0 |
380 | srl %r7,2 | 390 | llgh %r0,SP_SVCNR(%r15) |
381 | stg %r7,SP_R2(%r15) | 391 | stg %r0,SP_R2(%r15) |
382 | brasl %r14,do_syscall_trace_enter | 392 | brasl %r14,do_syscall_trace_enter |
383 | lghi %r0,NR_syscalls | 393 | lghi %r0,NR_syscalls |
384 | clgr %r0,%r2 | 394 | clgr %r0,%r2 |
@@ -391,7 +401,7 @@ sysc_tracego: | |||
391 | basr %r14,%r8 # call sys_xxx | 401 | basr %r14,%r8 # call sys_xxx |
392 | stg %r2,SP_R2(%r15) # store return value | 402 | stg %r2,SP_R2(%r15) # store return value |
393 | sysc_tracenogo: | 403 | sysc_tracenogo: |
394 | tm __TI_flags+6(%r9),_TIF_SYSCALL | 404 | tm __TI_flags+6(%r12),_TIF_SYSCALL |
395 | jz sysc_return | 405 | jz sysc_return |
396 | la %r2,SP_PTREGS(%r15) # load pt_regs | 406 | la %r2,SP_PTREGS(%r15) # load pt_regs |
397 | larl %r14,sysc_return # return point is sysc_return | 407 | larl %r14,sysc_return # return point is sysc_return |
@@ -403,7 +413,7 @@ sysc_tracenogo: | |||
403 | .globl ret_from_fork | 413 | .globl ret_from_fork |
404 | ret_from_fork: | 414 | ret_from_fork: |
405 | lg %r13,__LC_SVC_NEW_PSW+8 | 415 | lg %r13,__LC_SVC_NEW_PSW+8 |
406 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 416 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct |
407 | tm SP_PSW+1(%r15),0x01 # forking a kernel thread ? | 417 | tm SP_PSW+1(%r15),0x01 # forking a kernel thread ? |
408 | jo 0f | 418 | jo 0f |
409 | stg %r15,SP_R15(%r15) # store stack pointer for new kthread | 419 | stg %r15,SP_R15(%r15) # store stack pointer for new kthread |
@@ -437,8 +447,8 @@ kernel_execve: | |||
437 | lg %r15,__LC_KERNEL_STACK # load ksp | 447 | lg %r15,__LC_KERNEL_STACK # load ksp |
438 | aghi %r15,-SP_SIZE # make room for registers & psw | 448 | aghi %r15,-SP_SIZE # make room for registers & psw |
439 | lg %r13,__LC_SVC_NEW_PSW+8 | 449 | lg %r13,__LC_SVC_NEW_PSW+8 |
440 | lg %r9,__LC_THREAD_INFO | ||
441 | mvc SP_PTREGS(__PT_SIZE,%r15),0(%r12) # copy pt_regs | 450 | mvc SP_PTREGS(__PT_SIZE,%r15),0(%r12) # copy pt_regs |
451 | lg %r12,__LC_THREAD_INFO | ||
442 | xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) | 452 | xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) |
443 | # TRACE_IRQS_ON | 453 | # TRACE_IRQS_ON |
444 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 454 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
@@ -465,21 +475,23 @@ pgm_check_handler: | |||
465 | * for LPSW?). | 475 | * for LPSW?). |
466 | */ | 476 | */ |
467 | stpt __LC_SYNC_ENTER_TIMER | 477 | stpt __LC_SYNC_ENTER_TIMER |
468 | SAVE_ALL_BASE __LC_SAVE_AREA | ||
469 | tm __LC_PGM_INT_CODE+1,0x80 # check whether we got a per exception | 478 | tm __LC_PGM_INT_CODE+1,0x80 # check whether we got a per exception |
470 | jnz pgm_per # got per exception -> special case | 479 | jnz pgm_per # got per exception -> special case |
471 | SAVE_ALL_SYNC __LC_PGM_OLD_PSW,__LC_SAVE_AREA | 480 | SAVE_ALL_PGM __LC_PGM_OLD_PSW,__LC_SAVE_AREA |
472 | CREATE_STACK_FRAME __LC_PGM_OLD_PSW,__LC_SAVE_AREA | 481 | CREATE_STACK_FRAME __LC_SAVE_AREA |
482 | xc SP_ILC(4,%r15),SP_ILC(%r15) | ||
483 | mvc SP_PSW(16,%r15),__LC_PGM_OLD_PSW | ||
484 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
473 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? | 485 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? |
474 | jz pgm_no_vtime | 486 | jz pgm_no_vtime |
475 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER | 487 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER |
476 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 488 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
477 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 489 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
490 | LAST_BREAK | ||
478 | pgm_no_vtime: | 491 | pgm_no_vtime: |
479 | HANDLE_SIE_INTERCEPT | 492 | HANDLE_SIE_INTERCEPT |
480 | TRACE_IRQS_CHECK_OFF | 493 | TRACE_IRQS_CHECK_OFF |
481 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 494 | stg %r11,SP_ARGS(%r15) |
482 | mvc SP_ARGS(8,%r15),__LC_LAST_BREAK | ||
483 | lgf %r3,__LC_PGM_ILC # load program interruption code | 495 | lgf %r3,__LC_PGM_ILC # load program interruption code |
484 | lghi %r8,0x7f | 496 | lghi %r8,0x7f |
485 | ngr %r8,%r3 | 497 | ngr %r8,%r3 |
@@ -503,31 +515,32 @@ pgm_per: | |||
503 | clc __LC_PGM_OLD_PSW(16),__LC_SVC_NEW_PSW | 515 | clc __LC_PGM_OLD_PSW(16),__LC_SVC_NEW_PSW |
504 | je pgm_svcper | 516 | je pgm_svcper |
505 | # no interesting special case, ignore PER event | 517 | # no interesting special case, ignore PER event |
506 | lmg %r12,%r15,__LC_SAVE_AREA | ||
507 | lpswe __LC_PGM_OLD_PSW | 518 | lpswe __LC_PGM_OLD_PSW |
508 | 519 | ||
509 | # | 520 | # |
510 | # Normal per exception | 521 | # Normal per exception |
511 | # | 522 | # |
512 | pgm_per_std: | 523 | pgm_per_std: |
513 | SAVE_ALL_SYNC __LC_PGM_OLD_PSW,__LC_SAVE_AREA | 524 | SAVE_ALL_PGM __LC_PGM_OLD_PSW,__LC_SAVE_AREA |
514 | CREATE_STACK_FRAME __LC_PGM_OLD_PSW,__LC_SAVE_AREA | 525 | CREATE_STACK_FRAME __LC_SAVE_AREA |
526 | mvc SP_PSW(16,%r15),__LC_PGM_OLD_PSW | ||
527 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
515 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? | 528 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? |
516 | jz pgm_no_vtime2 | 529 | jz pgm_no_vtime2 |
517 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER | 530 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER |
518 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 531 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
519 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 532 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
533 | LAST_BREAK | ||
520 | pgm_no_vtime2: | 534 | pgm_no_vtime2: |
521 | HANDLE_SIE_INTERCEPT | 535 | HANDLE_SIE_INTERCEPT |
522 | TRACE_IRQS_CHECK_OFF | 536 | TRACE_IRQS_CHECK_OFF |
523 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 537 | lg %r1,__TI_task(%r12) |
524 | lg %r1,__TI_task(%r9) | ||
525 | tm SP_PSW+1(%r15),0x01 # kernel per event ? | 538 | tm SP_PSW+1(%r15),0x01 # kernel per event ? |
526 | jz kernel_per | 539 | jz kernel_per |
527 | mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID | 540 | mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID |
528 | mvc __THREAD_per+__PER_address(8,%r1),__LC_PER_ADDRESS | 541 | mvc __THREAD_per+__PER_address(8,%r1),__LC_PER_ADDRESS |
529 | mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID | 542 | mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID |
530 | oi __TI_flags+7(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP | 543 | oi __TI_flags+7(%r12),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP |
531 | lgf %r3,__LC_PGM_ILC # load program interruption code | 544 | lgf %r3,__LC_PGM_ILC # load program interruption code |
532 | lghi %r8,0x7f | 545 | lghi %r8,0x7f |
533 | ngr %r8,%r3 # clear per-event-bit and ilc | 546 | ngr %r8,%r3 # clear per-event-bit and ilc |
@@ -538,19 +551,21 @@ pgm_no_vtime2: | |||
538 | # it was a single stepped SVC that is causing all the trouble | 551 | # it was a single stepped SVC that is causing all the trouble |
539 | # | 552 | # |
540 | pgm_svcper: | 553 | pgm_svcper: |
541 | SAVE_ALL_SYNC __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 554 | SAVE_ALL_PGM __LC_SVC_OLD_PSW,__LC_SAVE_AREA |
542 | CREATE_STACK_FRAME __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 555 | CREATE_STACK_FRAME __LC_SAVE_AREA |
556 | mvc SP_PSW(16,%r15),__LC_SVC_OLD_PSW | ||
557 | mvc SP_ILC(4,%r15),__LC_SVC_ILC | ||
558 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
543 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER | 559 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_SYNC_ENTER_TIMER,__LC_USER_TIMER |
544 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 560 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
545 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 561 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
546 | llgh %r7,__LC_SVC_INT_CODE # get svc number from lowcore | 562 | LAST_BREAK |
547 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
548 | TRACE_IRQS_OFF | 563 | TRACE_IRQS_OFF |
549 | lg %r8,__TI_task(%r9) | 564 | lg %r8,__TI_task(%r12) |
550 | mvc __THREAD_per+__PER_atmid(2,%r8),__LC_PER_ATMID | 565 | mvc __THREAD_per+__PER_atmid(2,%r8),__LC_PER_ATMID |
551 | mvc __THREAD_per+__PER_address(8,%r8),__LC_PER_ADDRESS | 566 | mvc __THREAD_per+__PER_address(8,%r8),__LC_PER_ADDRESS |
552 | mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID | 567 | mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID |
553 | oi __TI_flags+7(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP | 568 | oi __TI_flags+7(%r12),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP |
554 | TRACE_IRQS_ON | 569 | TRACE_IRQS_ON |
555 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 570 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
556 | lmg %r2,%r6,SP_R2(%r15) # load svc arguments | 571 | lmg %r2,%r6,SP_R2(%r15) # load svc arguments |
@@ -572,16 +587,17 @@ kernel_per: | |||
572 | io_int_handler: | 587 | io_int_handler: |
573 | stck __LC_INT_CLOCK | 588 | stck __LC_INT_CLOCK |
574 | stpt __LC_ASYNC_ENTER_TIMER | 589 | stpt __LC_ASYNC_ENTER_TIMER |
575 | SAVE_ALL_BASE __LC_SAVE_AREA+32 | 590 | SAVE_ALL_ASYNC __LC_IO_OLD_PSW,__LC_SAVE_AREA+40 |
576 | SAVE_ALL_ASYNC __LC_IO_OLD_PSW,__LC_SAVE_AREA+32 | 591 | CREATE_STACK_FRAME __LC_SAVE_AREA+40 |
577 | CREATE_STACK_FRAME __LC_IO_OLD_PSW,__LC_SAVE_AREA+32 | 592 | mvc SP_PSW(16,%r15),0(%r12) # move user PSW to stack |
593 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
578 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? | 594 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? |
579 | jz io_no_vtime | 595 | jz io_no_vtime |
580 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_ASYNC_ENTER_TIMER,__LC_USER_TIMER | 596 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_ASYNC_ENTER_TIMER,__LC_USER_TIMER |
581 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 597 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
582 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER | 598 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER |
599 | LAST_BREAK | ||
583 | io_no_vtime: | 600 | io_no_vtime: |
584 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
585 | HANDLE_SIE_INTERCEPT | 601 | HANDLE_SIE_INTERCEPT |
586 | TRACE_IRQS_OFF | 602 | TRACE_IRQS_OFF |
587 | la %r2,SP_PTREGS(%r15) # address of register-save area | 603 | la %r2,SP_PTREGS(%r15) # address of register-save area |
@@ -590,7 +606,7 @@ io_return: | |||
590 | LOCKDEP_SYS_EXIT | 606 | LOCKDEP_SYS_EXIT |
591 | TRACE_IRQS_ON | 607 | TRACE_IRQS_ON |
592 | io_tif: | 608 | io_tif: |
593 | tm __TI_flags+7(%r9),_TIF_WORK_INT | 609 | tm __TI_flags+7(%r12),_TIF_WORK_INT |
594 | jnz io_work # there is work to do (signals etc.) | 610 | jnz io_work # there is work to do (signals etc.) |
595 | io_restore: | 611 | io_restore: |
596 | RESTORE_ALL __LC_RETURN_PSW,0 | 612 | RESTORE_ALL __LC_RETURN_PSW,0 |
@@ -610,7 +626,7 @@ io_work: | |||
610 | jo io_work_user # yes -> do resched & signal | 626 | jo io_work_user # yes -> do resched & signal |
611 | #ifdef CONFIG_PREEMPT | 627 | #ifdef CONFIG_PREEMPT |
612 | # check for preemptive scheduling | 628 | # check for preemptive scheduling |
613 | icm %r0,15,__TI_precount(%r9) | 629 | icm %r0,15,__TI_precount(%r12) |
614 | jnz io_restore # preemption is disabled | 630 | jnz io_restore # preemption is disabled |
615 | tm __TI_flags+7(%r12),_TIF_NEED_RESCHED | 631 | tm __TI_flags+7(%r12),_TIF_NEED_RESCHED |
616 | jno io_restore | 632 | jno io_restore |
@@ -645,13 +661,13 @@ io_work_user: | |||
645 | # and _TIF_MCCK_PENDING | 661 | # and _TIF_MCCK_PENDING |
646 | # | 662 | # |
647 | io_work_tif: | 663 | io_work_tif: |
648 | tm __TI_flags+7(%r9),_TIF_MCCK_PENDING | 664 | tm __TI_flags+7(%r12),_TIF_MCCK_PENDING |
649 | jo io_mcck_pending | 665 | jo io_mcck_pending |
650 | tm __TI_flags+7(%r9),_TIF_NEED_RESCHED | 666 | tm __TI_flags+7(%r12),_TIF_NEED_RESCHED |
651 | jo io_reschedule | 667 | jo io_reschedule |
652 | tm __TI_flags+7(%r9),_TIF_SIGPENDING | 668 | tm __TI_flags+7(%r12),_TIF_SIGPENDING |
653 | jo io_sigpending | 669 | jo io_sigpending |
654 | tm __TI_flags+7(%r9),_TIF_NOTIFY_RESUME | 670 | tm __TI_flags+7(%r12),_TIF_NOTIFY_RESUME |
655 | jo io_notify_resume | 671 | jo io_notify_resume |
656 | j io_return # beware of critical section cleanup | 672 | j io_return # beware of critical section cleanup |
657 | 673 | ||
@@ -706,16 +722,17 @@ io_notify_resume: | |||
706 | ext_int_handler: | 722 | ext_int_handler: |
707 | stck __LC_INT_CLOCK | 723 | stck __LC_INT_CLOCK |
708 | stpt __LC_ASYNC_ENTER_TIMER | 724 | stpt __LC_ASYNC_ENTER_TIMER |
709 | SAVE_ALL_BASE __LC_SAVE_AREA+32 | 725 | SAVE_ALL_ASYNC __LC_EXT_OLD_PSW,__LC_SAVE_AREA+40 |
710 | SAVE_ALL_ASYNC __LC_EXT_OLD_PSW,__LC_SAVE_AREA+32 | 726 | CREATE_STACK_FRAME __LC_SAVE_AREA+40 |
711 | CREATE_STACK_FRAME __LC_EXT_OLD_PSW,__LC_SAVE_AREA+32 | 727 | mvc SP_PSW(16,%r15),0(%r12) # move user PSW to stack |
728 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
712 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? | 729 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? |
713 | jz ext_no_vtime | 730 | jz ext_no_vtime |
714 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_ASYNC_ENTER_TIMER,__LC_USER_TIMER | 731 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_ASYNC_ENTER_TIMER,__LC_USER_TIMER |
715 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 732 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
716 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER | 733 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER |
734 | LAST_BREAK | ||
717 | ext_no_vtime: | 735 | ext_no_vtime: |
718 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
719 | HANDLE_SIE_INTERCEPT | 736 | HANDLE_SIE_INTERCEPT |
720 | TRACE_IRQS_OFF | 737 | TRACE_IRQS_OFF |
721 | la %r2,SP_PTREGS(%r15) # address of register-save area | 738 | la %r2,SP_PTREGS(%r15) # address of register-save area |
@@ -734,7 +751,9 @@ mcck_int_handler: | |||
734 | la %r1,4095 # revalidate r1 | 751 | la %r1,4095 # revalidate r1 |
735 | spt __LC_CPU_TIMER_SAVE_AREA-4095(%r1) # revalidate cpu timer | 752 | spt __LC_CPU_TIMER_SAVE_AREA-4095(%r1) # revalidate cpu timer |
736 | lmg %r0,%r15,__LC_GPREGS_SAVE_AREA-4095(%r1)# revalidate gprs | 753 | lmg %r0,%r15,__LC_GPREGS_SAVE_AREA-4095(%r1)# revalidate gprs |
737 | SAVE_ALL_BASE __LC_SAVE_AREA+64 | 754 | stmg %r11,%r15,__LC_SAVE_AREA+80 |
755 | larl %r13,system_call | ||
756 | lg %r11,__LC_LAST_BREAK | ||
738 | la %r12,__LC_MCK_OLD_PSW | 757 | la %r12,__LC_MCK_OLD_PSW |
739 | tm __LC_MCCK_CODE,0x80 # system damage? | 758 | tm __LC_MCCK_CODE,0x80 # system damage? |
740 | jo mcck_int_main # yes -> rest of mcck code invalid | 759 | jo mcck_int_main # yes -> rest of mcck code invalid |
@@ -769,7 +788,10 @@ mcck_int_main: | |||
769 | srag %r14,%r14,PAGE_SHIFT | 788 | srag %r14,%r14,PAGE_SHIFT |
770 | jz 0f | 789 | jz 0f |
771 | lg %r15,__LC_PANIC_STACK # load panic stack | 790 | lg %r15,__LC_PANIC_STACK # load panic stack |
772 | 0: CREATE_STACK_FRAME __LC_MCK_OLD_PSW,__LC_SAVE_AREA+64 | 791 | 0: aghi %r15,-SP_SIZE # make room for registers & psw |
792 | CREATE_STACK_FRAME __LC_SAVE_AREA+80 | ||
793 | mvc SP_PSW(16,%r15),0(%r12) | ||
794 | lg %r12,__LC_THREAD_INFO # load pointer to thread_info struct | ||
773 | tm __LC_MCCK_CODE+2,0x08 # mwp of old psw valid? | 795 | tm __LC_MCCK_CODE+2,0x08 # mwp of old psw valid? |
774 | jno mcck_no_vtime # no -> no timer update | 796 | jno mcck_no_vtime # no -> no timer update |
775 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? | 797 | tm SP_PSW+1(%r15),0x01 # interrupting from user ? |
@@ -777,8 +799,8 @@ mcck_int_main: | |||
777 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_MCCK_ENTER_TIMER,__LC_USER_TIMER | 799 | UPDATE_VTIME __LC_EXIT_TIMER,__LC_MCCK_ENTER_TIMER,__LC_USER_TIMER |
778 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 800 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
779 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_MCCK_ENTER_TIMER | 801 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_MCCK_ENTER_TIMER |
802 | LAST_BREAK | ||
780 | mcck_no_vtime: | 803 | mcck_no_vtime: |
781 | lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
782 | la %r2,SP_PTREGS(%r15) # load pt_regs | 804 | la %r2,SP_PTREGS(%r15) # load pt_regs |
783 | brasl %r14,s390_do_machine_check | 805 | brasl %r14,s390_do_machine_check |
784 | tm SP_PSW+1(%r15),0x01 # returning to user ? | 806 | tm SP_PSW+1(%r15),0x01 # returning to user ? |
@@ -789,7 +811,7 @@ mcck_no_vtime: | |||
789 | xc __SF_BACKCHAIN(8,%r1),__SF_BACKCHAIN(%r1) # clear back chain | 811 | xc __SF_BACKCHAIN(8,%r1),__SF_BACKCHAIN(%r1) # clear back chain |
790 | lgr %r15,%r1 | 812 | lgr %r15,%r1 |
791 | stosm __SF_EMPTY(%r15),0x04 # turn dat on | 813 | stosm __SF_EMPTY(%r15),0x04 # turn dat on |
792 | tm __TI_flags+7(%r9),_TIF_MCCK_PENDING | 814 | tm __TI_flags+7(%r12),_TIF_MCCK_PENDING |
793 | jno mcck_return | 815 | jno mcck_return |
794 | HANDLE_SIE_INTERCEPT | 816 | HANDLE_SIE_INTERCEPT |
795 | TRACE_IRQS_OFF | 817 | TRACE_IRQS_OFF |
@@ -803,6 +825,7 @@ mcck_return: | |||
803 | jno 0f | 825 | jno 0f |
804 | stpt __LC_EXIT_TIMER | 826 | stpt __LC_EXIT_TIMER |
805 | 0: lpswe __LC_RETURN_MCCK_PSW # back to caller | 827 | 0: lpswe __LC_RETURN_MCCK_PSW # back to caller |
828 | mcck_done: | ||
806 | 829 | ||
807 | /* | 830 | /* |
808 | * Restart interruption handler, kick starter for additional CPUs | 831 | * Restart interruption handler, kick starter for additional CPUs |
@@ -858,14 +881,14 @@ stack_overflow: | |||
858 | lg %r15,__LC_PANIC_STACK # change to panic stack | 881 | lg %r15,__LC_PANIC_STACK # change to panic stack |
859 | aghi %r15,-SP_SIZE | 882 | aghi %r15,-SP_SIZE |
860 | mvc SP_PSW(16,%r15),0(%r12) # move user PSW to stack | 883 | mvc SP_PSW(16,%r15),0(%r12) # move user PSW to stack |
861 | stmg %r0,%r11,SP_R0(%r15) # store gprs %r0-%r11 to kernel stack | 884 | stmg %r0,%r10,SP_R0(%r15) # store gprs %r0-%r10 to kernel stack |
862 | la %r1,__LC_SAVE_AREA | 885 | la %r1,__LC_SAVE_AREA |
863 | chi %r12,__LC_SVC_OLD_PSW | 886 | chi %r12,__LC_SVC_OLD_PSW |
864 | je 0f | 887 | je 0f |
865 | chi %r12,__LC_PGM_OLD_PSW | 888 | chi %r12,__LC_PGM_OLD_PSW |
866 | je 0f | 889 | je 0f |
867 | la %r1,__LC_SAVE_AREA+32 | 890 | la %r1,__LC_SAVE_AREA+40 |
868 | 0: mvc SP_R12(32,%r15),0(%r1) # move %r12-%r15 to stack | 891 | 0: mvc SP_R11(40,%r15),0(%r1) # move %r11-%r15 to stack |
869 | mvc SP_ARGS(8,%r15),__LC_LAST_BREAK | 892 | mvc SP_ARGS(8,%r15),__LC_LAST_BREAK |
870 | xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) # clear back chain | 893 | xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) # clear back chain |
871 | la %r2,SP_PTREGS(%r15) # load pt_regs | 894 | la %r2,SP_PTREGS(%r15) # load pt_regs |
@@ -920,21 +943,23 @@ cleanup_system_call: | |||
920 | je 0f | 943 | je 0f |
921 | mvc __LC_SYNC_ENTER_TIMER(8),__LC_ASYNC_ENTER_TIMER | 944 | mvc __LC_SYNC_ENTER_TIMER(8),__LC_ASYNC_ENTER_TIMER |
922 | 0: cghi %r12,__LC_MCK_OLD_PSW | 945 | 0: cghi %r12,__LC_MCK_OLD_PSW |
923 | la %r12,__LC_SAVE_AREA+64 | 946 | la %r12,__LC_SAVE_AREA+80 |
924 | je 0f | 947 | je 0f |
925 | la %r12,__LC_SAVE_AREA+32 | 948 | la %r12,__LC_SAVE_AREA+40 |
926 | 0: clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn+16) | 949 | 0: clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn+16) |
927 | jhe cleanup_vtime | 950 | jhe cleanup_vtime |
928 | clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn) | 951 | clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn) |
929 | jh 0f | 952 | jh 0f |
930 | mvc __LC_SAVE_AREA(32),0(%r12) | 953 | mvc __LC_SAVE_AREA(40),0(%r12) |
931 | 0: stg %r13,8(%r12) | 954 | 0: lg %r15,__LC_KERNEL_STACK # problem state -> load ksp |
932 | stg %r12,__LC_SAVE_AREA+96 # argh | 955 | aghi %r15,-SP_SIZE # make room for registers & psw |
933 | SAVE_ALL_SYNC __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 956 | stg %r15,32(%r12) |
934 | CREATE_STACK_FRAME __LC_SVC_OLD_PSW,__LC_SAVE_AREA | 957 | stg %r11,0(%r12) |
935 | lg %r12,__LC_SAVE_AREA+96 # argh | 958 | CREATE_STACK_FRAME __LC_SAVE_AREA |
936 | stg %r15,24(%r12) | 959 | mvc SP_PSW(16,%r15),__LC_SVC_OLD_PSW |
937 | llgh %r7,__LC_SVC_INT_CODE | 960 | mvc SP_ILC(4,%r15),__LC_SVC_ILC |
961 | stg %r7,SP_ARGS(%r15) | ||
962 | mvc 8(8,%r12),__LC_THREAD_INFO | ||
938 | cleanup_vtime: | 963 | cleanup_vtime: |
939 | clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn+24) | 964 | clc __LC_RETURN_PSW+8(8),BASED(cleanup_system_call_insn+24) |
940 | jhe cleanup_stime | 965 | jhe cleanup_stime |
@@ -945,7 +970,11 @@ cleanup_stime: | |||
945 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 970 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
946 | cleanup_update: | 971 | cleanup_update: |
947 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 972 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
948 | mvc __LC_RETURN_PSW+8(8),BASED(cleanup_table_system_call+8) | 973 | srag %r12,%r11,23 |
974 | lg %r12,__LC_THREAD_INFO | ||
975 | jz 0f | ||
976 | stg %r11,__TI_last_break(%r12) | ||
977 | 0: mvc __LC_RETURN_PSW+8(8),BASED(cleanup_table_system_call+8) | ||
949 | la %r12,__LC_RETURN_PSW | 978 | la %r12,__LC_RETURN_PSW |
950 | br %r14 | 979 | br %r14 |
951 | cleanup_system_call_insn: | 980 | cleanup_system_call_insn: |
@@ -972,11 +1001,11 @@ cleanup_sysc_restore: | |||
972 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER | 1001 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER |
973 | 0: mvc __LC_RETURN_PSW(16),SP_PSW(%r15) | 1002 | 0: mvc __LC_RETURN_PSW(16),SP_PSW(%r15) |
974 | cghi %r12,__LC_MCK_OLD_PSW | 1003 | cghi %r12,__LC_MCK_OLD_PSW |
975 | la %r12,__LC_SAVE_AREA+64 | 1004 | la %r12,__LC_SAVE_AREA+80 |
976 | je 1f | 1005 | je 1f |
977 | la %r12,__LC_SAVE_AREA+32 | 1006 | la %r12,__LC_SAVE_AREA+40 |
978 | 1: mvc 0(32,%r12),SP_R12(%r15) | 1007 | 1: mvc 0(40,%r12),SP_R11(%r15) |
979 | lmg %r0,%r11,SP_R0(%r15) | 1008 | lmg %r0,%r10,SP_R0(%r15) |
980 | lg %r15,SP_R15(%r15) | 1009 | lg %r15,SP_R15(%r15) |
981 | 2: la %r12,__LC_RETURN_PSW | 1010 | 2: la %r12,__LC_RETURN_PSW |
982 | br %r14 | 1011 | br %r14 |
@@ -997,8 +1026,8 @@ cleanup_io_restore: | |||
997 | jhe 0f | 1026 | jhe 0f |
998 | mvc __LC_EXIT_TIMER(8),__LC_MCCK_ENTER_TIMER | 1027 | mvc __LC_EXIT_TIMER(8),__LC_MCCK_ENTER_TIMER |
999 | 0: mvc __LC_RETURN_PSW(16),SP_PSW(%r15) | 1028 | 0: mvc __LC_RETURN_PSW(16),SP_PSW(%r15) |
1000 | mvc __LC_SAVE_AREA+64(32),SP_R12(%r15) | 1029 | mvc __LC_SAVE_AREA+80(40),SP_R11(%r15) |
1001 | lmg %r0,%r11,SP_R0(%r15) | 1030 | lmg %r0,%r10,SP_R0(%r15) |
1002 | lg %r15,SP_R15(%r15) | 1031 | lg %r15,SP_R15(%r15) |
1003 | 1: la %r12,__LC_RETURN_PSW | 1032 | 1: la %r12,__LC_RETURN_PSW |
1004 | br %r14 | 1033 | br %r14 |
@@ -1010,13 +1039,6 @@ cleanup_io_restore_insn: | |||
1010 | * Integer constants | 1039 | * Integer constants |
1011 | */ | 1040 | */ |
1012 | .align 4 | 1041 | .align 4 |
1013 | .Lconst: | ||
1014 | .Lnr_syscalls: .long NR_syscalls | ||
1015 | .L0x0130: .short 0x130 | ||
1016 | .L0x0140: .short 0x140 | ||
1017 | .L0x0150: .short 0x150 | ||
1018 | .L0x0160: .short 0x160 | ||
1019 | .L0x0170: .short 0x170 | ||
1020 | .Lcritical_start: | 1042 | .Lcritical_start: |
1021 | .quad __critical_start | 1043 | .quad __critical_start |
1022 | .Lcritical_end: | 1044 | .Lcritical_end: |