Merge 3.16-rc5 into char-misc-next
[deliverable/linux.git] / arch / mips / kernel / signal32.c
CommitLineData
1da177e4
LT
1/*
2 * This file is subject to the terms and conditions of the GNU General Public
3 * License. See the file "COPYING" in the main directory of this archive
4 * for more details.
5 *
6 * Copyright (C) 1991, 1992 Linus Torvalds
dda73d0b 7 * Copyright (C) 1994 - 2000, 2006 Ralf Baechle
1da177e4
LT
8 * Copyright (C) 1999, 2000 Silicon Graphics, Inc.
9 */
02416dcf 10#include <linux/cache.h>
431dc804 11#include <linux/compat.h>
1da177e4
LT
12#include <linux/sched.h>
13#include <linux/mm.h>
14#include <linux/smp.h>
1da177e4
LT
15#include <linux/kernel.h>
16#include <linux/signal.h>
17#include <linux/syscalls.h>
18#include <linux/errno.h>
19#include <linux/wait.h>
20#include <linux/ptrace.h>
1da177e4
LT
21#include <linux/suspend.h>
22#include <linux/compiler.h>
faea6234 23#include <linux/uaccess.h>
1da177e4 24
e50c0a8f 25#include <asm/abi.h>
1da177e4 26#include <asm/asm.h>
431dc804 27#include <asm/compat-signal.h>
1da177e4
LT
28#include <linux/bitops.h>
29#include <asm/cacheflush.h>
30#include <asm/sim.h>
1da177e4 31#include <asm/ucontext.h>
1da177e4 32#include <asm/fpu.h>
02416dcf 33#include <asm/war.h>
d814c28c 34#include <asm/vdso.h>
b81947c6 35#include <asm/dsp.h>
1da177e4 36
36a1f2c2
FBH
37#include "signal-common.h"
38
137f6f3e
RB
39static int (*save_fp_context32)(struct sigcontext32 __user *sc);
40static int (*restore_fp_context32)(struct sigcontext32 __user *sc);
41
42extern asmlinkage int _save_fp_context32(struct sigcontext32 __user *sc);
43extern asmlinkage int _restore_fp_context32(struct sigcontext32 __user *sc);
44
1da177e4
LT
45/*
46 * Including <asm/unistd.h> would give use the 64-bit syscall numbers ...
47 */
70342287 48#define __NR_O32_restart_syscall 4253
1da177e4 49
1da177e4
LT
50/* 32-bit compatibility types */
51
1da177e4
LT
52typedef unsigned int __sighandler32_t;
53typedef void (*vfptr_t)(void);
54
1da177e4 55struct ucontext32 {
70342287
RB
56 u32 uc_flags;
57 s32 uc_link;
ea536ad4 58 compat_stack_t uc_stack;
1da177e4 59 struct sigcontext32 uc_mcontext;
70342287 60 compat_sigset_t uc_sigmask; /* mask last for extensibility */
1da177e4
LT
61};
62
dd02f06a
RB
63struct sigframe32 {
64 u32 sf_ass[4]; /* argument save space for o32 */
d814c28c 65 u32 sf_pad[2]; /* Was: signal trampoline */
dd02f06a 66 struct sigcontext32 sf_sc;
755f21bb 67 compat_sigset_t sf_mask;
dd02f06a
RB
68};
69
c0b9bae9
FBH
70struct rt_sigframe32 {
71 u32 rs_ass[4]; /* argument save space for o32 */
d814c28c 72 u32 rs_pad[2]; /* Was: signal trampoline */
c0b9bae9
FBH
73 compat_siginfo_t rs_info;
74 struct ucontext32 rs_uc;
75};
76
b2ead528
PB
77/*
78 * Thread saved context copy to/from a signal context presumed to be on the
79 * user stack, and therefore accessed with appropriate macros from uaccess.h.
80 */
81static int copy_fp_to_sigcontext32(struct sigcontext32 __user *sc)
82{
83 int i;
84 int err = 0;
85 int inc = test_thread_flag(TIF_32BIT_FPREGS) ? 2 : 1;
86
6bbfd65e 87 for (i = 0; i < NUM_FPU_REGS; i += inc) {
b2ead528
PB
88 err |=
89 __put_user(get_fpr64(&current->thread.fpu.fpr[i], 0),
90 &sc->sc_fpregs[i]);
91 }
92 err |= __put_user(current->thread.fpu.fcr31, &sc->sc_fpc_csr);
93
94 return err;
95}
96
97static int copy_fp_from_sigcontext32(struct sigcontext32 __user *sc)
98{
99 int i;
100 int err = 0;
101 int inc = test_thread_flag(TIF_32BIT_FPREGS) ? 2 : 1;
102 u64 fpr_val;
103
6bbfd65e 104 for (i = 0; i < NUM_FPU_REGS; i += inc) {
b2ead528
PB
105 err |= __get_user(fpr_val, &sc->sc_fpregs[i]);
106 set_fpr64(&current->thread.fpu.fpr[i], 0, fpr_val);
107 }
108 err |= __get_user(current->thread.fpu.fcr31, &sc->sc_fpc_csr);
109
110 return err;
111}
112
9432a9ba
FBH
113/*
114 * sigcontext handlers
115 */
16f77de8 116static int protected_save_fp_context32(struct sigcontext32 __user *sc)
faea6234
AN
117{
118 int err;
119 while (1) {
120 lock_fpu_owner();
ff3aa5f2
PB
121 if (is_fpu_owner()) {
122 err = save_fp_context32(sc);
123 unlock_fpu_owner();
124 } else {
125 unlock_fpu_owner();
126 err = copy_fp_to_sigcontext32(sc);
127 }
faea6234
AN
128 if (likely(!err))
129 break;
130 /* touch the sigcontext and try again */
131 err = __put_user(0, &sc->sc_fpregs[0]) |
132 __put_user(0, &sc->sc_fpregs[31]) |
133 __put_user(0, &sc->sc_fpc_csr);
134 if (err)
135 break; /* really bad sigcontext */
136 }
137 return err;
138}
139
16f77de8 140static int protected_restore_fp_context32(struct sigcontext32 __user *sc)
faea6234 141{
c726b822 142 int err, tmp __maybe_unused;
faea6234
AN
143 while (1) {
144 lock_fpu_owner();
ff3aa5f2
PB
145 if (is_fpu_owner()) {
146 err = restore_fp_context32(sc);
147 unlock_fpu_owner();
148 } else {
149 unlock_fpu_owner();
150 err = copy_fp_from_sigcontext32(sc);
151 }
faea6234
AN
152 if (likely(!err))
153 break;
154 /* touch the sigcontext and try again */
155 err = __get_user(tmp, &sc->sc_fpregs[0]) |
156 __get_user(tmp, &sc->sc_fpregs[31]) |
157 __get_user(tmp, &sc->sc_fpc_csr);
158 if (err)
159 break; /* really bad sigcontext */
160 }
161 return err;
162}
163
9432a9ba
FBH
164static int setup_sigcontext32(struct pt_regs *regs,
165 struct sigcontext32 __user *sc)
166{
167 int err = 0;
168 int i;
53dc8028 169 u32 used_math;
9432a9ba
FBH
170
171 err |= __put_user(regs->cp0_epc, &sc->sc_pc);
9432a9ba
FBH
172
173 err |= __put_user(0, &sc->sc_regs[0]);
174 for (i = 1; i < 32; i++)
175 err |= __put_user(regs->regs[i], &sc->sc_regs[i]);
176
177 err |= __put_user(regs->hi, &sc->sc_mdhi);
178 err |= __put_user(regs->lo, &sc->sc_mdlo);
179 if (cpu_has_dsp) {
180 err |= __put_user(rddsp(DSP_MASK), &sc->sc_dsp);
181 err |= __put_user(mfhi1(), &sc->sc_hi1);
182 err |= __put_user(mflo1(), &sc->sc_lo1);
183 err |= __put_user(mfhi2(), &sc->sc_hi2);
184 err |= __put_user(mflo2(), &sc->sc_lo2);
185 err |= __put_user(mfhi3(), &sc->sc_hi3);
186 err |= __put_user(mflo3(), &sc->sc_lo3);
187 }
188
16f77de8 189 used_math = !!used_math();
53dc8028 190 err |= __put_user(used_math, &sc->sc_used_math);
9432a9ba 191
53dc8028 192 if (used_math) {
9432a9ba
FBH
193 /*
194 * Save FPU state to signal context. Signal handler
195 * will "inherit" current FPU state.
196 */
16f77de8 197 err |= protected_save_fp_context32(sc);
9432a9ba
FBH
198 }
199 return err;
200}
201
c6a2f467 202static int
16f77de8 203check_and_restore_fp_context32(struct sigcontext32 __user *sc)
c6a2f467
AN
204{
205 int err, sig;
206
207 err = sig = fpcsr_pending(&sc->sc_fpc_csr);
208 if (err > 0)
209 err = 0;
16f77de8 210 err |= protected_restore_fp_context32(sc);
c6a2f467
AN
211 return err ?: sig;
212}
213
9432a9ba
FBH
214static int restore_sigcontext32(struct pt_regs *regs,
215 struct sigcontext32 __user *sc)
216{
217 u32 used_math;
218 int err = 0;
219 s32 treg;
220 int i;
221
222 /* Always make any pending restarted system calls return -EINTR */
223 current_thread_info()->restart_block.fn = do_no_restart_syscall;
224
225 err |= __get_user(regs->cp0_epc, &sc->sc_pc);
226 err |= __get_user(regs->hi, &sc->sc_mdhi);
227 err |= __get_user(regs->lo, &sc->sc_mdlo);
228 if (cpu_has_dsp) {
229 err |= __get_user(treg, &sc->sc_hi1); mthi1(treg);
230 err |= __get_user(treg, &sc->sc_lo1); mtlo1(treg);
231 err |= __get_user(treg, &sc->sc_hi2); mthi2(treg);
232 err |= __get_user(treg, &sc->sc_lo2); mtlo2(treg);
233 err |= __get_user(treg, &sc->sc_hi3); mthi3(treg);
234 err |= __get_user(treg, &sc->sc_lo3); mtlo3(treg);
235 err |= __get_user(treg, &sc->sc_dsp); wrdsp(treg, DSP_MASK);
236 }
237
238 for (i = 1; i < 32; i++)
239 err |= __get_user(regs->regs[i], &sc->sc_regs[i]);
240
241 err |= __get_user(used_math, &sc->sc_used_math);
242 conditional_used_math(used_math);
243
53dc8028 244 if (used_math) {
9432a9ba 245 /* restore fpu context if we have used it before */
c6a2f467 246 if (!err)
16f77de8 247 err = check_and_restore_fp_context32(sc);
9432a9ba 248 } else {
16f77de8 249 /* signal handler may have used FPU. Give it up. */
53dc8028 250 lose_fpu(0);
9432a9ba
FBH
251 }
252
9432a9ba
FBH
253 return err;
254}
255
256/*
257 *
258 */
1da177e4
LT
259extern void __put_sigset_unknown_nsig(void);
260extern void __get_sigset_unknown_nsig(void);
261
9bbf28a3 262static inline int put_sigset(const sigset_t *kbuf, compat_sigset_t __user *ubuf)
1da177e4
LT
263{
264 int err = 0;
265
266 if (!access_ok(VERIFY_WRITE, ubuf, sizeof(*ubuf)))
267 return -EFAULT;
268
269 switch (_NSIG_WORDS) {
270 default:
271 __put_sigset_unknown_nsig();
272 case 2:
49a89efb
RB
273 err |= __put_user(kbuf->sig[1] >> 32, &ubuf->sig[3]);
274 err |= __put_user(kbuf->sig[1] & 0xffffffff, &ubuf->sig[2]);
1da177e4 275 case 1:
49a89efb
RB
276 err |= __put_user(kbuf->sig[0] >> 32, &ubuf->sig[1]);
277 err |= __put_user(kbuf->sig[0] & 0xffffffff, &ubuf->sig[0]);
1da177e4
LT
278 }
279
280 return err;
281}
282
9c6031cc 283static inline int get_sigset(sigset_t *kbuf, const compat_sigset_t __user *ubuf)
1da177e4
LT
284{
285 int err = 0;
286 unsigned long sig[4];
287
288 if (!access_ok(VERIFY_READ, ubuf, sizeof(*ubuf)))
289 return -EFAULT;
290
291 switch (_NSIG_WORDS) {
292 default:
293 __get_sigset_unknown_nsig();
294 case 2:
49a89efb
RB
295 err |= __get_user(sig[3], &ubuf->sig[3]);
296 err |= __get_user(sig[2], &ubuf->sig[2]);
1da177e4
LT
297 kbuf->sig[1] = sig[2] | (sig[3] << 32);
298 case 1:
49a89efb
RB
299 err |= __get_user(sig[1], &ubuf->sig[1]);
300 err |= __get_user(sig[0], &ubuf->sig[0]);
1da177e4
LT
301 kbuf->sig[0] = sig[0] | (sig[1] << 32);
302 }
303
304 return err;
305}
306
307/*
308 * Atomically swap in the new signal mask, and wait for a signal.
309 */
310
1910f4ab 311asmlinkage int sys32_sigsuspend(compat_sigset_t __user *uset)
1da177e4 312{
1910f4ab 313 return compat_sys_rt_sigsuspend(uset, sizeof(compat_sigset_t));
1da177e4
LT
314}
315
aa584802
AV
316SYSCALL_DEFINE3(32_sigaction, long, sig, const struct compat_sigaction __user *, act,
317 struct compat_sigaction __user *, oact)
1da177e4
LT
318{
319 struct k_sigaction new_ka, old_ka;
320 int ret;
321 int err = 0;
322
323 if (act) {
324 old_sigset_t mask;
77c728c2 325 s32 handler;
1da177e4
LT
326
327 if (!access_ok(VERIFY_READ, act, sizeof(*act)))
328 return -EFAULT;
77c728c2 329 err |= __get_user(handler, &act->sa_handler);
9bbf28a3 330 new_ka.sa.sa_handler = (void __user *)(s64)handler;
1da177e4
LT
331 err |= __get_user(new_ka.sa.sa_flags, &act->sa_flags);
332 err |= __get_user(mask, &act->sa_mask.sig[0]);
333 if (err)
334 return -EFAULT;
335
336 siginitset(&new_ka.sa.sa_mask, mask);
337 }
338
339 ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL);
340
341 if (!ret && oact) {
342 if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)))
6254944f 343 return -EFAULT;
1da177e4
LT
344 err |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags);
345 err |= __put_user((u32)(u64)old_ka.sa.sa_handler,
70342287 346 &oact->sa_handler);
1da177e4 347 err |= __put_user(old_ka.sa.sa_mask.sig[0], oact->sa_mask.sig);
6254944f
MM
348 err |= __put_user(0, &oact->sa_mask.sig[1]);
349 err |= __put_user(0, &oact->sa_mask.sig[2]);
350 err |= __put_user(0, &oact->sa_mask.sig[3]);
351 if (err)
1da177e4
LT
352 return -EFAULT;
353 }
354
355 return ret;
356}
357
ce395960 358int copy_siginfo_to_user32(compat_siginfo_t __user *to, const siginfo_t *from)
1da177e4
LT
359{
360 int err;
361
362 if (!access_ok (VERIFY_WRITE, to, sizeof(compat_siginfo_t)))
363 return -EFAULT;
364
365 /* If you change siginfo_t structure, please be sure
366 this code is fixed accordingly.
367 It should never copy any pad contained in the structure
368 to avoid security leaks, but must copy the generic
369 3 ints plus the relevant union member.
370 This routine must convert siginfo from 64bit to 32bit as well
371 at the same time. */
372 err = __put_user(from->si_signo, &to->si_signo);
373 err |= __put_user(from->si_errno, &to->si_errno);
374 err |= __put_user((short)from->si_code, &to->si_code);
375 if (from->si_code < 0)
376 err |= __copy_to_user(&to->_sifields._pad, &from->_sifields._pad, SI_PAD_SIZE);
377 else {
378 switch (from->si_code >> 16) {
a982099c
RB
379 case __SI_TIMER >> 16:
380 err |= __put_user(from->si_tid, &to->si_tid);
381 err |= __put_user(from->si_overrun, &to->si_overrun);
382 err |= __put_user(from->si_int, &to->si_int);
383 break;
1da177e4
LT
384 case __SI_CHLD >> 16:
385 err |= __put_user(from->si_utime, &to->si_utime);
386 err |= __put_user(from->si_stime, &to->si_stime);
387 err |= __put_user(from->si_status, &to->si_status);
388 default:
389 err |= __put_user(from->si_pid, &to->si_pid);
390 err |= __put_user(from->si_uid, &to->si_uid);
391 break;
392 case __SI_FAULT >> 16:
5665a0ac 393 err |= __put_user((unsigned long)from->si_addr, &to->si_addr);
1da177e4
LT
394 break;
395 case __SI_POLL >> 16:
396 err |= __put_user(from->si_band, &to->si_band);
397 err |= __put_user(from->si_fd, &to->si_fd);
398 break;
399 case __SI_RT >> 16: /* This is not generated by the kernel as of now. */
400 case __SI_MESGQ >> 16:
401 err |= __put_user(from->si_pid, &to->si_pid);
402 err |= __put_user(from->si_uid, &to->si_uid);
403 err |= __put_user(from->si_int, &to->si_int);
404 break;
405 }
406 }
407 return err;
408}
409
5d9a76cd
TB
410int copy_siginfo_from_user32(siginfo_t *to, compat_siginfo_t __user *from)
411{
412 memset(to, 0, sizeof *to);
413
414 if (copy_from_user(to, from, 3*sizeof(int)) ||
415 copy_from_user(to->_sifields._pad,
416 from->_sifields._pad, SI_PAD_SIZE32))
417 return -EFAULT;
418
419 return 0;
420}
421
f90080a0 422asmlinkage void sys32_sigreturn(nabi_no_regargs struct pt_regs regs)
1da177e4 423{
dd02f06a 424 struct sigframe32 __user *frame;
1da177e4 425 sigset_t blocked;
c6a2f467 426 int sig;
1da177e4 427
dd02f06a 428 frame = (struct sigframe32 __user *) regs.regs[29];
1da177e4
LT
429 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
430 goto badframe;
431dc804 431 if (__copy_conv_sigset_from_user(&blocked, &frame->sf_mask))
1da177e4
LT
432 goto badframe;
433
8598f3cd 434 set_current_blocked(&blocked);
1da177e4 435
c6a2f467
AN
436 sig = restore_sigcontext32(&regs, &frame->sf_sc);
437 if (sig < 0)
1da177e4 438 goto badframe;
c6a2f467
AN
439 else if (sig)
440 force_sig(sig, current);
1da177e4
LT
441
442 /*
443 * Don't let your children do this ...
444 */
1da177e4
LT
445 __asm__ __volatile__(
446 "move\t$29, %0\n\t"
447 "j\tsyscall_exit"
448 :/* no outputs */
449 :"r" (&regs));
450 /* Unreached */
451
452badframe:
453 force_sig(SIGSEGV, current);
454}
455
f90080a0 456asmlinkage void sys32_rt_sigreturn(nabi_no_regargs struct pt_regs regs)
1da177e4 457{
9bbf28a3 458 struct rt_sigframe32 __user *frame;
1da177e4 459 sigset_t set;
c6a2f467 460 int sig;
1da177e4 461
9bbf28a3 462 frame = (struct rt_sigframe32 __user *) regs.regs[29];
1da177e4
LT
463 if (!access_ok(VERIFY_READ, frame, sizeof(*frame)))
464 goto badframe;
431dc804 465 if (__copy_conv_sigset_from_user(&set, &frame->rs_uc.uc_sigmask))
1da177e4
LT
466 goto badframe;
467
8598f3cd 468 set_current_blocked(&set);
1da177e4 469
c6a2f467
AN
470 sig = restore_sigcontext32(&regs, &frame->rs_uc.uc_mcontext);
471 if (sig < 0)
1da177e4 472 goto badframe;
c6a2f467
AN
473 else if (sig)
474 force_sig(sig, current);
1da177e4 475
ea536ad4 476 if (compat_restore_altstack(&frame->rs_uc.uc_stack))
1da177e4 477 goto badframe;
1da177e4
LT
478
479 /*
480 * Don't let your children do this ...
481 */
482 __asm__ __volatile__(
483 "move\t$29, %0\n\t"
484 "j\tsyscall_exit"
485 :/* no outputs */
486 :"r" (&regs));
487 /* Unreached */
488
489badframe:
490 force_sig(SIGSEGV, current);
491}
492
d814c28c
DD
493static int setup_frame_32(void *sig_return, struct k_sigaction *ka,
494 struct pt_regs *regs, int signr, sigset_t *set)
1da177e4 495{
dd02f06a 496 struct sigframe32 __user *frame;
1da177e4
LT
497 int err = 0;
498
499 frame = get_sigframe(ka, regs, sizeof(*frame));
500 if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame)))
501 goto give_sigsegv;
502
1da177e4 503 err |= setup_sigcontext32(regs, &frame->sf_sc);
431dc804
RB
504 err |= __copy_conv_sigset_to_user(&frame->sf_mask, set);
505
1da177e4
LT
506 if (err)
507 goto give_sigsegv;
508
509 /*
510 * Arguments to signal handler:
511 *
512 * a0 = signal number
513 * a1 = 0 (should be cause)
514 * a2 = pointer to struct sigcontext
515 *
516 * $25 and c0_epc point to the signal handler, $29 points to the
517 * struct sigframe.
518 */
519 regs->regs[ 4] = signr;
520 regs->regs[ 5] = 0;
521 regs->regs[ 6] = (unsigned long) &frame->sf_sc;
522 regs->regs[29] = (unsigned long) frame;
d814c28c 523 regs->regs[31] = (unsigned long) sig_return;
1da177e4
LT
524 regs->cp0_epc = regs->regs[25] = (unsigned long) ka->sa.sa_handler;
525
722bb63d 526 DEBUGP("SIG deliver (%s:%d): sp=0x%p pc=0x%lx ra=0x%lx\n",
1da177e4 527 current->comm, current->pid,
722bb63d
FBH
528 frame, regs->cp0_epc, regs->regs[31]);
529
7b3e2fc8 530 return 0;
1da177e4
LT
531
532give_sigsegv:
533 force_sigsegv(signr, current);
7b3e2fc8 534 return -EFAULT;
1da177e4
LT
535}
536
d814c28c
DD
537static int setup_rt_frame_32(void *sig_return, struct k_sigaction *ka,
538 struct pt_regs *regs, int signr, sigset_t *set,
539 siginfo_t *info)
1da177e4 540{
9bbf28a3 541 struct rt_sigframe32 __user *frame;
1da177e4 542 int err = 0;
1da177e4
LT
543
544 frame = get_sigframe(ka, regs, sizeof(*frame));
545 if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame)))
546 goto give_sigsegv;
547
1da177e4
LT
548 /* Convert (siginfo_t -> compat_siginfo_t) and copy to user. */
549 err |= copy_siginfo_to_user32(&frame->rs_info, info);
550
70342287 551 /* Create the ucontext. */
1da177e4
LT
552 err |= __put_user(0, &frame->rs_uc.uc_flags);
553 err |= __put_user(0, &frame->rs_uc.uc_link);
ea536ad4 554 err |= __compat_save_altstack(&frame->rs_uc.uc_stack, regs->regs[29]);
1da177e4 555 err |= setup_sigcontext32(regs, &frame->rs_uc.uc_mcontext);
431dc804 556 err |= __copy_conv_sigset_to_user(&frame->rs_uc.uc_sigmask, set);
1da177e4
LT
557
558 if (err)
559 goto give_sigsegv;
560
561 /*
562 * Arguments to signal handler:
563 *
564 * a0 = signal number
565 * a1 = 0 (should be cause)
566 * a2 = pointer to ucontext
567 *
568 * $25 and c0_epc point to the signal handler, $29 points to
569 * the struct rt_sigframe32.
570 */
571 regs->regs[ 4] = signr;
572 regs->regs[ 5] = (unsigned long) &frame->rs_info;
573 regs->regs[ 6] = (unsigned long) &frame->rs_uc;
574 regs->regs[29] = (unsigned long) frame;
d814c28c 575 regs->regs[31] = (unsigned long) sig_return;
1da177e4
LT
576 regs->cp0_epc = regs->regs[25] = (unsigned long) ka->sa.sa_handler;
577
722bb63d 578 DEBUGP("SIG deliver (%s:%d): sp=0x%p pc=0x%lx ra=0x%lx\n",
1da177e4 579 current->comm, current->pid,
722bb63d
FBH
580 frame, regs->cp0_epc, regs->regs[31]);
581
7b3e2fc8 582 return 0;
1da177e4
LT
583
584give_sigsegv:
585 force_sigsegv(signr, current);
7b3e2fc8 586 return -EFAULT;
1da177e4
LT
587}
588
151fd6ac
RB
589/*
590 * o32 compatibility on 64-bit kernels, without DSP ASE
591 */
592struct mips_abi mips_abi_32 = {
593 .setup_frame = setup_frame_32,
d814c28c
DD
594 .signal_return_offset =
595 offsetof(struct mips_vdso, o32_signal_trampoline),
70342287 596 .setup_rt_frame = setup_rt_frame_32,
d814c28c
DD
597 .rt_signal_return_offset =
598 offsetof(struct mips_vdso, o32_rt_signal_trampoline),
151fd6ac
RB
599 .restart = __NR_O32_restart_syscall
600};
1da177e4 601
137f6f3e
RB
602static int signal32_init(void)
603{
604 if (cpu_has_fpu) {
605 save_fp_context32 = _save_fp_context32;
606 restore_fp_context32 = _restore_fp_context32;
607 } else {
b2ead528
PB
608 save_fp_context32 = copy_fp_to_sigcontext32;
609 restore_fp_context32 = copy_fp_from_sigcontext32;
137f6f3e
RB
610 }
611
612 return 0;
613}
614
615arch_initcall(signal32_init);
This page took 1.144729 seconds and 5 git commands to generate.