blob: 5c6170c44b008bc49b5882e73cae206df930c878 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
Linus Torvalds1da177e2005-04-16 15:20:36 -07002 * Copyright (C) 1991, 1992 Linus Torvalds
3 *
4 * 1997-11-28 Modified for POSIX.1b signals by Richard Henderson
5 * 2000-06-20 Pentium III FXSR, SSE support by Gareth Hughes
6 */
7
8#include <linux/sched.h>
9#include <linux/mm.h>
10#include <linux/smp.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070011#include <linux/kernel.h>
12#include <linux/signal.h>
13#include <linux/errno.h>
14#include <linux/wait.h>
15#include <linux/unistd.h>
16#include <linux/stddef.h>
17#include <linux/personality.h>
18#include <linux/suspend.h>
19#include <linux/ptrace.h>
20#include <linux/elf.h>
Andi Kleen9fbbd4d2007-02-13 13:26:26 +010021#include <linux/binfmts.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070022#include <asm/processor.h>
23#include <asm/ucontext.h>
24#include <asm/uaccess.h>
25#include <asm/i387.h>
Thomas Gleixner56cc6232007-10-11 11:12:46 +020026#include "sigframe_32.h"
Linus Torvalds1da177e2005-04-16 15:20:36 -070027
28#define DEBUG_SIG 0
29
30#define _BLOCKABLE (~(sigmask(SIGKILL) | sigmask(SIGSTOP)))
31
32/*
33 * Atomically swap in the new signal mask, and wait for a signal.
34 */
35asmlinkage int
36sys_sigsuspend(int history0, int history1, old_sigset_t mask)
37{
Linus Torvalds1da177e2005-04-16 15:20:36 -070038 mask &= _BLOCKABLE;
39 spin_lock_irq(&current->sighand->siglock);
David Howells283828f2006-01-18 17:44:00 -080040 current->saved_sigmask = current->blocked;
Linus Torvalds1da177e2005-04-16 15:20:36 -070041 siginitset(&current->blocked, mask);
42 recalc_sigpending();
43 spin_unlock_irq(&current->sighand->siglock);
44
David Howells283828f2006-01-18 17:44:00 -080045 current->state = TASK_INTERRUPTIBLE;
46 schedule();
47 set_thread_flag(TIF_RESTORE_SIGMASK);
48 return -ERESTARTNOHAND;
Linus Torvalds1da177e2005-04-16 15:20:36 -070049}
50
51asmlinkage int
52sys_sigaction(int sig, const struct old_sigaction __user *act,
53 struct old_sigaction __user *oact)
54{
55 struct k_sigaction new_ka, old_ka;
56 int ret;
57
58 if (act) {
59 old_sigset_t mask;
60 if (!access_ok(VERIFY_READ, act, sizeof(*act)) ||
61 __get_user(new_ka.sa.sa_handler, &act->sa_handler) ||
62 __get_user(new_ka.sa.sa_restorer, &act->sa_restorer))
63 return -EFAULT;
64 __get_user(new_ka.sa.sa_flags, &act->sa_flags);
65 __get_user(mask, &act->sa_mask);
66 siginitset(&new_ka.sa.sa_mask, mask);
67 }
68
69 ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL);
70
71 if (!ret && oact) {
72 if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) ||
73 __put_user(old_ka.sa.sa_handler, &oact->sa_handler) ||
74 __put_user(old_ka.sa.sa_restorer, &oact->sa_restorer))
75 return -EFAULT;
76 __put_user(old_ka.sa.sa_flags, &oact->sa_flags);
77 __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask);
78 }
79
80 return ret;
81}
82
83asmlinkage int
84sys_sigaltstack(unsigned long ebx)
85{
86 /* This is needed to make gcc realize it doesn't own the "struct pt_regs" */
87 struct pt_regs *regs = (struct pt_regs *)&ebx;
88 const stack_t __user *uss = (const stack_t __user *)ebx;
89 stack_t __user *uoss = (stack_t __user *)regs->ecx;
90
91 return do_sigaltstack(uss, uoss, regs->esp);
92}
93
94
95/*
96 * Do a signal return; undo the signal stack.
97 */
98
99static int
100restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc, int *peax)
101{
102 unsigned int err = 0;
103
104 /* Always make any pending restarted system calls return -EINTR */
105 current_thread_info()->restart_block.fn = do_no_restart_syscall;
106
107#define COPY(x) err |= __get_user(regs->x, &sc->x)
108
109#define COPY_SEG(seg) \
110 { unsigned short tmp; \
111 err |= __get_user(tmp, &sc->seg); \
112 regs->x##seg = tmp; }
113
114#define COPY_SEG_STRICT(seg) \
115 { unsigned short tmp; \
116 err |= __get_user(tmp, &sc->seg); \
117 regs->x##seg = tmp|3; }
118
119#define GET_SEG(seg) \
120 { unsigned short tmp; \
121 err |= __get_user(tmp, &sc->seg); \
122 loadsegment(seg,tmp); }
123
Chuck Ebbert8bed51c2006-03-23 02:59:40 -0800124#define FIX_EFLAGS (X86_EFLAGS_AC | X86_EFLAGS_RF | \
125 X86_EFLAGS_OF | X86_EFLAGS_DF | \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700126 X86_EFLAGS_TF | X86_EFLAGS_SF | X86_EFLAGS_ZF | \
127 X86_EFLAGS_AF | X86_EFLAGS_PF | X86_EFLAGS_CF)
128
Jeremy Fitzhardinge464d1a72007-02-13 13:26:20 +0100129 GET_SEG(gs);
130 COPY_SEG(fs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700131 COPY_SEG(es);
132 COPY_SEG(ds);
133 COPY(edi);
134 COPY(esi);
135 COPY(ebp);
136 COPY(esp);
137 COPY(ebx);
138 COPY(edx);
139 COPY(ecx);
140 COPY(eip);
141 COPY_SEG_STRICT(cs);
142 COPY_SEG_STRICT(ss);
143
144 {
145 unsigned int tmpflags;
146 err |= __get_user(tmpflags, &sc->eflags);
147 regs->eflags = (regs->eflags & ~FIX_EFLAGS) | (tmpflags & FIX_EFLAGS);
148 regs->orig_eax = -1; /* disable syscall checks */
149 }
150
151 {
152 struct _fpstate __user * buf;
153 err |= __get_user(buf, &sc->fpstate);
154 if (buf) {
155 if (!access_ok(VERIFY_READ, buf, sizeof(*buf)))
156 goto badframe;
157 err |= restore_i387(buf);
158 } else {
159 struct task_struct *me = current;
160 if (used_math()) {
161 clear_fpu(me);
162 clear_used_math();
163 }
164 }
165 }
166
167 err |= __get_user(*peax, &sc->eax);
168 return err;
169
170badframe:
171 return 1;
172}
173
174asmlinkage int sys_sigreturn(unsigned long __unused)
175{
176 struct pt_regs *regs = (struct pt_regs *) &__unused;
177 struct sigframe __user *frame = (struct sigframe __user *)(regs->esp - 8);
178 sigset_t set;
179 int eax;
180
181 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
182 goto badframe;
183 if (__get_user(set.sig[0], &frame->sc.oldmask)
184 || (_NSIG_WORDS > 1
185 && __copy_from_user(&set.sig[1], &frame->extramask,
186 sizeof(frame->extramask))))
187 goto badframe;
188
189 sigdelsetmask(&set, ~_BLOCKABLE);
190 spin_lock_irq(&current->sighand->siglock);
191 current->blocked = set;
192 recalc_sigpending();
193 spin_unlock_irq(&current->sighand->siglock);
194
195 if (restore_sigcontext(regs, &frame->sc, &eax))
196 goto badframe;
197 return eax;
198
199badframe:
Masoud Asgharifard Sharbianiabd4f752007-07-22 11:12:28 +0200200 if (show_unhandled_signals && printk_ratelimit())
201 printk("%s%s[%d] bad frame in sigreturn frame:%p eip:%lx"
202 " esp:%lx oeax:%lx\n",
Alexey Dobriyan19c58702007-10-18 23:40:41 -0700203 task_pid_nr(current) > 1 ? KERN_INFO : KERN_EMERG,
204 current->comm, task_pid_nr(current), frame, regs->eip,
Masoud Asgharifard Sharbianiabd4f752007-07-22 11:12:28 +0200205 regs->esp, regs->orig_eax);
206
Linus Torvalds1da177e2005-04-16 15:20:36 -0700207 force_sig(SIGSEGV, current);
208 return 0;
209}
210
211asmlinkage int sys_rt_sigreturn(unsigned long __unused)
212{
213 struct pt_regs *regs = (struct pt_regs *) &__unused;
214 struct rt_sigframe __user *frame = (struct rt_sigframe __user *)(regs->esp - 4);
215 sigset_t set;
216 int eax;
217
218 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
219 goto badframe;
220 if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set)))
221 goto badframe;
222
223 sigdelsetmask(&set, ~_BLOCKABLE);
224 spin_lock_irq(&current->sighand->siglock);
225 current->blocked = set;
226 recalc_sigpending();
227 spin_unlock_irq(&current->sighand->siglock);
228
229 if (restore_sigcontext(regs, &frame->uc.uc_mcontext, &eax))
230 goto badframe;
231
232 if (do_sigaltstack(&frame->uc.uc_stack, NULL, regs->esp) == -EFAULT)
233 goto badframe;
234
235 return eax;
236
237badframe:
238 force_sig(SIGSEGV, current);
239 return 0;
240}
241
242/*
243 * Set up a signal frame.
244 */
245
246static int
247setup_sigcontext(struct sigcontext __user *sc, struct _fpstate __user *fpstate,
248 struct pt_regs *regs, unsigned long mask)
249{
250 int tmp, err = 0;
251
Jeremy Fitzhardinge464d1a72007-02-13 13:26:20 +0100252 err |= __put_user(regs->xfs, (unsigned int __user *)&sc->fs);
253 savesegment(gs, tmp);
254 err |= __put_user(tmp, (unsigned int __user *)&sc->gs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700255
256 err |= __put_user(regs->xes, (unsigned int __user *)&sc->es);
257 err |= __put_user(regs->xds, (unsigned int __user *)&sc->ds);
258 err |= __put_user(regs->edi, &sc->edi);
259 err |= __put_user(regs->esi, &sc->esi);
260 err |= __put_user(regs->ebp, &sc->ebp);
261 err |= __put_user(regs->esp, &sc->esp);
262 err |= __put_user(regs->ebx, &sc->ebx);
263 err |= __put_user(regs->edx, &sc->edx);
264 err |= __put_user(regs->ecx, &sc->ecx);
265 err |= __put_user(regs->eax, &sc->eax);
266 err |= __put_user(current->thread.trap_no, &sc->trapno);
267 err |= __put_user(current->thread.error_code, &sc->err);
268 err |= __put_user(regs->eip, &sc->eip);
269 err |= __put_user(regs->xcs, (unsigned int __user *)&sc->cs);
270 err |= __put_user(regs->eflags, &sc->eflags);
271 err |= __put_user(regs->esp, &sc->esp_at_signal);
272 err |= __put_user(regs->xss, (unsigned int __user *)&sc->ss);
273
274 tmp = save_i387(fpstate);
275 if (tmp < 0)
276 err = 1;
277 else
278 err |= __put_user(tmp ? fpstate : NULL, &sc->fpstate);
279
280 /* non-iBCS2 extensions.. */
281 err |= __put_user(mask, &sc->oldmask);
282 err |= __put_user(current->thread.cr2, &sc->cr2);
283
284 return err;
285}
286
287/*
288 * Determine which stack to use..
289 */
290static inline void __user *
291get_sigframe(struct k_sigaction *ka, struct pt_regs * regs, size_t frame_size)
292{
293 unsigned long esp;
294
295 /* Default to using normal stack */
296 esp = regs->esp;
297
Roland McGrath83bd0102008-01-30 13:30:06 +0100298 /*
299 * If we are on the alternate signal stack and would overflow it, don't.
300 * Return an always-bogus address instead so we will die with SIGSEGV.
301 */
302 if (on_sig_stack(esp) && !likely(on_sig_stack(esp - frame_size)))
303 return (void __user *) -1L;
304
Linus Torvalds1da177e2005-04-16 15:20:36 -0700305 /* This is the X/Open sanctioned signal stack switching. */
306 if (ka->sa.sa_flags & SA_ONSTACK) {
307 if (sas_ss_flags(esp) == 0)
308 esp = current->sas_ss_sp + current->sas_ss_size;
309 }
310
311 /* This is the legacy signal stack switching. */
312 else if ((regs->xss & 0xffff) != __USER_DS &&
313 !(ka->sa.sa_flags & SA_RESTORER) &&
314 ka->sa.sa_restorer) {
315 esp = (unsigned long) ka->sa.sa_restorer;
316 }
317
Markus F.X.J. Oberhumerd347f372005-10-09 18:54:23 +0200318 esp -= frame_size;
319 /* Align the stack pointer according to the i386 ABI,
320 * i.e. so that on function entry ((sp + 4) & 15) == 0. */
321 esp = ((esp + 4) & -16ul) - 4;
322 return (void __user *) esp;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700323}
324
325/* These symbols are defined with the addresses in the vsyscall page.
326 See vsyscall-sigreturn.S. */
327extern void __user __kernel_sigreturn;
328extern void __user __kernel_rt_sigreturn;
329
Roland McGrath7c1def12005-06-23 00:08:21 -0700330static int setup_frame(int sig, struct k_sigaction *ka,
331 sigset_t *set, struct pt_regs * regs)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700332{
333 void __user *restorer;
334 struct sigframe __user *frame;
335 int err = 0;
336 int usig;
337
338 frame = get_sigframe(ka, regs, sizeof(*frame));
339
340 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
341 goto give_sigsegv;
342
343 usig = current_thread_info()->exec_domain
344 && current_thread_info()->exec_domain->signal_invmap
345 && sig < 32
346 ? current_thread_info()->exec_domain->signal_invmap[sig]
347 : sig;
348
349 err = __put_user(usig, &frame->sig);
350 if (err)
351 goto give_sigsegv;
352
353 err = setup_sigcontext(&frame->sc, &frame->fpstate, regs, set->sig[0]);
354 if (err)
355 goto give_sigsegv;
356
357 if (_NSIG_WORDS > 1) {
358 err = __copy_to_user(&frame->extramask, &set->sig[1],
359 sizeof(frame->extramask));
360 if (err)
361 goto give_sigsegv;
362 }
363
Andi Kleen9fbbd4d2007-02-13 13:26:26 +0100364 if (current->binfmt->hasvdso)
365 restorer = (void *)VDSO_SYM(&__kernel_sigreturn);
366 else
367 restorer = (void *)&frame->retcode;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700368 if (ka->sa.sa_flags & SA_RESTORER)
369 restorer = ka->sa.sa_restorer;
370
371 /* Set up to return from userspace. */
372 err |= __put_user(restorer, &frame->pretcode);
373
374 /*
375 * This is popl %eax ; movl $,%eax ; int $0x80
376 *
377 * WE DO NOT USE IT ANY MORE! It's only left here for historical
378 * reasons and because gdb uses it as a signature to notice
379 * signal handler stack frames.
380 */
381 err |= __put_user(0xb858, (short __user *)(frame->retcode+0));
382 err |= __put_user(__NR_sigreturn, (int __user *)(frame->retcode+2));
383 err |= __put_user(0x80cd, (short __user *)(frame->retcode+6));
384
385 if (err)
386 goto give_sigsegv;
387
388 /* Set up registers for signal handler */
389 regs->esp = (unsigned long) frame;
390 regs->eip = (unsigned long) ka->sa.sa_handler;
391 regs->eax = (unsigned long) sig;
392 regs->edx = (unsigned long) 0;
393 regs->ecx = (unsigned long) 0;
394
Linus Torvalds1da177e2005-04-16 15:20:36 -0700395 regs->xds = __USER_DS;
396 regs->xes = __USER_DS;
397 regs->xss = __USER_DS;
398 regs->xcs = __USER_CS;
399
400 /*
401 * Clear TF when entering the signal handler, but
402 * notify any tracer that was single-stepping it.
403 * The tracer may want to single-step inside the
404 * handler too.
405 */
406 regs->eflags &= ~TF_MASK;
407 if (test_thread_flag(TIF_SINGLESTEP))
408 ptrace_notify(SIGTRAP);
409
410#if DEBUG_SIG
411 printk("SIG deliver (%s:%d): sp=%p pc=%p ra=%p\n",
412 current->comm, current->pid, frame, regs->eip, frame->pretcode);
413#endif
414
David Howells283828f2006-01-18 17:44:00 -0800415 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700416
417give_sigsegv:
418 force_sigsegv(sig, current);
David Howells283828f2006-01-18 17:44:00 -0800419 return -EFAULT;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700420}
421
Roland McGrath7c1def12005-06-23 00:08:21 -0700422static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700423 sigset_t *set, struct pt_regs * regs)
424{
425 void __user *restorer;
426 struct rt_sigframe __user *frame;
427 int err = 0;
428 int usig;
429
430 frame = get_sigframe(ka, regs, sizeof(*frame));
431
432 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
433 goto give_sigsegv;
434
435 usig = current_thread_info()->exec_domain
436 && current_thread_info()->exec_domain->signal_invmap
437 && sig < 32
438 ? current_thread_info()->exec_domain->signal_invmap[sig]
439 : sig;
440
441 err |= __put_user(usig, &frame->sig);
442 err |= __put_user(&frame->info, &frame->pinfo);
443 err |= __put_user(&frame->uc, &frame->puc);
444 err |= copy_siginfo_to_user(&frame->info, info);
445 if (err)
446 goto give_sigsegv;
447
448 /* Create the ucontext. */
449 err |= __put_user(0, &frame->uc.uc_flags);
450 err |= __put_user(0, &frame->uc.uc_link);
451 err |= __put_user(current->sas_ss_sp, &frame->uc.uc_stack.ss_sp);
452 err |= __put_user(sas_ss_flags(regs->esp),
453 &frame->uc.uc_stack.ss_flags);
454 err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size);
455 err |= setup_sigcontext(&frame->uc.uc_mcontext, &frame->fpstate,
456 regs, set->sig[0]);
457 err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
458 if (err)
459 goto give_sigsegv;
460
461 /* Set up to return from userspace. */
Ingo Molnare6e54942006-06-27 02:53:50 -0700462 restorer = (void *)VDSO_SYM(&__kernel_rt_sigreturn);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700463 if (ka->sa.sa_flags & SA_RESTORER)
464 restorer = ka->sa.sa_restorer;
465 err |= __put_user(restorer, &frame->pretcode);
466
467 /*
468 * This is movl $,%eax ; int $0x80
469 *
470 * WE DO NOT USE IT ANY MORE! It's only left here for historical
471 * reasons and because gdb uses it as a signature to notice
472 * signal handler stack frames.
473 */
474 err |= __put_user(0xb8, (char __user *)(frame->retcode+0));
475 err |= __put_user(__NR_rt_sigreturn, (int __user *)(frame->retcode+1));
476 err |= __put_user(0x80cd, (short __user *)(frame->retcode+5));
477
478 if (err)
479 goto give_sigsegv;
480
481 /* Set up registers for signal handler */
482 regs->esp = (unsigned long) frame;
483 regs->eip = (unsigned long) ka->sa.sa_handler;
484 regs->eax = (unsigned long) usig;
485 regs->edx = (unsigned long) &frame->info;
486 regs->ecx = (unsigned long) &frame->uc;
487
Linus Torvalds1da177e2005-04-16 15:20:36 -0700488 regs->xds = __USER_DS;
489 regs->xes = __USER_DS;
490 regs->xss = __USER_DS;
491 regs->xcs = __USER_CS;
492
493 /*
494 * Clear TF when entering the signal handler, but
495 * notify any tracer that was single-stepping it.
496 * The tracer may want to single-step inside the
497 * handler too.
498 */
499 regs->eflags &= ~TF_MASK;
500 if (test_thread_flag(TIF_SINGLESTEP))
501 ptrace_notify(SIGTRAP);
502
503#if DEBUG_SIG
504 printk("SIG deliver (%s:%d): sp=%p pc=%p ra=%p\n",
505 current->comm, current->pid, frame, regs->eip, frame->pretcode);
506#endif
507
David Howells283828f2006-01-18 17:44:00 -0800508 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700509
510give_sigsegv:
511 force_sigsegv(sig, current);
David Howells283828f2006-01-18 17:44:00 -0800512 return -EFAULT;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700513}
514
515/*
516 * OK, we're invoking a handler
517 */
518
Roland McGrath7c1def12005-06-23 00:08:21 -0700519static int
Linus Torvalds1da177e2005-04-16 15:20:36 -0700520handle_signal(unsigned long sig, siginfo_t *info, struct k_sigaction *ka,
521 sigset_t *oldset, struct pt_regs * regs)
522{
Roland McGrath7c1def12005-06-23 00:08:21 -0700523 int ret;
524
Linus Torvalds1da177e2005-04-16 15:20:36 -0700525 /* Are we from a system call? */
526 if (regs->orig_eax >= 0) {
527 /* If so, check system call restarting.. */
528 switch (regs->eax) {
529 case -ERESTART_RESTARTBLOCK:
530 case -ERESTARTNOHAND:
531 regs->eax = -EINTR;
532 break;
533
534 case -ERESTARTSYS:
535 if (!(ka->sa.sa_flags & SA_RESTART)) {
536 regs->eax = -EINTR;
537 break;
538 }
539 /* fallthrough */
540 case -ERESTARTNOINTR:
541 regs->eax = regs->orig_eax;
542 regs->eip -= 2;
543 }
544 }
545
546 /*
547 * If TF is set due to a debugger (PT_DTRACE), clear the TF flag so
548 * that register information in the sigcontext is correct.
549 */
550 if (unlikely(regs->eflags & TF_MASK)
551 && likely(current->ptrace & PT_DTRACE)) {
552 current->ptrace &= ~PT_DTRACE;
553 regs->eflags &= ~TF_MASK;
554 }
555
556 /* Set up the stack frame */
557 if (ka->sa.sa_flags & SA_SIGINFO)
Roland McGrath7c1def12005-06-23 00:08:21 -0700558 ret = setup_rt_frame(sig, ka, info, oldset, regs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700559 else
Roland McGrath7c1def12005-06-23 00:08:21 -0700560 ret = setup_frame(sig, ka, oldset, regs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700561
David Howells283828f2006-01-18 17:44:00 -0800562 if (ret == 0) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700563 spin_lock_irq(&current->sighand->siglock);
564 sigorsets(&current->blocked,&current->blocked,&ka->sa.sa_mask);
Steven Rostedt69be8f12005-08-29 11:44:09 -0400565 if (!(ka->sa.sa_flags & SA_NODEFER))
566 sigaddset(&current->blocked,sig);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700567 recalc_sigpending();
568 spin_unlock_irq(&current->sighand->siglock);
569 }
Roland McGrath7c1def12005-06-23 00:08:21 -0700570
571 return ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700572}
573
574/*
575 * Note that 'init' is a special process: it doesn't get signals it doesn't
576 * want to handle. Thus you cannot kill init even with a SIGKILL even by
577 * mistake.
578 */
David Howells283828f2006-01-18 17:44:00 -0800579static void fastcall do_signal(struct pt_regs *regs)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700580{
581 siginfo_t info;
582 int signr;
583 struct k_sigaction ka;
David Howells283828f2006-01-18 17:44:00 -0800584 sigset_t *oldset;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700585
586 /*
587 * We want the common case to go fast, which
588 * is why we may in certain cases get here from
589 * kernel mode. Just return without doing anything
Zachary Amsden0998e422005-09-03 15:56:43 -0700590 * if so. vm86 regs switched out by assembly code
591 * before reaching here, so testing against kernel
592 * CS suffices.
Linus Torvalds1da177e2005-04-16 15:20:36 -0700593 */
Vincent Hanquez717b5942005-06-23 00:08:45 -0700594 if (!user_mode(regs))
David Howells283828f2006-01-18 17:44:00 -0800595 return;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700596
David Howells283828f2006-01-18 17:44:00 -0800597 if (test_thread_flag(TIF_RESTORE_SIGMASK))
598 oldset = &current->saved_sigmask;
599 else
Linus Torvalds1da177e2005-04-16 15:20:36 -0700600 oldset = &current->blocked;
601
602 signr = get_signal_to_deliver(&info, &ka, regs, NULL);
603 if (signr > 0) {
Simon Arlott27b46d72007-10-20 01:13:56 +0200604 /* Re-enable any watchpoints before delivering the
Linus Torvalds1da177e2005-04-16 15:20:36 -0700605 * signal to user space. The processor register will
606 * have been cleared if the watchpoint triggered
607 * inside the kernel.
608 */
David Howells283828f2006-01-18 17:44:00 -0800609 if (unlikely(current->thread.debugreg[7]))
Vincent Hanquez1cc6f122005-06-23 00:08:43 -0700610 set_debugreg(current->thread.debugreg[7], 7);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700611
612 /* Whee! Actually deliver the signal. */
David Howells283828f2006-01-18 17:44:00 -0800613 if (handle_signal(signr, &info, &ka, oldset, regs) == 0) {
614 /* a signal was successfully delivered; the saved
615 * sigmask will have been stored in the signal frame,
616 * and will be restored by sigreturn, so we can simply
617 * clear the TIF_RESTORE_SIGMASK flag */
618 if (test_thread_flag(TIF_RESTORE_SIGMASK))
619 clear_thread_flag(TIF_RESTORE_SIGMASK);
620 }
621
622 return;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700623 }
624
Linus Torvalds1da177e2005-04-16 15:20:36 -0700625 /* Did we come from a system call? */
626 if (regs->orig_eax >= 0) {
627 /* Restart the system call - no handlers present */
David Howells283828f2006-01-18 17:44:00 -0800628 switch (regs->eax) {
629 case -ERESTARTNOHAND:
630 case -ERESTARTSYS:
631 case -ERESTARTNOINTR:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700632 regs->eax = regs->orig_eax;
633 regs->eip -= 2;
David Howells283828f2006-01-18 17:44:00 -0800634 break;
635
636 case -ERESTART_RESTARTBLOCK:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700637 regs->eax = __NR_restart_syscall;
638 regs->eip -= 2;
David Howells283828f2006-01-18 17:44:00 -0800639 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700640 }
641 }
David Howells283828f2006-01-18 17:44:00 -0800642
643 /* if there's no signal to deliver, we just put the saved sigmask
644 * back */
645 if (test_thread_flag(TIF_RESTORE_SIGMASK)) {
646 clear_thread_flag(TIF_RESTORE_SIGMASK);
647 sigprocmask(SIG_SETMASK, &current->saved_sigmask, NULL);
648 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700649}
650
651/*
652 * notification of userspace execution resumption
David Howells283828f2006-01-18 17:44:00 -0800653 * - triggered by the TIF_WORK_MASK flags
Linus Torvalds1da177e2005-04-16 15:20:36 -0700654 */
655__attribute__((regparm(3)))
David Howells283828f2006-01-18 17:44:00 -0800656void do_notify_resume(struct pt_regs *regs, void *_unused,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700657 __u32 thread_info_flags)
658{
659 /* Pending single-step? */
660 if (thread_info_flags & _TIF_SINGLESTEP) {
661 regs->eflags |= TF_MASK;
662 clear_thread_flag(TIF_SINGLESTEP);
663 }
David Howells283828f2006-01-18 17:44:00 -0800664
Linus Torvalds1da177e2005-04-16 15:20:36 -0700665 /* deal with pending signal delivery */
David Howells283828f2006-01-18 17:44:00 -0800666 if (thread_info_flags & (_TIF_SIGPENDING | _TIF_RESTORE_SIGMASK))
667 do_signal(regs);
Peter Zijlstra8f4d37e2008-01-25 21:08:29 +0100668
669 if (thread_info_flags & _TIF_HRTICK_RESCHED)
670 hrtick_resched();
Linus Torvalds1da177e2005-04-16 15:20:36 -0700671
672 clear_thread_flag(TIF_IRET);
673}