]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - arch/x86/kernel/signal_64.c
Merge commit 'v2.6.27-rc3' into x86/prototypes
[linux-2.6-omap-h63xx.git] / arch / x86 / kernel / signal_64.c
index b95a0a609053ea65dd2d5614fd5ba3483919fef6..02b02583f5b5c08d3d0e33c82f5634ebfb9de4b2 100644 (file)
@@ -54,6 +54,59 @@ sys_sigaltstack(const stack_t __user *uss, stack_t __user *uoss,
        return do_sigaltstack(uss, uoss, regs->sp);
 }
 
+/*
+ * Signal frame handlers.
+ */
+
+static inline int save_i387(struct _fpstate __user *buf)
+{
+       struct task_struct *tsk = current;
+       int err = 0;
+
+       BUILD_BUG_ON(sizeof(struct user_i387_struct) !=
+                       sizeof(tsk->thread.xstate->fxsave));
+
+       if ((unsigned long)buf % 16)
+               printk("save_i387: bad fpstate %p\n", buf);
+
+       if (!used_math())
+               return 0;
+       clear_used_math(); /* trigger finit */
+       if (task_thread_info(tsk)->status & TS_USEDFPU) {
+               err = save_i387_checking((struct i387_fxsave_struct __user *)
+                                        buf);
+               if (err)
+                       return err;
+               task_thread_info(tsk)->status &= ~TS_USEDFPU;
+               stts();
+       } else {
+               if (__copy_to_user(buf, &tsk->thread.xstate->fxsave,
+                                  sizeof(struct i387_fxsave_struct)))
+                       return -1;
+       }
+       return 1;
+}
+
+/*
+ * This restores directly out of user space. Exceptions are handled.
+ */
+static inline int restore_i387(struct _fpstate __user *buf)
+{
+       struct task_struct *tsk = current;
+       int err;
+
+       if (!used_math()) {
+               err = init_fpu(tsk);
+               if (err)
+                       return err;
+       }
+
+       if (!(task_thread_info(current)->status & TS_USEDFPU)) {
+               clts();
+               task_thread_info(current)->status |= TS_USEDFPU;
+       }
+       return restore_fpu_checking((__force struct i387_fxsave_struct *)buf);
+}
 
 /*
  * Do a signal return; undo the signal stack.
@@ -497,9 +550,6 @@ void do_notify_resume(struct pt_regs *regs, void *unused,
        /* deal with pending signal delivery */
        if (thread_info_flags & _TIF_SIGPENDING)
                do_signal(regs);
-
-       if (thread_info_flags & _TIF_HRTICK_RESCHED)
-               hrtick_resched();
 }
 
 void signal_fault(struct pt_regs *regs, void __user *frame, char *where)