diff options
author | Martin Schwidefsky <schwidefsky@de.ibm.com> | 2010-05-17 04:00:02 -0400 |
---|---|---|
committer | Martin Schwidefsky <sky@mschwide.boeblingen.de.ibm.com> | 2010-05-17 04:00:15 -0400 |
commit | 6a2df3a87276cdc08fd87070d09ea18d1fb9d622 (patch) | |
tree | 384b646d0a826ab5c2bafa63e9bea4a057815fe2 /arch/s390/kernel/entry.S | |
parent | 43d399d2ab7e96cb8d952d0ba4e9131587b7c8b9 (diff) |
[S390] improve irq tracing code in entry[64].S
The system call path in entry[64].S is run with interrupts enabled.
Remove the irq tracing check from the system call exit code. If a
program check interrupted a context enabled for interrupts do a
call to trace_irq_off_caller in the program check handler before
branching to the system call exit code.
Restructure the system call and io interrupt return code to avoid
avoid the lpsw[e] to disable machine checks.
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'arch/s390/kernel/entry.S')
-rw-r--r-- | arch/s390/kernel/entry.S | 205 |
1 files changed, 91 insertions, 114 deletions
diff --git a/arch/s390/kernel/entry.S b/arch/s390/kernel/entry.S index ffebfb64b913..07d849995dac 100644 --- a/arch/s390/kernel/entry.S +++ b/arch/s390/kernel/entry.S | |||
@@ -73,21 +73,24 @@ STACK_SIZE = 1 << STACK_SHIFT | |||
73 | basr %r14,%r1 | 73 | basr %r14,%r1 |
74 | .endm | 74 | .endm |
75 | 75 | ||
76 | .macro TRACE_IRQS_CHECK | 76 | .macro TRACE_IRQS_CHECK_ON |
77 | basr %r2,%r0 | ||
78 | tm SP_PSW(%r15),0x03 # irqs enabled? | 77 | tm SP_PSW(%r15),0x03 # irqs enabled? |
79 | jz 0f | 78 | bz BASED(0f) |
80 | l %r1,BASED(.Ltrace_irq_on_caller) | 79 | TRACE_IRQS_ON |
81 | basr %r14,%r1 | 80 | 0: |
82 | j 1f | 81 | .endm |
83 | 0: l %r1,BASED(.Ltrace_irq_off_caller) | 82 | |
84 | basr %r14,%r1 | 83 | .macro TRACE_IRQS_CHECK_OFF |
85 | 1: | 84 | tm SP_PSW(%r15),0x03 # irqs enabled? |
85 | bz BASED(0f) | ||
86 | TRACE_IRQS_OFF | ||
87 | 0: | ||
86 | .endm | 88 | .endm |
87 | #else | 89 | #else |
88 | #define TRACE_IRQS_ON | 90 | #define TRACE_IRQS_ON |
89 | #define TRACE_IRQS_OFF | 91 | #define TRACE_IRQS_OFF |
90 | #define TRACE_IRQS_CHECK | 92 | #define TRACE_IRQS_CHECK_ON |
93 | #define TRACE_IRQS_CHECK_OFF | ||
91 | #endif | 94 | #endif |
92 | 95 | ||
93 | #ifdef CONFIG_LOCKDEP | 96 | #ifdef CONFIG_LOCKDEP |
@@ -273,33 +276,14 @@ sysc_do_restart: | |||
273 | st %r2,SP_R2(%r15) # store return value (change R2 on stack) | 276 | st %r2,SP_R2(%r15) # store return value (change R2 on stack) |
274 | 277 | ||
275 | sysc_return: | 278 | sysc_return: |
279 | LOCKDEP_SYS_EXIT | ||
280 | sysc_tif: | ||
276 | tm __TI_flags+3(%r9),_TIF_WORK_SVC | 281 | tm __TI_flags+3(%r9),_TIF_WORK_SVC |
277 | bnz BASED(sysc_work) # there is work to do (signals etc.) | 282 | bnz BASED(sysc_work) # there is work to do (signals etc.) |
278 | sysc_restore: | 283 | sysc_restore: |
279 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
280 | la %r1,BASED(sysc_restore_trace_psw_addr) | ||
281 | l %r1,0(%r1) | ||
282 | lpsw 0(%r1) | ||
283 | sysc_restore_trace: | ||
284 | TRACE_IRQS_CHECK | ||
285 | LOCKDEP_SYS_EXIT | ||
286 | #endif | ||
287 | sysc_leave: | ||
288 | RESTORE_ALL __LC_RETURN_PSW,1 | 284 | RESTORE_ALL __LC_RETURN_PSW,1 |
289 | sysc_done: | 285 | sysc_done: |
290 | 286 | ||
291 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
292 | sysc_restore_trace_psw_addr: | ||
293 | .long sysc_restore_trace_psw | ||
294 | |||
295 | .section .data,"aw",@progbits | ||
296 | .align 8 | ||
297 | .globl sysc_restore_trace_psw | ||
298 | sysc_restore_trace_psw: | ||
299 | .long 0, sysc_restore_trace + 0x80000000 | ||
300 | .previous | ||
301 | #endif | ||
302 | |||
303 | # | 287 | # |
304 | # There is work to do, but first we need to check if we return to userspace. | 288 | # There is work to do, but first we need to check if we return to userspace. |
305 | # | 289 | # |
@@ -310,7 +294,7 @@ sysc_work: | |||
310 | # | 294 | # |
311 | # One of the work bits is on. Find out which one. | 295 | # One of the work bits is on. Find out which one. |
312 | # | 296 | # |
313 | sysc_work_loop: | 297 | sysc_work_tif: |
314 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING | 298 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING |
315 | bo BASED(sysc_mcck_pending) | 299 | bo BASED(sysc_mcck_pending) |
316 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED | 300 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED |
@@ -330,7 +314,7 @@ sysc_work_loop: | |||
330 | # | 314 | # |
331 | sysc_reschedule: | 315 | sysc_reschedule: |
332 | l %r1,BASED(.Lschedule) | 316 | l %r1,BASED(.Lschedule) |
333 | la %r14,BASED(sysc_work_loop) | 317 | la %r14,BASED(sysc_return) |
334 | br %r1 # call scheduler | 318 | br %r1 # call scheduler |
335 | 319 | ||
336 | # | 320 | # |
@@ -338,7 +322,7 @@ sysc_reschedule: | |||
338 | # | 322 | # |
339 | sysc_mcck_pending: | 323 | sysc_mcck_pending: |
340 | l %r1,BASED(.Ls390_handle_mcck) | 324 | l %r1,BASED(.Ls390_handle_mcck) |
341 | la %r14,BASED(sysc_work_loop) | 325 | la %r14,BASED(sysc_return) |
342 | br %r1 # TIF bit will be cleared by handler | 326 | br %r1 # TIF bit will be cleared by handler |
343 | 327 | ||
344 | # | 328 | # |
@@ -353,7 +337,7 @@ sysc_sigpending: | |||
353 | bo BASED(sysc_restart) | 337 | bo BASED(sysc_restart) |
354 | tm __TI_flags+3(%r9),_TIF_SINGLE_STEP | 338 | tm __TI_flags+3(%r9),_TIF_SINGLE_STEP |
355 | bo BASED(sysc_singlestep) | 339 | bo BASED(sysc_singlestep) |
356 | b BASED(sysc_work_loop) | 340 | b BASED(sysc_return) |
357 | 341 | ||
358 | # | 342 | # |
359 | # _TIF_NOTIFY_RESUME is set, call do_notify_resume | 343 | # _TIF_NOTIFY_RESUME is set, call do_notify_resume |
@@ -361,7 +345,7 @@ sysc_sigpending: | |||
361 | sysc_notify_resume: | 345 | sysc_notify_resume: |
362 | la %r2,SP_PTREGS(%r15) # load pt_regs | 346 | la %r2,SP_PTREGS(%r15) # load pt_regs |
363 | l %r1,BASED(.Ldo_notify_resume) | 347 | l %r1,BASED(.Ldo_notify_resume) |
364 | la %r14,BASED(sysc_work_loop) | 348 | la %r14,BASED(sysc_return) |
365 | br %r1 # call do_notify_resume | 349 | br %r1 # call do_notify_resume |
366 | 350 | ||
367 | 351 | ||
@@ -384,7 +368,7 @@ sysc_singlestep: | |||
384 | mvi SP_SVCNR+1(%r15),0xff | 368 | mvi SP_SVCNR+1(%r15),0xff |
385 | la %r2,SP_PTREGS(%r15) # address of register-save area | 369 | la %r2,SP_PTREGS(%r15) # address of register-save area |
386 | l %r1,BASED(.Lhandle_per) # load adr. of per handler | 370 | l %r1,BASED(.Lhandle_per) # load adr. of per handler |
387 | la %r14,BASED(sysc_work_loop) # load adr. of system return | 371 | la %r14,BASED(sysc_return) # load adr. of system return |
388 | br %r1 # branch to do_single_step | 372 | br %r1 # branch to do_single_step |
389 | 373 | ||
390 | # | 374 | # |
@@ -456,11 +440,13 @@ kernel_execve: | |||
456 | br %r14 | 440 | br %r14 |
457 | # execve succeeded. | 441 | # execve succeeded. |
458 | 0: stnsm __SF_EMPTY(%r15),0xfc # disable interrupts | 442 | 0: stnsm __SF_EMPTY(%r15),0xfc # disable interrupts |
443 | TRACE_IRQS_OFF | ||
459 | l %r15,__LC_KERNEL_STACK # load ksp | 444 | l %r15,__LC_KERNEL_STACK # load ksp |
460 | s %r15,BASED(.Lc_spsize) # make room for registers & psw | 445 | s %r15,BASED(.Lc_spsize) # make room for registers & psw |
461 | l %r9,__LC_THREAD_INFO | 446 | l %r9,__LC_THREAD_INFO |
462 | mvc SP_PTREGS(__PT_SIZE,%r15),0(%r12) # copy pt_regs | 447 | mvc SP_PTREGS(__PT_SIZE,%r15),0(%r12) # copy pt_regs |
463 | xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) | 448 | xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) |
449 | TRACE_IRQS_ON | ||
464 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 450 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
465 | l %r1,BASED(.Lexecve_tail) | 451 | l %r1,BASED(.Lexecve_tail) |
466 | basr %r14,%r1 | 452 | basr %r14,%r1 |
@@ -497,8 +483,8 @@ pgm_check_handler: | |||
497 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 483 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
498 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 484 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
499 | pgm_no_vtime: | 485 | pgm_no_vtime: |
486 | TRACE_IRQS_CHECK_OFF | ||
500 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 487 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct |
501 | TRACE_IRQS_OFF | ||
502 | l %r3,__LC_PGM_ILC # load program interruption code | 488 | l %r3,__LC_PGM_ILC # load program interruption code |
503 | la %r8,0x7f | 489 | la %r8,0x7f |
504 | nr %r8,%r3 | 490 | nr %r8,%r3 |
@@ -507,8 +493,10 @@ pgm_do_call: | |||
507 | sll %r8,2 | 493 | sll %r8,2 |
508 | l %r7,0(%r8,%r7) # load address of handler routine | 494 | l %r7,0(%r8,%r7) # load address of handler routine |
509 | la %r2,SP_PTREGS(%r15) # address of register-save area | 495 | la %r2,SP_PTREGS(%r15) # address of register-save area |
510 | la %r14,BASED(sysc_return) | 496 | basr %r14,%r7 # branch to interrupt-handler |
511 | br %r7 # branch to interrupt-handler | 497 | pgm_exit: |
498 | TRACE_IRQS_CHECK_ON | ||
499 | b BASED(sysc_return) | ||
512 | 500 | ||
513 | # | 501 | # |
514 | # handle per exception | 502 | # handle per exception |
@@ -535,19 +523,19 @@ pgm_per_std: | |||
535 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 523 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
536 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER | 524 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER |
537 | pgm_no_vtime2: | 525 | pgm_no_vtime2: |
526 | TRACE_IRQS_CHECK_OFF | ||
538 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct | 527 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct |
539 | TRACE_IRQS_OFF | ||
540 | l %r1,__TI_task(%r9) | 528 | l %r1,__TI_task(%r9) |
529 | tm SP_PSW+1(%r15),0x01 # kernel per event ? | ||
530 | bz BASED(kernel_per) | ||
541 | mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID | 531 | mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID |
542 | mvc __THREAD_per+__PER_address(4,%r1),__LC_PER_ADDRESS | 532 | mvc __THREAD_per+__PER_address(4,%r1),__LC_PER_ADDRESS |
543 | mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID | 533 | mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID |
544 | oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP | 534 | oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP |
545 | tm SP_PSW+1(%r15),0x01 # kernel per event ? | ||
546 | bz BASED(kernel_per) | ||
547 | l %r3,__LC_PGM_ILC # load program interruption code | 535 | l %r3,__LC_PGM_ILC # load program interruption code |
548 | la %r8,0x7f | 536 | la %r8,0x7f |
549 | nr %r8,%r3 # clear per-event-bit and ilc | 537 | nr %r8,%r3 # clear per-event-bit and ilc |
550 | be BASED(sysc_return) # only per or per+check ? | 538 | be BASED(pgm_exit) # only per or per+check ? |
551 | b BASED(pgm_do_call) | 539 | b BASED(pgm_do_call) |
552 | 540 | ||
553 | # | 541 | # |
@@ -568,8 +556,8 @@ pgm_svcper: | |||
568 | mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID | 556 | mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID |
569 | oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP | 557 | oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP |
570 | TRACE_IRQS_ON | 558 | TRACE_IRQS_ON |
571 | lm %r2,%r6,SP_R2(%r15) # load svc arguments | ||
572 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 559 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
560 | lm %r2,%r6,SP_R2(%r15) # load svc arguments | ||
573 | b BASED(sysc_do_svc) | 561 | b BASED(sysc_do_svc) |
574 | 562 | ||
575 | # | 563 | # |
@@ -580,8 +568,8 @@ kernel_per: | |||
580 | mvi SP_SVCNR+1(%r15),0xff | 568 | mvi SP_SVCNR+1(%r15),0xff |
581 | la %r2,SP_PTREGS(%r15) # address of register-save area | 569 | la %r2,SP_PTREGS(%r15) # address of register-save area |
582 | l %r1,BASED(.Lhandle_per) # load adr. of per handler | 570 | l %r1,BASED(.Lhandle_per) # load adr. of per handler |
583 | la %r14,BASED(sysc_restore)# load adr. of system return | 571 | basr %r14,%r1 # branch to do_single_step |
584 | br %r1 # branch to do_single_step | 572 | b BASED(pgm_exit) |
585 | 573 | ||
586 | /* | 574 | /* |
587 | * IO interrupt handler routine | 575 | * IO interrupt handler routine |
@@ -600,39 +588,21 @@ io_int_handler: | |||
600 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER | 588 | UPDATE_VTIME __LC_LAST_UPDATE_TIMER,__LC_EXIT_TIMER,__LC_SYSTEM_TIMER |
601 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER | 589 | mvc __LC_LAST_UPDATE_TIMER(8),__LC_ASYNC_ENTER_TIMER |
602 | io_no_vtime: | 590 | io_no_vtime: |
603 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
604 | TRACE_IRQS_OFF | 591 | TRACE_IRQS_OFF |
592 | l %r9,__LC_THREAD_INFO # load pointer to thread_info struct | ||
605 | l %r1,BASED(.Ldo_IRQ) # load address of do_IRQ | 593 | l %r1,BASED(.Ldo_IRQ) # load address of do_IRQ |
606 | la %r2,SP_PTREGS(%r15) # address of register-save area | 594 | la %r2,SP_PTREGS(%r15) # address of register-save area |
607 | basr %r14,%r1 # branch to standard irq handler | 595 | basr %r14,%r1 # branch to standard irq handler |
608 | io_return: | 596 | io_return: |
597 | LOCKDEP_SYS_EXIT | ||
598 | TRACE_IRQS_ON | ||
599 | io_tif: | ||
609 | tm __TI_flags+3(%r9),_TIF_WORK_INT | 600 | tm __TI_flags+3(%r9),_TIF_WORK_INT |
610 | bnz BASED(io_work) # there is work to do (signals etc.) | 601 | bnz BASED(io_work) # there is work to do (signals etc.) |
611 | io_restore: | 602 | io_restore: |
612 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
613 | la %r1,BASED(io_restore_trace_psw_addr) | ||
614 | l %r1,0(%r1) | ||
615 | lpsw 0(%r1) | ||
616 | io_restore_trace: | ||
617 | TRACE_IRQS_CHECK | ||
618 | LOCKDEP_SYS_EXIT | ||
619 | #endif | ||
620 | io_leave: | ||
621 | RESTORE_ALL __LC_RETURN_PSW,0 | 603 | RESTORE_ALL __LC_RETURN_PSW,0 |
622 | io_done: | 604 | io_done: |
623 | 605 | ||
624 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
625 | io_restore_trace_psw_addr: | ||
626 | .long io_restore_trace_psw | ||
627 | |||
628 | .section .data,"aw",@progbits | ||
629 | .align 8 | ||
630 | .globl io_restore_trace_psw | ||
631 | io_restore_trace_psw: | ||
632 | .long 0, io_restore_trace + 0x80000000 | ||
633 | .previous | ||
634 | #endif | ||
635 | |||
636 | # | 606 | # |
637 | # There is work todo, find out in which context we have been interrupted: | 607 | # There is work todo, find out in which context we have been interrupted: |
638 | # 1) if we return to user space we can do all _TIF_WORK_INT work | 608 | # 1) if we return to user space we can do all _TIF_WORK_INT work |
@@ -647,19 +617,23 @@ io_work: | |||
647 | # check for preemptive scheduling | 617 | # check for preemptive scheduling |
648 | icm %r0,15,__TI_precount(%r9) | 618 | icm %r0,15,__TI_precount(%r9) |
649 | bnz BASED(io_restore) # preemption disabled | 619 | bnz BASED(io_restore) # preemption disabled |
620 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED | ||
621 | bno BASED(io_restore) | ||
650 | # switch to kernel stack | 622 | # switch to kernel stack |
651 | l %r1,SP_R15(%r15) | 623 | l %r1,SP_R15(%r15) |
652 | s %r1,BASED(.Lc_spsize) | 624 | s %r1,BASED(.Lc_spsize) |
653 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) | 625 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) |
654 | xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) # clear back chain | 626 | xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) # clear back chain |
655 | lr %r15,%r1 | 627 | lr %r15,%r1 |
656 | io_resume_loop: | 628 | # TRACE_IRQS_ON already done at io_return, call |
629 | # TRACE_IRQS_OFF to keep things symmetrical | ||
630 | TRACE_IRQS_OFF | ||
657 | l %r1,BASED(.Lpreempt_schedule_irq) | 631 | l %r1,BASED(.Lpreempt_schedule_irq) |
658 | la %r14,BASED(io_resume_loop) | 632 | basr %r14,%r1 # call preempt_schedule_irq |
659 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED | 633 | b BASED(io_return) |
660 | bor %r1 # call preempt_schedule_irq | 634 | #else |
661 | #endif | ||
662 | b BASED(io_restore) | 635 | b BASED(io_restore) |
636 | #endif | ||
663 | 637 | ||
664 | # | 638 | # |
665 | # Need to do work before returning to userspace, switch to kernel stack | 639 | # Need to do work before returning to userspace, switch to kernel stack |
@@ -670,12 +644,13 @@ io_work_user: | |||
670 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) | 644 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) |
671 | xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) # clear back chain | 645 | xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) # clear back chain |
672 | lr %r15,%r1 | 646 | lr %r15,%r1 |
647 | |||
673 | # | 648 | # |
674 | # One of the work bits is on. Find out which one. | 649 | # One of the work bits is on. Find out which one. |
675 | # Checked are: _TIF_SIGPENDING, _TIF_NOTIFY_RESUME, _TIF_NEED_RESCHED | 650 | # Checked are: _TIF_SIGPENDING, _TIF_NOTIFY_RESUME, _TIF_NEED_RESCHED |
676 | # and _TIF_MCCK_PENDING | 651 | # and _TIF_MCCK_PENDING |
677 | # | 652 | # |
678 | io_work_loop: | 653 | io_work_tif: |
679 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING | 654 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING |
680 | bo BASED(io_mcck_pending) | 655 | bo BASED(io_mcck_pending) |
681 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED | 656 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED |
@@ -690,47 +665,49 @@ io_work_loop: | |||
690 | # _TIF_MCCK_PENDING is set, call handler | 665 | # _TIF_MCCK_PENDING is set, call handler |
691 | # | 666 | # |
692 | io_mcck_pending: | 667 | io_mcck_pending: |
668 | # TRACE_IRQS_ON already done at io_return | ||
693 | l %r1,BASED(.Ls390_handle_mcck) | 669 | l %r1,BASED(.Ls390_handle_mcck) |
694 | basr %r14,%r1 # TIF bit will be cleared by handler | 670 | basr %r14,%r1 # TIF bit will be cleared by handler |
695 | b BASED(io_work_loop) | 671 | TRACE_IRQS_OFF |
672 | b BASED(io_return) | ||
696 | 673 | ||
697 | # | 674 | # |
698 | # _TIF_NEED_RESCHED is set, call schedule | 675 | # _TIF_NEED_RESCHED is set, call schedule |
699 | # | 676 | # |
700 | io_reschedule: | 677 | io_reschedule: |
701 | TRACE_IRQS_ON | 678 | # TRACE_IRQS_ON already done at io_return |
702 | l %r1,BASED(.Lschedule) | 679 | l %r1,BASED(.Lschedule) |
703 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 680 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
704 | basr %r14,%r1 # call scheduler | 681 | basr %r14,%r1 # call scheduler |
705 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts | 682 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts |
706 | TRACE_IRQS_OFF | 683 | TRACE_IRQS_OFF |
707 | b BASED(io_work_loop) | 684 | b BASED(io_return) |
708 | 685 | ||
709 | # | 686 | # |
710 | # _TIF_SIGPENDING is set, call do_signal | 687 | # _TIF_SIGPENDING is set, call do_signal |
711 | # | 688 | # |
712 | io_sigpending: | 689 | io_sigpending: |
713 | TRACE_IRQS_ON | 690 | # TRACE_IRQS_ON already done at io_return |
714 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 691 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
715 | la %r2,SP_PTREGS(%r15) # load pt_regs | 692 | la %r2,SP_PTREGS(%r15) # load pt_regs |
716 | l %r1,BASED(.Ldo_signal) | 693 | l %r1,BASED(.Ldo_signal) |
717 | basr %r14,%r1 # call do_signal | 694 | basr %r14,%r1 # call do_signal |
718 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts | 695 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts |
719 | TRACE_IRQS_OFF | 696 | TRACE_IRQS_OFF |
720 | b BASED(io_work_loop) | 697 | b BASED(io_return) |
721 | 698 | ||
722 | # | 699 | # |
723 | # _TIF_SIGPENDING is set, call do_signal | 700 | # _TIF_SIGPENDING is set, call do_signal |
724 | # | 701 | # |
725 | io_notify_resume: | 702 | io_notify_resume: |
726 | TRACE_IRQS_ON | 703 | # TRACE_IRQS_ON already done at io_return |
727 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts | 704 | stosm __SF_EMPTY(%r15),0x03 # reenable interrupts |
728 | la %r2,SP_PTREGS(%r15) # load pt_regs | 705 | la %r2,SP_PTREGS(%r15) # load pt_regs |
729 | l %r1,BASED(.Ldo_notify_resume) | 706 | l %r1,BASED(.Ldo_notify_resume) |
730 | basr %r14,%r1 # call do_signal | 707 | basr %r14,%r1 # call do_signal |
731 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts | 708 | stnsm __SF_EMPTY(%r15),0xfc # disable I/O and ext. interrupts |
732 | TRACE_IRQS_OFF | 709 | TRACE_IRQS_OFF |
733 | b BASED(io_work_loop) | 710 | b BASED(io_return) |
734 | 711 | ||
735 | /* | 712 | /* |
736 | * External interrupt handler routine | 713 | * External interrupt handler routine |
@@ -918,14 +895,14 @@ stack_overflow: | |||
918 | 895 | ||
919 | cleanup_table_system_call: | 896 | cleanup_table_system_call: |
920 | .long system_call + 0x80000000, sysc_do_svc + 0x80000000 | 897 | .long system_call + 0x80000000, sysc_do_svc + 0x80000000 |
921 | cleanup_table_sysc_return: | 898 | cleanup_table_sysc_tif: |
922 | .long sysc_return + 0x80000000, sysc_leave + 0x80000000 | 899 | .long sysc_tif + 0x80000000, sysc_restore + 0x80000000 |
923 | cleanup_table_sysc_leave: | 900 | cleanup_table_sysc_restore: |
924 | .long sysc_leave + 0x80000000, sysc_done + 0x80000000 | 901 | .long sysc_restore + 0x80000000, sysc_done + 0x80000000 |
925 | cleanup_table_io_return: | 902 | cleanup_table_io_tif: |
926 | .long io_return + 0x80000000, io_leave + 0x80000000 | 903 | .long io_tif + 0x80000000, io_restore + 0x80000000 |
927 | cleanup_table_io_leave: | 904 | cleanup_table_io_restore: |
928 | .long io_leave + 0x80000000, io_done + 0x80000000 | 905 | .long io_restore + 0x80000000, io_done + 0x80000000 |
929 | 906 | ||
930 | cleanup_critical: | 907 | cleanup_critical: |
931 | clc 4(4,%r12),BASED(cleanup_table_system_call) | 908 | clc 4(4,%r12),BASED(cleanup_table_system_call) |
@@ -933,25 +910,25 @@ cleanup_critical: | |||
933 | clc 4(4,%r12),BASED(cleanup_table_system_call+4) | 910 | clc 4(4,%r12),BASED(cleanup_table_system_call+4) |
934 | bl BASED(cleanup_system_call) | 911 | bl BASED(cleanup_system_call) |
935 | 0: | 912 | 0: |
936 | clc 4(4,%r12),BASED(cleanup_table_sysc_return) | 913 | clc 4(4,%r12),BASED(cleanup_table_sysc_tif) |
937 | bl BASED(0f) | 914 | bl BASED(0f) |
938 | clc 4(4,%r12),BASED(cleanup_table_sysc_return+4) | 915 | clc 4(4,%r12),BASED(cleanup_table_sysc_tif+4) |
939 | bl BASED(cleanup_sysc_return) | 916 | bl BASED(cleanup_sysc_tif) |
940 | 0: | 917 | 0: |
941 | clc 4(4,%r12),BASED(cleanup_table_sysc_leave) | 918 | clc 4(4,%r12),BASED(cleanup_table_sysc_restore) |
942 | bl BASED(0f) | 919 | bl BASED(0f) |
943 | clc 4(4,%r12),BASED(cleanup_table_sysc_leave+4) | 920 | clc 4(4,%r12),BASED(cleanup_table_sysc_restore+4) |
944 | bl BASED(cleanup_sysc_leave) | 921 | bl BASED(cleanup_sysc_restore) |
945 | 0: | 922 | 0: |
946 | clc 4(4,%r12),BASED(cleanup_table_io_return) | 923 | clc 4(4,%r12),BASED(cleanup_table_io_tif) |
947 | bl BASED(0f) | 924 | bl BASED(0f) |
948 | clc 4(4,%r12),BASED(cleanup_table_io_return+4) | 925 | clc 4(4,%r12),BASED(cleanup_table_io_tif+4) |
949 | bl BASED(cleanup_io_return) | 926 | bl BASED(cleanup_io_tif) |
950 | 0: | 927 | 0: |
951 | clc 4(4,%r12),BASED(cleanup_table_io_leave) | 928 | clc 4(4,%r12),BASED(cleanup_table_io_restore) |
952 | bl BASED(0f) | 929 | bl BASED(0f) |
953 | clc 4(4,%r12),BASED(cleanup_table_io_leave+4) | 930 | clc 4(4,%r12),BASED(cleanup_table_io_restore+4) |
954 | bl BASED(cleanup_io_leave) | 931 | bl BASED(cleanup_io_restore) |
955 | 0: | 932 | 0: |
956 | br %r14 | 933 | br %r14 |
957 | 934 | ||
@@ -998,17 +975,17 @@ cleanup_system_call_insn: | |||
998 | .long sysc_stime + 0x80000000 | 975 | .long sysc_stime + 0x80000000 |
999 | .long sysc_update + 0x80000000 | 976 | .long sysc_update + 0x80000000 |
1000 | 977 | ||
1001 | cleanup_sysc_return: | 978 | cleanup_sysc_tif: |
1002 | mvc __LC_RETURN_PSW(4),0(%r12) | 979 | mvc __LC_RETURN_PSW(4),0(%r12) |
1003 | mvc __LC_RETURN_PSW+4(4),BASED(cleanup_table_sysc_return) | 980 | mvc __LC_RETURN_PSW+4(4),BASED(cleanup_table_sysc_tif) |
1004 | la %r12,__LC_RETURN_PSW | 981 | la %r12,__LC_RETURN_PSW |
1005 | br %r14 | 982 | br %r14 |
1006 | 983 | ||
1007 | cleanup_sysc_leave: | 984 | cleanup_sysc_restore: |
1008 | clc 4(4,%r12),BASED(cleanup_sysc_leave_insn) | 985 | clc 4(4,%r12),BASED(cleanup_sysc_restore_insn) |
1009 | be BASED(2f) | 986 | be BASED(2f) |
1010 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER | 987 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER |
1011 | clc 4(4,%r12),BASED(cleanup_sysc_leave_insn+4) | 988 | clc 4(4,%r12),BASED(cleanup_sysc_restore_insn+4) |
1012 | be BASED(2f) | 989 | be BASED(2f) |
1013 | mvc __LC_RETURN_PSW(8),SP_PSW(%r15) | 990 | mvc __LC_RETURN_PSW(8),SP_PSW(%r15) |
1014 | c %r12,BASED(.Lmck_old_psw) | 991 | c %r12,BASED(.Lmck_old_psw) |
@@ -1020,21 +997,21 @@ cleanup_sysc_leave: | |||
1020 | l %r15,SP_R15(%r15) | 997 | l %r15,SP_R15(%r15) |
1021 | 2: la %r12,__LC_RETURN_PSW | 998 | 2: la %r12,__LC_RETURN_PSW |
1022 | br %r14 | 999 | br %r14 |
1023 | cleanup_sysc_leave_insn: | 1000 | cleanup_sysc_restore_insn: |
1024 | .long sysc_done - 4 + 0x80000000 | 1001 | .long sysc_done - 4 + 0x80000000 |
1025 | .long sysc_done - 8 + 0x80000000 | 1002 | .long sysc_done - 8 + 0x80000000 |
1026 | 1003 | ||
1027 | cleanup_io_return: | 1004 | cleanup_io_tif: |
1028 | mvc __LC_RETURN_PSW(4),0(%r12) | 1005 | mvc __LC_RETURN_PSW(4),0(%r12) |
1029 | mvc __LC_RETURN_PSW+4(4),BASED(cleanup_table_io_return) | 1006 | mvc __LC_RETURN_PSW+4(4),BASED(cleanup_table_io_tif) |
1030 | la %r12,__LC_RETURN_PSW | 1007 | la %r12,__LC_RETURN_PSW |
1031 | br %r14 | 1008 | br %r14 |
1032 | 1009 | ||
1033 | cleanup_io_leave: | 1010 | cleanup_io_restore: |
1034 | clc 4(4,%r12),BASED(cleanup_io_leave_insn) | 1011 | clc 4(4,%r12),BASED(cleanup_io_restore_insn) |
1035 | be BASED(2f) | 1012 | be BASED(2f) |
1036 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER | 1013 | mvc __LC_EXIT_TIMER(8),__LC_ASYNC_ENTER_TIMER |
1037 | clc 4(4,%r12),BASED(cleanup_io_leave_insn+4) | 1014 | clc 4(4,%r12),BASED(cleanup_io_restore_insn+4) |
1038 | be BASED(2f) | 1015 | be BASED(2f) |
1039 | mvc __LC_RETURN_PSW(8),SP_PSW(%r15) | 1016 | mvc __LC_RETURN_PSW(8),SP_PSW(%r15) |
1040 | c %r12,BASED(.Lmck_old_psw) | 1017 | c %r12,BASED(.Lmck_old_psw) |
@@ -1046,7 +1023,7 @@ cleanup_io_leave: | |||
1046 | l %r15,SP_R15(%r15) | 1023 | l %r15,SP_R15(%r15) |
1047 | 2: la %r12,__LC_RETURN_PSW | 1024 | 2: la %r12,__LC_RETURN_PSW |
1048 | br %r14 | 1025 | br %r14 |
1049 | cleanup_io_leave_insn: | 1026 | cleanup_io_restore_insn: |
1050 | .long io_done - 4 + 0x80000000 | 1027 | .long io_done - 4 + 0x80000000 |
1051 | .long io_done - 8 + 0x80000000 | 1028 | .long io_done - 8 + 0x80000000 |
1052 | 1029 | ||