diff --git a/arch/alpha/kernel/entry.S b/arch/alpha/kernel/entry.S index 802108b15be83b67424f22acec13f7c2c55ce322..0c30ccea9294000e74b56b75d6aa1c0ae4064b83 100644 --- a/arch/alpha/kernel/entry.S +++ b/arch/alpha/kernel/entry.S @@ -390,15 +390,9 @@ $work_notifysig: bsr $1, do_switch_stack mov $sp, $17 mov $5, $18 - mov $19, $9 /* save old syscall number */ - mov $20, $10 /* save old a3 */ - and $5, _TIF_SIGPENDING, $2 - cmovne $2, 0, $9 /* we don't want double syscall restarts */ - jsr $26, do_notify_resume - mov $9, $19 - mov $10, $20 + jsr $26, do_work_pending bsr $1, undo_switch_stack - br ret_to_user + br restore_all .end work_pending /* diff --git a/arch/alpha/kernel/signal.c b/arch/alpha/kernel/signal.c index a8c97d42ec8eaef9215c32a40f743bd94505bc55..235a8677eca8d7e2f855ae8e71678c9a3135ee99 100644 --- a/arch/alpha/kernel/signal.c +++ b/arch/alpha/kernel/signal.c @@ -568,15 +568,24 @@ do_signal(struct pt_regs * regs, struct switch_stack * sw, } void -do_notify_resume(struct pt_regs *regs, struct switch_stack *sw, - unsigned long thread_info_flags, +do_work_pending(struct pt_regs *regs, struct switch_stack *sw, + unsigned long thread_flags, unsigned long r0, unsigned long r19) { - if (thread_info_flags & _TIF_SIGPENDING) - do_signal(regs, sw, r0, r19); - - if (thread_info_flags & _TIF_NOTIFY_RESUME) { - clear_thread_flag(TIF_NOTIFY_RESUME); - tracehook_notify_resume(regs); - } + do { + if (thread_flags & _TIF_NEED_RESCHED) { + schedule(); + } else { + local_irq_enable(); + if (thread_flags & _TIF_SIGPENDING) { + do_signal(regs, sw, r0, r19); + r0 = 0; + } else { + clear_thread_flag(TIF_NOTIFY_RESUME); + tracehook_notify_resume(regs); + } + } + local_irq_disable(); + thread_flags = current_thread_info()->flags; + } while (thread_flags & _TIF_WORK_MASK); }