20 #include <linux/errno.h>
21 #include <linux/signal.h>
22 #include <linux/personality.h>
28 #include <asm/compat.h>
31 #include <asm/cacheflush.h>
32 #include <asm/ucontext.h>
33 #include <asm/unistd.h>
66 static int restore_fpsimd_context(
struct fpsimd_context __user *ctx)
82 sizeof(fpsimd.
vregs));
108 for (i = 0; i < 31; i++)
120 err |= !valid_user_regs(®s->
user_regs);
123 err |= restore_fpsimd_context(&aux->
fpsimd);
147 if (restore_sigframe(regs, frame))
154 return regs->
regs[0];
171 static int setup_sigframe(
struct rt_sigframe __user *sf,
178 for (i = 0; i < 31; i++)
190 err |= preserve_fpsimd_context(&aux->
fpsimd);
202 unsigned long sp, sp_top;
205 sp = sp_top = regs->
sp;
210 if ((ka->
sa.sa_flags &
SA_ONSTACK) && !sas_ss_flags(sp))
216 sp = (sp - framesize) & ~15;
217 frame = (
void __user *)sp;
229 void __user *frame,
int usig)
239 regs->
regs[0] = usig;
240 regs->
regs[29] = regs->
sp - 16;
241 regs->
sp = (
unsigned long)frame;
242 regs->
pc = (
unsigned long)ka->
sa.sa_handler;
245 sigtramp = ka->
sa.sa_restorer;
247 sigtramp = VDSO_SYMBOL(
current->mm->context.vdso, sigtramp);
249 regs->
regs[30] = (
unsigned long)sigtramp;
261 frame = get_sigframe(ka, regs,
sizeof(*frame));
268 memset(&stack, 0,
sizeof(stack));
274 err |= setup_sigframe(frame, regs,
set);
276 err = setup_return(regs, ka, frame, usig);
281 regs->
regs[2] = (
unsigned long)&frame->
uc;
287 static void setup_restart_syscall(
struct pt_regs *regs)
298 static void handle_signal(
unsigned long sig,
struct k_sigaction *ka,
303 sigset_t *oldset = sigmask_to_save();
323 ret = setup_rt_frame(usig, ka, info, oldset, regs);
329 ret |= !valid_user_regs(®s->
user_regs);
354 static void do_signal(
struct pt_regs *regs)
356 unsigned long continue_addr = 0, restart_addr = 0;
366 continue_addr = regs->
pc;
368 retval = regs->
regs[0];
385 regs->
pc = restart_addr;
401 if (regs->
pc == restart_addr &&
407 regs->
pc = continue_addr;
410 handle_signal(signr, &ka, &info, regs);
418 if (syscall >= 0 && regs->
pc == restart_addr) {
420 setup_restart_syscall(regs);
424 restore_saved_sigmask();
428 unsigned int thread_flags)
435 tracehook_notify_resume(regs);