Loading...
1/*
2 * arch/sh/kernel/signal_64.c
3 *
4 * Copyright (C) 2000, 2001 Paolo Alberelli
5 * Copyright (C) 2003 - 2008 Paul Mundt
6 * Copyright (C) 2004 Richard Curnow
7 *
8 * This file is subject to the terms and conditions of the GNU General Public
9 * License. See the file "COPYING" in the main directory of this archive
10 * for more details.
11 */
12#include <linux/rwsem.h>
13#include <linux/sched.h>
14#include <linux/mm.h>
15#include <linux/smp.h>
16#include <linux/kernel.h>
17#include <linux/signal.h>
18#include <linux/errno.h>
19#include <linux/wait.h>
20#include <linux/personality.h>
21#include <linux/ptrace.h>
22#include <linux/unistd.h>
23#include <linux/stddef.h>
24#include <linux/tracehook.h>
25#include <asm/ucontext.h>
26#include <asm/uaccess.h>
27#include <asm/pgtable.h>
28#include <asm/cacheflush.h>
29#include <asm/fpu.h>
30
31#define REG_RET 9
32#define REG_ARG1 2
33#define REG_ARG2 3
34#define REG_ARG3 4
35#define REG_SP 15
36#define REG_PR 18
37#define REF_REG_RET regs->regs[REG_RET]
38#define REF_REG_SP regs->regs[REG_SP]
39#define DEREF_REG_PR regs->regs[REG_PR]
40
41#define DEBUG_SIG 0
42
43static void
44handle_signal(struct ksignal *ksig, struct pt_regs *regs);
45
46static inline void
47handle_syscall_restart(struct pt_regs *regs, struct sigaction *sa)
48{
49 /* If we're not from a syscall, bail out */
50 if (regs->syscall_nr < 0)
51 return;
52
53 /* check for system call restart.. */
54 switch (regs->regs[REG_RET]) {
55 case -ERESTART_RESTARTBLOCK:
56 case -ERESTARTNOHAND:
57 no_system_call_restart:
58 regs->regs[REG_RET] = -EINTR;
59 break;
60
61 case -ERESTARTSYS:
62 if (!(sa->sa_flags & SA_RESTART))
63 goto no_system_call_restart;
64 /* fallthrough */
65 case -ERESTARTNOINTR:
66 /* Decode syscall # */
67 regs->regs[REG_RET] = regs->syscall_nr;
68 regs->pc -= 4;
69 break;
70 }
71}
72
73/*
74 * Note that 'init' is a special process: it doesn't get signals it doesn't
75 * want to handle. Thus you cannot kill init even with a SIGKILL even by
76 * mistake.
77 *
78 * Note that we go through the signals twice: once to check the signals that
79 * the kernel can handle, and then we build all the user-level signal handling
80 * stack-frames in one go after that.
81 */
82static void do_signal(struct pt_regs *regs)
83{
84 struct ksignal ksig;
85
86 /*
87 * We want the common case to go fast, which
88 * is why we may in certain cases get here from
89 * kernel mode. Just return without doing anything
90 * if so.
91 */
92 if (!user_mode(regs))
93 return;
94
95 if (get_signal(&ksig)) {
96 handle_syscall_restart(regs, &ksig.ka.sa);
97
98 /* Whee! Actually deliver the signal. */
99 handle_signal(&ksig, regs);
100 return;
101 }
102
103 /* Did we come from a system call? */
104 if (regs->syscall_nr >= 0) {
105 /* Restart the system call - no handlers present */
106 switch (regs->regs[REG_RET]) {
107 case -ERESTARTNOHAND:
108 case -ERESTARTSYS:
109 case -ERESTARTNOINTR:
110 /* Decode Syscall # */
111 regs->regs[REG_RET] = regs->syscall_nr;
112 regs->pc -= 4;
113 break;
114
115 case -ERESTART_RESTARTBLOCK:
116 regs->regs[REG_RET] = __NR_restart_syscall;
117 regs->pc -= 4;
118 break;
119 }
120 }
121
122 /* No signal to deliver -- put the saved sigmask back */
123 restore_saved_sigmask();
124}
125
126/*
127 * Do a signal return; undo the signal stack.
128 */
129struct sigframe {
130 struct sigcontext sc;
131 unsigned long extramask[_NSIG_WORDS-1];
132 long long retcode[2];
133};
134
135struct rt_sigframe {
136 struct siginfo __user *pinfo;
137 void *puc;
138 struct siginfo info;
139 struct ucontext uc;
140 long long retcode[2];
141};
142
143#ifdef CONFIG_SH_FPU
144static inline int
145restore_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
146{
147 int err = 0;
148 int fpvalid;
149
150 err |= __get_user (fpvalid, &sc->sc_fpvalid);
151 conditional_used_math(fpvalid);
152 if (! fpvalid)
153 return err;
154
155 if (current == last_task_used_math) {
156 last_task_used_math = NULL;
157 regs->sr |= SR_FD;
158 }
159
160 err |= __copy_from_user(¤t->thread.xstate->hardfpu, &sc->sc_fpregs[0],
161 (sizeof(long long) * 32) + (sizeof(int) * 1));
162
163 return err;
164}
165
166static inline int
167setup_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
168{
169 int err = 0;
170 int fpvalid;
171
172 fpvalid = !!used_math();
173 err |= __put_user(fpvalid, &sc->sc_fpvalid);
174 if (! fpvalid)
175 return err;
176
177 if (current == last_task_used_math) {
178 enable_fpu();
179 save_fpu(current);
180 disable_fpu();
181 last_task_used_math = NULL;
182 regs->sr |= SR_FD;
183 }
184
185 err |= __copy_to_user(&sc->sc_fpregs[0], ¤t->thread.xstate->hardfpu,
186 (sizeof(long long) * 32) + (sizeof(int) * 1));
187 clear_used_math();
188
189 return err;
190}
191#else
192static inline int
193restore_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
194{
195 return 0;
196}
197static inline int
198setup_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
199{
200 return 0;
201}
202#endif
203
204static int
205restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc, long long *r2_p)
206{
207 unsigned int err = 0;
208 unsigned long long current_sr, new_sr;
209#define SR_MASK 0xffff8cfd
210
211#define COPY(x) err |= __get_user(regs->x, &sc->sc_##x)
212
213 COPY(regs[0]); COPY(regs[1]); COPY(regs[2]); COPY(regs[3]);
214 COPY(regs[4]); COPY(regs[5]); COPY(regs[6]); COPY(regs[7]);
215 COPY(regs[8]); COPY(regs[9]); COPY(regs[10]); COPY(regs[11]);
216 COPY(regs[12]); COPY(regs[13]); COPY(regs[14]); COPY(regs[15]);
217 COPY(regs[16]); COPY(regs[17]); COPY(regs[18]); COPY(regs[19]);
218 COPY(regs[20]); COPY(regs[21]); COPY(regs[22]); COPY(regs[23]);
219 COPY(regs[24]); COPY(regs[25]); COPY(regs[26]); COPY(regs[27]);
220 COPY(regs[28]); COPY(regs[29]); COPY(regs[30]); COPY(regs[31]);
221 COPY(regs[32]); COPY(regs[33]); COPY(regs[34]); COPY(regs[35]);
222 COPY(regs[36]); COPY(regs[37]); COPY(regs[38]); COPY(regs[39]);
223 COPY(regs[40]); COPY(regs[41]); COPY(regs[42]); COPY(regs[43]);
224 COPY(regs[44]); COPY(regs[45]); COPY(regs[46]); COPY(regs[47]);
225 COPY(regs[48]); COPY(regs[49]); COPY(regs[50]); COPY(regs[51]);
226 COPY(regs[52]); COPY(regs[53]); COPY(regs[54]); COPY(regs[55]);
227 COPY(regs[56]); COPY(regs[57]); COPY(regs[58]); COPY(regs[59]);
228 COPY(regs[60]); COPY(regs[61]); COPY(regs[62]);
229 COPY(tregs[0]); COPY(tregs[1]); COPY(tregs[2]); COPY(tregs[3]);
230 COPY(tregs[4]); COPY(tregs[5]); COPY(tregs[6]); COPY(tregs[7]);
231
232 /* Prevent the signal handler manipulating SR in a way that can
233 crash the kernel. i.e. only allow S, Q, M, PR, SZ, FR to be
234 modified */
235 current_sr = regs->sr;
236 err |= __get_user(new_sr, &sc->sc_sr);
237 regs->sr &= SR_MASK;
238 regs->sr |= (new_sr & ~SR_MASK);
239
240 COPY(pc);
241
242#undef COPY
243
244 /* Must do this last in case it sets regs->sr.fd (i.e. after rest of sr
245 * has been restored above.) */
246 err |= restore_sigcontext_fpu(regs, sc);
247
248 regs->syscall_nr = -1; /* disable syscall checks */
249 err |= __get_user(*r2_p, &sc->sc_regs[REG_RET]);
250 return err;
251}
252
253asmlinkage int sys_sigreturn(unsigned long r2, unsigned long r3,
254 unsigned long r4, unsigned long r5,
255 unsigned long r6, unsigned long r7,
256 struct pt_regs * regs)
257{
258 struct sigframe __user *frame = (struct sigframe __user *) (long) REF_REG_SP;
259 sigset_t set;
260 long long ret;
261
262 /* Always make any pending restarted system calls return -EINTR */
263 current->restart_block.fn = do_no_restart_syscall;
264
265 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
266 goto badframe;
267
268 if (__get_user(set.sig[0], &frame->sc.oldmask)
269 || (_NSIG_WORDS > 1
270 && __copy_from_user(&set.sig[1], &frame->extramask,
271 sizeof(frame->extramask))))
272 goto badframe;
273
274 set_current_blocked(&set);
275
276 if (restore_sigcontext(regs, &frame->sc, &ret))
277 goto badframe;
278 regs->pc -= 4;
279
280 return (int) ret;
281
282badframe:
283 force_sig(SIGSEGV, current);
284 return 0;
285}
286
287asmlinkage int sys_rt_sigreturn(unsigned long r2, unsigned long r3,
288 unsigned long r4, unsigned long r5,
289 unsigned long r6, unsigned long r7,
290 struct pt_regs * regs)
291{
292 struct rt_sigframe __user *frame = (struct rt_sigframe __user *) (long) REF_REG_SP;
293 sigset_t set;
294 long long ret;
295
296 /* Always make any pending restarted system calls return -EINTR */
297 current->restart_block.fn = do_no_restart_syscall;
298
299 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
300 goto badframe;
301
302 if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set)))
303 goto badframe;
304
305 set_current_blocked(&set);
306
307 if (restore_sigcontext(regs, &frame->uc.uc_mcontext, &ret))
308 goto badframe;
309 regs->pc -= 4;
310
311 if (restore_altstack(&frame->uc.uc_stack))
312 goto badframe;
313
314 return (int) ret;
315
316badframe:
317 force_sig(SIGSEGV, current);
318 return 0;
319}
320
321/*
322 * Set up a signal frame.
323 */
324static int
325setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs,
326 unsigned long mask)
327{
328 int err = 0;
329
330 /* Do this first, otherwise is this sets sr->fd, that value isn't preserved. */
331 err |= setup_sigcontext_fpu(regs, sc);
332
333#define COPY(x) err |= __put_user(regs->x, &sc->sc_##x)
334
335 COPY(regs[0]); COPY(regs[1]); COPY(regs[2]); COPY(regs[3]);
336 COPY(regs[4]); COPY(regs[5]); COPY(regs[6]); COPY(regs[7]);
337 COPY(regs[8]); COPY(regs[9]); COPY(regs[10]); COPY(regs[11]);
338 COPY(regs[12]); COPY(regs[13]); COPY(regs[14]); COPY(regs[15]);
339 COPY(regs[16]); COPY(regs[17]); COPY(regs[18]); COPY(regs[19]);
340 COPY(regs[20]); COPY(regs[21]); COPY(regs[22]); COPY(regs[23]);
341 COPY(regs[24]); COPY(regs[25]); COPY(regs[26]); COPY(regs[27]);
342 COPY(regs[28]); COPY(regs[29]); COPY(regs[30]); COPY(regs[31]);
343 COPY(regs[32]); COPY(regs[33]); COPY(regs[34]); COPY(regs[35]);
344 COPY(regs[36]); COPY(regs[37]); COPY(regs[38]); COPY(regs[39]);
345 COPY(regs[40]); COPY(regs[41]); COPY(regs[42]); COPY(regs[43]);
346 COPY(regs[44]); COPY(regs[45]); COPY(regs[46]); COPY(regs[47]);
347 COPY(regs[48]); COPY(regs[49]); COPY(regs[50]); COPY(regs[51]);
348 COPY(regs[52]); COPY(regs[53]); COPY(regs[54]); COPY(regs[55]);
349 COPY(regs[56]); COPY(regs[57]); COPY(regs[58]); COPY(regs[59]);
350 COPY(regs[60]); COPY(regs[61]); COPY(regs[62]);
351 COPY(tregs[0]); COPY(tregs[1]); COPY(tregs[2]); COPY(tregs[3]);
352 COPY(tregs[4]); COPY(tregs[5]); COPY(tregs[6]); COPY(tregs[7]);
353 COPY(sr); COPY(pc);
354
355#undef COPY
356
357 err |= __put_user(mask, &sc->oldmask);
358
359 return err;
360}
361
362/*
363 * Determine which stack to use..
364 */
365static inline void __user *
366get_sigframe(struct k_sigaction *ka, unsigned long sp, size_t frame_size)
367{
368 if ((ka->sa.sa_flags & SA_ONSTACK) != 0 && ! sas_ss_flags(sp))
369 sp = current->sas_ss_sp + current->sas_ss_size;
370
371 return (void __user *)((sp - frame_size) & -8ul);
372}
373
374void sa_default_restorer(void); /* See comments below */
375void sa_default_rt_restorer(void); /* See comments below */
376
377static int setup_frame(struct ksignal *ksig, sigset_t *set, struct pt_regs *regs)
378{
379 struct sigframe __user *frame;
380 int err = 0, sig = ksig->sig;
381 int signal;
382
383 frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame));
384
385 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
386 return -EFAULT;
387
388 err |= setup_sigcontext(&frame->sc, regs, set->sig[0]);
389
390 /* Give up earlier as i386, in case */
391 if (err)
392 return -EFAULT;
393
394 if (_NSIG_WORDS > 1) {
395 err |= __copy_to_user(frame->extramask, &set->sig[1],
396 sizeof(frame->extramask)); }
397
398 /* Give up earlier as i386, in case */
399 if (err)
400 return -EFAULT;
401
402 /* Set up to return from userspace. If provided, use a stub
403 already in userspace. */
404 if (ksig->ka.sa.sa_flags & SA_RESTORER) {
405 /*
406 * On SH5 all edited pointers are subject to NEFF
407 */
408 DEREF_REG_PR = neff_sign_extend((unsigned long)
409 ksig->ka->sa.sa_restorer | 0x1);
410 } else {
411 /*
412 * Different approach on SH5.
413 * . Endianness independent asm code gets placed in entry.S .
414 * This is limited to four ASM instructions corresponding
415 * to two long longs in size.
416 * . err checking is done on the else branch only
417 * . flush_icache_range() is called upon __put_user() only
418 * . all edited pointers are subject to NEFF
419 * . being code, linker turns ShMedia bit on, always
420 * dereference index -1.
421 */
422 DEREF_REG_PR = neff_sign_extend((unsigned long)
423 frame->retcode | 0x01);
424
425 if (__copy_to_user(frame->retcode,
426 (void *)((unsigned long)sa_default_restorer & (~1)), 16) != 0)
427 return -EFAULT;
428
429 /* Cohere the trampoline with the I-cache. */
430 flush_cache_sigtramp(DEREF_REG_PR-1);
431 }
432
433 /*
434 * Set up registers for signal handler.
435 * All edited pointers are subject to NEFF.
436 */
437 regs->regs[REG_SP] = neff_sign_extend((unsigned long)frame);
438 regs->regs[REG_ARG1] = sig; /* Arg for signal handler */
439
440 /* FIXME:
441 The glibc profiling support for SH-5 needs to be passed a sigcontext
442 so it can retrieve the PC. At some point during 2003 the glibc
443 support was changed to receive the sigcontext through the 2nd
444 argument, but there are still versions of libc.so in use that use
445 the 3rd argument. Until libc.so is stabilised, pass the sigcontext
446 through both 2nd and 3rd arguments.
447 */
448
449 regs->regs[REG_ARG2] = (unsigned long long)(unsigned long)(signed long)&frame->sc;
450 regs->regs[REG_ARG3] = (unsigned long long)(unsigned long)(signed long)&frame->sc;
451
452 regs->pc = neff_sign_extend((unsigned long)ksig->ka.sa.sa_handler);
453
454 /* Broken %016Lx */
455 pr_debug("SIG deliver (#%d,%s:%d): sp=%p pc=%08Lx%08Lx link=%08Lx%08Lx\n",
456 sig, current->comm, current->pid, frame,
457 regs->pc >> 32, regs->pc & 0xffffffff,
458 DEREF_REG_PR >> 32, DEREF_REG_PR & 0xffffffff);
459
460 return 0;
461}
462
463static int setup_rt_frame(struct ksignal *kig, sigset_t *set,
464 struct pt_regs *regs)
465{
466 struct rt_sigframe __user *frame;
467 int err = 0, sig = ksig->sig;
468
469 frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame));
470
471 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
472 return -EFAULT;
473
474 err |= __put_user(&frame->info, &frame->pinfo);
475 err |= __put_user(&frame->uc, &frame->puc);
476 err |= copy_siginfo_to_user(&frame->info, &ksig->info);
477
478 /* Give up earlier as i386, in case */
479 if (err)
480 return -EFAULT;
481
482 /* Create the ucontext. */
483 err |= __put_user(0, &frame->uc.uc_flags);
484 err |= __put_user(0, &frame->uc.uc_link);
485 err |= __save_altstack(&frame->uc.uc_stack, regs->regs[REG_SP]);
486 err |= setup_sigcontext(&frame->uc.uc_mcontext,
487 regs, set->sig[0]);
488 err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
489
490 /* Give up earlier as i386, in case */
491 if (err)
492 return -EFAULT;
493
494 /* Set up to return from userspace. If provided, use a stub
495 already in userspace. */
496 if (ksig->ka.sa.sa_flags & SA_RESTORER) {
497 /*
498 * On SH5 all edited pointers are subject to NEFF
499 */
500 DEREF_REG_PR = neff_sign_extend((unsigned long)
501 ksig->ka.sa.sa_restorer | 0x1);
502 } else {
503 /*
504 * Different approach on SH5.
505 * . Endianness independent asm code gets placed in entry.S .
506 * This is limited to four ASM instructions corresponding
507 * to two long longs in size.
508 * . err checking is done on the else branch only
509 * . flush_icache_range() is called upon __put_user() only
510 * . all edited pointers are subject to NEFF
511 * . being code, linker turns ShMedia bit on, always
512 * dereference index -1.
513 */
514 DEREF_REG_PR = neff_sign_extend((unsigned long)
515 frame->retcode | 0x01);
516
517 if (__copy_to_user(frame->retcode,
518 (void *)((unsigned long)sa_default_rt_restorer & (~1)), 16) != 0)
519 return -EFAULT;
520
521 /* Cohere the trampoline with the I-cache. */
522 flush_icache_range(DEREF_REG_PR-1, DEREF_REG_PR-1+15);
523 }
524
525 /*
526 * Set up registers for signal handler.
527 * All edited pointers are subject to NEFF.
528 */
529 regs->regs[REG_SP] = neff_sign_extend((unsigned long)frame);
530 regs->regs[REG_ARG1] = sig; /* Arg for signal handler */
531 regs->regs[REG_ARG2] = (unsigned long long)(unsigned long)(signed long)&frame->info;
532 regs->regs[REG_ARG3] = (unsigned long long)(unsigned long)(signed long)&frame->uc.uc_mcontext;
533 regs->pc = neff_sign_extend((unsigned long)ksig->ka.sa.sa_handler);
534
535 pr_debug("SIG deliver (#%d,%s:%d): sp=%p pc=%08Lx%08Lx link=%08Lx%08Lx\n",
536 sig, current->comm, current->pid, frame,
537 regs->pc >> 32, regs->pc & 0xffffffff,
538 DEREF_REG_PR >> 32, DEREF_REG_PR & 0xffffffff);
539
540 return 0;
541}
542
543/*
544 * OK, we're invoking a handler
545 */
546static void
547handle_signal(struct ksignal *ksig, struct pt_regs *regs)
548{
549 sigset_t *oldset = sigmask_to_save();
550 int ret;
551
552 /* Set up the stack frame */
553 if (ksig->ka.sa.sa_flags & SA_SIGINFO)
554 ret = setup_rt_frame(ksig, oldset, regs);
555 else
556 ret = setup_frame(ksig, oldset, regs);
557
558 signal_setup_done(ret, ksig, test_thread_flag(TIF_SINGLESTEP));
559}
560
561asmlinkage void do_notify_resume(struct pt_regs *regs, unsigned long thread_info_flags)
562{
563 if (thread_info_flags & _TIF_SIGPENDING)
564 do_signal(regs);
565
566 if (thread_info_flags & _TIF_NOTIFY_RESUME) {
567 clear_thread_flag(TIF_NOTIFY_RESUME);
568 tracehook_notify_resume(regs);
569 }
570}
1/*
2 * arch/sh/kernel/signal_64.c
3 *
4 * Copyright (C) 2000, 2001 Paolo Alberelli
5 * Copyright (C) 2003 - 2008 Paul Mundt
6 * Copyright (C) 2004 Richard Curnow
7 *
8 * This file is subject to the terms and conditions of the GNU General Public
9 * License. See the file "COPYING" in the main directory of this archive
10 * for more details.
11 */
12#include <linux/rwsem.h>
13#include <linux/sched.h>
14#include <linux/mm.h>
15#include <linux/smp.h>
16#include <linux/kernel.h>
17#include <linux/signal.h>
18#include <linux/errno.h>
19#include <linux/wait.h>
20#include <linux/personality.h>
21#include <linux/freezer.h>
22#include <linux/ptrace.h>
23#include <linux/unistd.h>
24#include <linux/stddef.h>
25#include <linux/tracehook.h>
26#include <asm/ucontext.h>
27#include <asm/uaccess.h>
28#include <asm/pgtable.h>
29#include <asm/cacheflush.h>
30#include <asm/fpu.h>
31
32#define REG_RET 9
33#define REG_ARG1 2
34#define REG_ARG2 3
35#define REG_ARG3 4
36#define REG_SP 15
37#define REG_PR 18
38#define REF_REG_RET regs->regs[REG_RET]
39#define REF_REG_SP regs->regs[REG_SP]
40#define DEREF_REG_PR regs->regs[REG_PR]
41
42#define DEBUG_SIG 0
43
44#define _BLOCKABLE (~(sigmask(SIGKILL) | sigmask(SIGSTOP)))
45
46static int
47handle_signal(unsigned long sig, siginfo_t *info, struct k_sigaction *ka,
48 sigset_t *oldset, struct pt_regs * regs);
49
50static inline void
51handle_syscall_restart(struct pt_regs *regs, struct sigaction *sa)
52{
53 /* If we're not from a syscall, bail out */
54 if (regs->syscall_nr < 0)
55 return;
56
57 /* check for system call restart.. */
58 switch (regs->regs[REG_RET]) {
59 case -ERESTART_RESTARTBLOCK:
60 case -ERESTARTNOHAND:
61 no_system_call_restart:
62 regs->regs[REG_RET] = -EINTR;
63 break;
64
65 case -ERESTARTSYS:
66 if (!(sa->sa_flags & SA_RESTART))
67 goto no_system_call_restart;
68 /* fallthrough */
69 case -ERESTARTNOINTR:
70 /* Decode syscall # */
71 regs->regs[REG_RET] = regs->syscall_nr;
72 regs->pc -= 4;
73 break;
74 }
75}
76
77/*
78 * Note that 'init' is a special process: it doesn't get signals it doesn't
79 * want to handle. Thus you cannot kill init even with a SIGKILL even by
80 * mistake.
81 *
82 * Note that we go through the signals twice: once to check the signals that
83 * the kernel can handle, and then we build all the user-level signal handling
84 * stack-frames in one go after that.
85 */
86static int do_signal(struct pt_regs *regs, sigset_t *oldset)
87{
88 siginfo_t info;
89 int signr;
90 struct k_sigaction ka;
91
92 /*
93 * We want the common case to go fast, which
94 * is why we may in certain cases get here from
95 * kernel mode. Just return without doing anything
96 * if so.
97 */
98 if (!user_mode(regs))
99 return 1;
100
101 if (try_to_freeze())
102 goto no_signal;
103
104 if (current_thread_info()->status & TS_RESTORE_SIGMASK)
105 oldset = ¤t->saved_sigmask;
106 else if (!oldset)
107 oldset = ¤t->blocked;
108
109 signr = get_signal_to_deliver(&info, &ka, regs, 0);
110 if (signr > 0) {
111 handle_syscall_restart(regs, &ka.sa);
112
113 /* Whee! Actually deliver the signal. */
114 if (handle_signal(signr, &info, &ka, oldset, regs) == 0) {
115 /*
116 * If a signal was successfully delivered, the
117 * saved sigmask is in its frame, and we can
118 * clear the TS_RESTORE_SIGMASK flag.
119 */
120 current_thread_info()->status &= ~TS_RESTORE_SIGMASK;
121
122 tracehook_signal_handler(signr, &info, &ka, regs,
123 test_thread_flag(TIF_SINGLESTEP));
124 return 1;
125 }
126 }
127
128no_signal:
129 /* Did we come from a system call? */
130 if (regs->syscall_nr >= 0) {
131 /* Restart the system call - no handlers present */
132 switch (regs->regs[REG_RET]) {
133 case -ERESTARTNOHAND:
134 case -ERESTARTSYS:
135 case -ERESTARTNOINTR:
136 /* Decode Syscall # */
137 regs->regs[REG_RET] = regs->syscall_nr;
138 regs->pc -= 4;
139 break;
140
141 case -ERESTART_RESTARTBLOCK:
142 regs->regs[REG_RET] = __NR_restart_syscall;
143 regs->pc -= 4;
144 break;
145 }
146 }
147
148 /* No signal to deliver -- put the saved sigmask back */
149 if (current_thread_info()->status & TS_RESTORE_SIGMASK) {
150 current_thread_info()->status &= ~TS_RESTORE_SIGMASK;
151 sigprocmask(SIG_SETMASK, ¤t->saved_sigmask, NULL);
152 }
153
154 return 0;
155}
156
157/*
158 * Atomically swap in the new signal mask, and wait for a signal.
159 */
160asmlinkage int
161sys_sigsuspend(old_sigset_t mask,
162 unsigned long r3, unsigned long r4, unsigned long r5,
163 unsigned long r6, unsigned long r7,
164 struct pt_regs * regs)
165{
166 sigset_t saveset;
167
168 mask &= _BLOCKABLE;
169 spin_lock_irq(¤t->sighand->siglock);
170 saveset = current->blocked;
171 siginitset(¤t->blocked, mask);
172 recalc_sigpending();
173 spin_unlock_irq(¤t->sighand->siglock);
174
175 REF_REG_RET = -EINTR;
176 while (1) {
177 current->state = TASK_INTERRUPTIBLE;
178 schedule();
179 set_restore_sigmask();
180 regs->pc += 4; /* because sys_sigreturn decrements the pc */
181 if (do_signal(regs, &saveset)) {
182 /* pc now points at signal handler. Need to decrement
183 it because entry.S will increment it. */
184 regs->pc -= 4;
185 return -EINTR;
186 }
187 }
188}
189
190asmlinkage int
191sys_rt_sigsuspend(sigset_t *unewset, size_t sigsetsize,
192 unsigned long r4, unsigned long r5, unsigned long r6,
193 unsigned long r7,
194 struct pt_regs * regs)
195{
196 sigset_t saveset, newset;
197
198 /* XXX: Don't preclude handling different sized sigset_t's. */
199 if (sigsetsize != sizeof(sigset_t))
200 return -EINVAL;
201
202 if (copy_from_user(&newset, unewset, sizeof(newset)))
203 return -EFAULT;
204 sigdelsetmask(&newset, ~_BLOCKABLE);
205 spin_lock_irq(¤t->sighand->siglock);
206 saveset = current->blocked;
207 current->blocked = newset;
208 recalc_sigpending();
209 spin_unlock_irq(¤t->sighand->siglock);
210
211 REF_REG_RET = -EINTR;
212 while (1) {
213 current->state = TASK_INTERRUPTIBLE;
214 schedule();
215 regs->pc += 4; /* because sys_sigreturn decrements the pc */
216 if (do_signal(regs, &saveset)) {
217 /* pc now points at signal handler. Need to decrement
218 it because entry.S will increment it. */
219 regs->pc -= 4;
220 return -EINTR;
221 }
222 }
223}
224
225asmlinkage int
226sys_sigaction(int sig, const struct old_sigaction __user *act,
227 struct old_sigaction __user *oact)
228{
229 struct k_sigaction new_ka, old_ka;
230 int ret;
231
232 if (act) {
233 old_sigset_t mask;
234 if (!access_ok(VERIFY_READ, act, sizeof(*act)) ||
235 __get_user(new_ka.sa.sa_handler, &act->sa_handler) ||
236 __get_user(new_ka.sa.sa_restorer, &act->sa_restorer))
237 return -EFAULT;
238 __get_user(new_ka.sa.sa_flags, &act->sa_flags);
239 __get_user(mask, &act->sa_mask);
240 siginitset(&new_ka.sa.sa_mask, mask);
241 }
242
243 ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL);
244
245 if (!ret && oact) {
246 if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) ||
247 __put_user(old_ka.sa.sa_handler, &oact->sa_handler) ||
248 __put_user(old_ka.sa.sa_restorer, &oact->sa_restorer))
249 return -EFAULT;
250 __put_user(old_ka.sa.sa_flags, &oact->sa_flags);
251 __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask);
252 }
253
254 return ret;
255}
256
257asmlinkage int
258sys_sigaltstack(const stack_t __user *uss, stack_t __user *uoss,
259 unsigned long r4, unsigned long r5, unsigned long r6,
260 unsigned long r7,
261 struct pt_regs * regs)
262{
263 return do_sigaltstack(uss, uoss, REF_REG_SP);
264}
265
266/*
267 * Do a signal return; undo the signal stack.
268 */
269struct sigframe {
270 struct sigcontext sc;
271 unsigned long extramask[_NSIG_WORDS-1];
272 long long retcode[2];
273};
274
275struct rt_sigframe {
276 struct siginfo __user *pinfo;
277 void *puc;
278 struct siginfo info;
279 struct ucontext uc;
280 long long retcode[2];
281};
282
283#ifdef CONFIG_SH_FPU
284static inline int
285restore_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
286{
287 int err = 0;
288 int fpvalid;
289
290 err |= __get_user (fpvalid, &sc->sc_fpvalid);
291 conditional_used_math(fpvalid);
292 if (! fpvalid)
293 return err;
294
295 if (current == last_task_used_math) {
296 last_task_used_math = NULL;
297 regs->sr |= SR_FD;
298 }
299
300 err |= __copy_from_user(¤t->thread.xstate->hardfpu, &sc->sc_fpregs[0],
301 (sizeof(long long) * 32) + (sizeof(int) * 1));
302
303 return err;
304}
305
306static inline int
307setup_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
308{
309 int err = 0;
310 int fpvalid;
311
312 fpvalid = !!used_math();
313 err |= __put_user(fpvalid, &sc->sc_fpvalid);
314 if (! fpvalid)
315 return err;
316
317 if (current == last_task_used_math) {
318 enable_fpu();
319 save_fpu(current);
320 disable_fpu();
321 last_task_used_math = NULL;
322 regs->sr |= SR_FD;
323 }
324
325 err |= __copy_to_user(&sc->sc_fpregs[0], ¤t->thread.xstate->hardfpu,
326 (sizeof(long long) * 32) + (sizeof(int) * 1));
327 clear_used_math();
328
329 return err;
330}
331#else
332static inline int
333restore_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
334{
335 return 0;
336}
337static inline int
338setup_sigcontext_fpu(struct pt_regs *regs, struct sigcontext __user *sc)
339{
340 return 0;
341}
342#endif
343
344static int
345restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc, long long *r2_p)
346{
347 unsigned int err = 0;
348 unsigned long long current_sr, new_sr;
349#define SR_MASK 0xffff8cfd
350
351#define COPY(x) err |= __get_user(regs->x, &sc->sc_##x)
352
353 COPY(regs[0]); COPY(regs[1]); COPY(regs[2]); COPY(regs[3]);
354 COPY(regs[4]); COPY(regs[5]); COPY(regs[6]); COPY(regs[7]);
355 COPY(regs[8]); COPY(regs[9]); COPY(regs[10]); COPY(regs[11]);
356 COPY(regs[12]); COPY(regs[13]); COPY(regs[14]); COPY(regs[15]);
357 COPY(regs[16]); COPY(regs[17]); COPY(regs[18]); COPY(regs[19]);
358 COPY(regs[20]); COPY(regs[21]); COPY(regs[22]); COPY(regs[23]);
359 COPY(regs[24]); COPY(regs[25]); COPY(regs[26]); COPY(regs[27]);
360 COPY(regs[28]); COPY(regs[29]); COPY(regs[30]); COPY(regs[31]);
361 COPY(regs[32]); COPY(regs[33]); COPY(regs[34]); COPY(regs[35]);
362 COPY(regs[36]); COPY(regs[37]); COPY(regs[38]); COPY(regs[39]);
363 COPY(regs[40]); COPY(regs[41]); COPY(regs[42]); COPY(regs[43]);
364 COPY(regs[44]); COPY(regs[45]); COPY(regs[46]); COPY(regs[47]);
365 COPY(regs[48]); COPY(regs[49]); COPY(regs[50]); COPY(regs[51]);
366 COPY(regs[52]); COPY(regs[53]); COPY(regs[54]); COPY(regs[55]);
367 COPY(regs[56]); COPY(regs[57]); COPY(regs[58]); COPY(regs[59]);
368 COPY(regs[60]); COPY(regs[61]); COPY(regs[62]);
369 COPY(tregs[0]); COPY(tregs[1]); COPY(tregs[2]); COPY(tregs[3]);
370 COPY(tregs[4]); COPY(tregs[5]); COPY(tregs[6]); COPY(tregs[7]);
371
372 /* Prevent the signal handler manipulating SR in a way that can
373 crash the kernel. i.e. only allow S, Q, M, PR, SZ, FR to be
374 modified */
375 current_sr = regs->sr;
376 err |= __get_user(new_sr, &sc->sc_sr);
377 regs->sr &= SR_MASK;
378 regs->sr |= (new_sr & ~SR_MASK);
379
380 COPY(pc);
381
382#undef COPY
383
384 /* Must do this last in case it sets regs->sr.fd (i.e. after rest of sr
385 * has been restored above.) */
386 err |= restore_sigcontext_fpu(regs, sc);
387
388 regs->syscall_nr = -1; /* disable syscall checks */
389 err |= __get_user(*r2_p, &sc->sc_regs[REG_RET]);
390 return err;
391}
392
393asmlinkage int sys_sigreturn(unsigned long r2, unsigned long r3,
394 unsigned long r4, unsigned long r5,
395 unsigned long r6, unsigned long r7,
396 struct pt_regs * regs)
397{
398 struct sigframe __user *frame = (struct sigframe __user *) (long) REF_REG_SP;
399 sigset_t set;
400 long long ret;
401
402 /* Always make any pending restarted system calls return -EINTR */
403 current_thread_info()->restart_block.fn = do_no_restart_syscall;
404
405 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
406 goto badframe;
407
408 if (__get_user(set.sig[0], &frame->sc.oldmask)
409 || (_NSIG_WORDS > 1
410 && __copy_from_user(&set.sig[1], &frame->extramask,
411 sizeof(frame->extramask))))
412 goto badframe;
413
414 sigdelsetmask(&set, ~_BLOCKABLE);
415
416 spin_lock_irq(¤t->sighand->siglock);
417 current->blocked = set;
418 recalc_sigpending();
419 spin_unlock_irq(¤t->sighand->siglock);
420
421 if (restore_sigcontext(regs, &frame->sc, &ret))
422 goto badframe;
423 regs->pc -= 4;
424
425 return (int) ret;
426
427badframe:
428 force_sig(SIGSEGV, current);
429 return 0;
430}
431
432asmlinkage int sys_rt_sigreturn(unsigned long r2, unsigned long r3,
433 unsigned long r4, unsigned long r5,
434 unsigned long r6, unsigned long r7,
435 struct pt_regs * regs)
436{
437 struct rt_sigframe __user *frame = (struct rt_sigframe __user *) (long) REF_REG_SP;
438 sigset_t set;
439 stack_t __user st;
440 long long ret;
441
442 /* Always make any pending restarted system calls return -EINTR */
443 current_thread_info()->restart_block.fn = do_no_restart_syscall;
444
445 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
446 goto badframe;
447
448 if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set)))
449 goto badframe;
450
451 sigdelsetmask(&set, ~_BLOCKABLE);
452 spin_lock_irq(¤t->sighand->siglock);
453 current->blocked = set;
454 recalc_sigpending();
455 spin_unlock_irq(¤t->sighand->siglock);
456
457 if (restore_sigcontext(regs, &frame->uc.uc_mcontext, &ret))
458 goto badframe;
459 regs->pc -= 4;
460
461 if (__copy_from_user(&st, &frame->uc.uc_stack, sizeof(st)))
462 goto badframe;
463 /* It is more difficult to avoid calling this function than to
464 call it and ignore errors. */
465 do_sigaltstack(&st, NULL, REF_REG_SP);
466
467 return (int) ret;
468
469badframe:
470 force_sig(SIGSEGV, current);
471 return 0;
472}
473
474/*
475 * Set up a signal frame.
476 */
477static int
478setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs,
479 unsigned long mask)
480{
481 int err = 0;
482
483 /* Do this first, otherwise is this sets sr->fd, that value isn't preserved. */
484 err |= setup_sigcontext_fpu(regs, sc);
485
486#define COPY(x) err |= __put_user(regs->x, &sc->sc_##x)
487
488 COPY(regs[0]); COPY(regs[1]); COPY(regs[2]); COPY(regs[3]);
489 COPY(regs[4]); COPY(regs[5]); COPY(regs[6]); COPY(regs[7]);
490 COPY(regs[8]); COPY(regs[9]); COPY(regs[10]); COPY(regs[11]);
491 COPY(regs[12]); COPY(regs[13]); COPY(regs[14]); COPY(regs[15]);
492 COPY(regs[16]); COPY(regs[17]); COPY(regs[18]); COPY(regs[19]);
493 COPY(regs[20]); COPY(regs[21]); COPY(regs[22]); COPY(regs[23]);
494 COPY(regs[24]); COPY(regs[25]); COPY(regs[26]); COPY(regs[27]);
495 COPY(regs[28]); COPY(regs[29]); COPY(regs[30]); COPY(regs[31]);
496 COPY(regs[32]); COPY(regs[33]); COPY(regs[34]); COPY(regs[35]);
497 COPY(regs[36]); COPY(regs[37]); COPY(regs[38]); COPY(regs[39]);
498 COPY(regs[40]); COPY(regs[41]); COPY(regs[42]); COPY(regs[43]);
499 COPY(regs[44]); COPY(regs[45]); COPY(regs[46]); COPY(regs[47]);
500 COPY(regs[48]); COPY(regs[49]); COPY(regs[50]); COPY(regs[51]);
501 COPY(regs[52]); COPY(regs[53]); COPY(regs[54]); COPY(regs[55]);
502 COPY(regs[56]); COPY(regs[57]); COPY(regs[58]); COPY(regs[59]);
503 COPY(regs[60]); COPY(regs[61]); COPY(regs[62]);
504 COPY(tregs[0]); COPY(tregs[1]); COPY(tregs[2]); COPY(tregs[3]);
505 COPY(tregs[4]); COPY(tregs[5]); COPY(tregs[6]); COPY(tregs[7]);
506 COPY(sr); COPY(pc);
507
508#undef COPY
509
510 err |= __put_user(mask, &sc->oldmask);
511
512 return err;
513}
514
515/*
516 * Determine which stack to use..
517 */
518static inline void __user *
519get_sigframe(struct k_sigaction *ka, unsigned long sp, size_t frame_size)
520{
521 if ((ka->sa.sa_flags & SA_ONSTACK) != 0 && ! sas_ss_flags(sp))
522 sp = current->sas_ss_sp + current->sas_ss_size;
523
524 return (void __user *)((sp - frame_size) & -8ul);
525}
526
527void sa_default_restorer(void); /* See comments below */
528void sa_default_rt_restorer(void); /* See comments below */
529
530static int setup_frame(int sig, struct k_sigaction *ka,
531 sigset_t *set, struct pt_regs *regs)
532{
533 struct sigframe __user *frame;
534 int err = 0;
535 int signal;
536
537 frame = get_sigframe(ka, regs->regs[REG_SP], sizeof(*frame));
538
539 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
540 goto give_sigsegv;
541
542 signal = current_thread_info()->exec_domain
543 && current_thread_info()->exec_domain->signal_invmap
544 && sig < 32
545 ? current_thread_info()->exec_domain->signal_invmap[sig]
546 : sig;
547
548 err |= setup_sigcontext(&frame->sc, regs, set->sig[0]);
549
550 /* Give up earlier as i386, in case */
551 if (err)
552 goto give_sigsegv;
553
554 if (_NSIG_WORDS > 1) {
555 err |= __copy_to_user(frame->extramask, &set->sig[1],
556 sizeof(frame->extramask)); }
557
558 /* Give up earlier as i386, in case */
559 if (err)
560 goto give_sigsegv;
561
562 /* Set up to return from userspace. If provided, use a stub
563 already in userspace. */
564 if (ka->sa.sa_flags & SA_RESTORER) {
565 /*
566 * On SH5 all edited pointers are subject to NEFF
567 */
568 DEREF_REG_PR = neff_sign_extend((unsigned long)
569 ka->sa.sa_restorer | 0x1);
570 } else {
571 /*
572 * Different approach on SH5.
573 * . Endianness independent asm code gets placed in entry.S .
574 * This is limited to four ASM instructions corresponding
575 * to two long longs in size.
576 * . err checking is done on the else branch only
577 * . flush_icache_range() is called upon __put_user() only
578 * . all edited pointers are subject to NEFF
579 * . being code, linker turns ShMedia bit on, always
580 * dereference index -1.
581 */
582 DEREF_REG_PR = neff_sign_extend((unsigned long)
583 frame->retcode | 0x01);
584
585 if (__copy_to_user(frame->retcode,
586 (void *)((unsigned long)sa_default_restorer & (~1)), 16) != 0)
587 goto give_sigsegv;
588
589 /* Cohere the trampoline with the I-cache. */
590 flush_cache_sigtramp(DEREF_REG_PR-1);
591 }
592
593 /*
594 * Set up registers for signal handler.
595 * All edited pointers are subject to NEFF.
596 */
597 regs->regs[REG_SP] = neff_sign_extend((unsigned long)frame);
598 regs->regs[REG_ARG1] = signal; /* Arg for signal handler */
599
600 /* FIXME:
601 The glibc profiling support for SH-5 needs to be passed a sigcontext
602 so it can retrieve the PC. At some point during 2003 the glibc
603 support was changed to receive the sigcontext through the 2nd
604 argument, but there are still versions of libc.so in use that use
605 the 3rd argument. Until libc.so is stabilised, pass the sigcontext
606 through both 2nd and 3rd arguments.
607 */
608
609 regs->regs[REG_ARG2] = (unsigned long long)(unsigned long)(signed long)&frame->sc;
610 regs->regs[REG_ARG3] = (unsigned long long)(unsigned long)(signed long)&frame->sc;
611
612 regs->pc = neff_sign_extend((unsigned long)ka->sa.sa_handler);
613
614 set_fs(USER_DS);
615
616 /* Broken %016Lx */
617 pr_debug("SIG deliver (#%d,%s:%d): sp=%p pc=%08Lx%08Lx link=%08Lx%08Lx\n",
618 signal, current->comm, current->pid, frame,
619 regs->pc >> 32, regs->pc & 0xffffffff,
620 DEREF_REG_PR >> 32, DEREF_REG_PR & 0xffffffff);
621
622 return 0;
623
624give_sigsegv:
625 force_sigsegv(sig, current);
626 return -EFAULT;
627}
628
629static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info,
630 sigset_t *set, struct pt_regs *regs)
631{
632 struct rt_sigframe __user *frame;
633 int err = 0;
634 int signal;
635
636 frame = get_sigframe(ka, regs->regs[REG_SP], sizeof(*frame));
637
638 if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
639 goto give_sigsegv;
640
641 signal = current_thread_info()->exec_domain
642 && current_thread_info()->exec_domain->signal_invmap
643 && sig < 32
644 ? current_thread_info()->exec_domain->signal_invmap[sig]
645 : sig;
646
647 err |= __put_user(&frame->info, &frame->pinfo);
648 err |= __put_user(&frame->uc, &frame->puc);
649 err |= copy_siginfo_to_user(&frame->info, info);
650
651 /* Give up earlier as i386, in case */
652 if (err)
653 goto give_sigsegv;
654
655 /* Create the ucontext. */
656 err |= __put_user(0, &frame->uc.uc_flags);
657 err |= __put_user(0, &frame->uc.uc_link);
658 err |= __put_user((void *)current->sas_ss_sp,
659 &frame->uc.uc_stack.ss_sp);
660 err |= __put_user(sas_ss_flags(regs->regs[REG_SP]),
661 &frame->uc.uc_stack.ss_flags);
662 err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size);
663 err |= setup_sigcontext(&frame->uc.uc_mcontext,
664 regs, set->sig[0]);
665 err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));
666
667 /* Give up earlier as i386, in case */
668 if (err)
669 goto give_sigsegv;
670
671 /* Set up to return from userspace. If provided, use a stub
672 already in userspace. */
673 if (ka->sa.sa_flags & SA_RESTORER) {
674 /*
675 * On SH5 all edited pointers are subject to NEFF
676 */
677 DEREF_REG_PR = neff_sign_extend((unsigned long)
678 ka->sa.sa_restorer | 0x1);
679 } else {
680 /*
681 * Different approach on SH5.
682 * . Endianness independent asm code gets placed in entry.S .
683 * This is limited to four ASM instructions corresponding
684 * to two long longs in size.
685 * . err checking is done on the else branch only
686 * . flush_icache_range() is called upon __put_user() only
687 * . all edited pointers are subject to NEFF
688 * . being code, linker turns ShMedia bit on, always
689 * dereference index -1.
690 */
691 DEREF_REG_PR = neff_sign_extend((unsigned long)
692 frame->retcode | 0x01);
693
694 if (__copy_to_user(frame->retcode,
695 (void *)((unsigned long)sa_default_rt_restorer & (~1)), 16) != 0)
696 goto give_sigsegv;
697
698 /* Cohere the trampoline with the I-cache. */
699 flush_icache_range(DEREF_REG_PR-1, DEREF_REG_PR-1+15);
700 }
701
702 /*
703 * Set up registers for signal handler.
704 * All edited pointers are subject to NEFF.
705 */
706 regs->regs[REG_SP] = neff_sign_extend((unsigned long)frame);
707 regs->regs[REG_ARG1] = signal; /* Arg for signal handler */
708 regs->regs[REG_ARG2] = (unsigned long long)(unsigned long)(signed long)&frame->info;
709 regs->regs[REG_ARG3] = (unsigned long long)(unsigned long)(signed long)&frame->uc.uc_mcontext;
710 regs->pc = neff_sign_extend((unsigned long)ka->sa.sa_handler);
711
712 set_fs(USER_DS);
713
714 pr_debug("SIG deliver (#%d,%s:%d): sp=%p pc=%08Lx%08Lx link=%08Lx%08Lx\n",
715 signal, current->comm, current->pid, frame,
716 regs->pc >> 32, regs->pc & 0xffffffff,
717 DEREF_REG_PR >> 32, DEREF_REG_PR & 0xffffffff);
718
719 return 0;
720
721give_sigsegv:
722 force_sigsegv(sig, current);
723 return -EFAULT;
724}
725
726/*
727 * OK, we're invoking a handler
728 */
729static int
730handle_signal(unsigned long sig, siginfo_t *info, struct k_sigaction *ka,
731 sigset_t *oldset, struct pt_regs * regs)
732{
733 int ret;
734
735 /* Set up the stack frame */
736 if (ka->sa.sa_flags & SA_SIGINFO)
737 ret = setup_rt_frame(sig, ka, info, oldset, regs);
738 else
739 ret = setup_frame(sig, ka, oldset, regs);
740
741 if (ka->sa.sa_flags & SA_ONESHOT)
742 ka->sa.sa_handler = SIG_DFL;
743
744 if (ret == 0) {
745 spin_lock_irq(¤t->sighand->siglock);
746 sigorsets(¤t->blocked,¤t->blocked,&ka->sa.sa_mask);
747 if (!(ka->sa.sa_flags & SA_NODEFER))
748 sigaddset(¤t->blocked,sig);
749 recalc_sigpending();
750 spin_unlock_irq(¤t->sighand->siglock);
751 }
752
753 return ret;
754}
755
756asmlinkage void do_notify_resume(struct pt_regs *regs, unsigned long thread_info_flags)
757{
758 if (thread_info_flags & _TIF_SIGPENDING)
759 do_signal(regs, 0);
760
761 if (thread_info_flags & _TIF_NOTIFY_RESUME) {
762 clear_thread_flag(TIF_NOTIFY_RESUME);
763 tracehook_notify_resume(regs);
764 if (current->replacement_session_keyring)
765 key_replace_session_keyring();
766 }
767}