Pull release into acpica branch
[pandora-kernel.git] / arch / mips / kernel / linux32.c
index 4613219..330cf84 100644 (file)
@@ -215,81 +215,32 @@ sys32_readdir(unsigned int fd, void * dirent32, unsigned int count)
        return(n);
 }
 
-struct rusage32 {
-        struct compat_timeval ru_utime;
-        struct compat_timeval ru_stime;
-        int    ru_maxrss;
-        int    ru_ixrss;
-        int    ru_idrss;
-        int    ru_isrss;
-        int    ru_minflt;
-        int    ru_majflt;
-        int    ru_nswap;
-        int    ru_inblock;
-        int    ru_oublock;
-        int    ru_msgsnd;
-        int    ru_msgrcv;
-        int    ru_nsignals;
-        int    ru_nvcsw;
-        int    ru_nivcsw;
-};
-
-static int
-put_rusage (struct rusage32 *ru, struct rusage *r)
+asmlinkage int
+sys32_waitpid(compat_pid_t pid, unsigned int *stat_addr, int options)
 {
-       int err;
-
-       if (!access_ok(VERIFY_WRITE, ru, sizeof *ru))
-               return -EFAULT;
-
-       err = __put_user (r->ru_utime.tv_sec, &ru->ru_utime.tv_sec);
-       err |= __put_user (r->ru_utime.tv_usec, &ru->ru_utime.tv_usec);
-       err |= __put_user (r->ru_stime.tv_sec, &ru->ru_stime.tv_sec);
-       err |= __put_user (r->ru_stime.tv_usec, &ru->ru_stime.tv_usec);
-       err |= __put_user (r->ru_maxrss, &ru->ru_maxrss);
-       err |= __put_user (r->ru_ixrss, &ru->ru_ixrss);
-       err |= __put_user (r->ru_idrss, &ru->ru_idrss);
-       err |= __put_user (r->ru_isrss, &ru->ru_isrss);
-       err |= __put_user (r->ru_minflt, &ru->ru_minflt);
-       err |= __put_user (r->ru_majflt, &ru->ru_majflt);
-       err |= __put_user (r->ru_nswap, &ru->ru_nswap);
-       err |= __put_user (r->ru_inblock, &ru->ru_inblock);
-       err |= __put_user (r->ru_oublock, &ru->ru_oublock);
-       err |= __put_user (r->ru_msgsnd, &ru->ru_msgsnd);
-       err |= __put_user (r->ru_msgrcv, &ru->ru_msgrcv);
-       err |= __put_user (r->ru_nsignals, &ru->ru_nsignals);
-       err |= __put_user (r->ru_nvcsw, &ru->ru_nvcsw);
-       err |= __put_user (r->ru_nivcsw, &ru->ru_nivcsw);
-
-       return err;
+       return compat_sys_wait4(pid, stat_addr, options, NULL);
 }
 
-asmlinkage int
-sys32_wait4(compat_pid_t pid, unsigned int * stat_addr, int options,
-           struct rusage32 * ru)
+asmlinkage long
+sysn32_waitid(int which, compat_pid_t pid,
+             siginfo_t __user *uinfo, int options,
+             struct compat_rusage __user *uru)
 {
-       if (!ru)
-               return sys_wait4(pid, stat_addr, options, NULL);
-       else {
-               struct rusage r;
-               int ret;
-               unsigned int status;
-               mm_segment_t old_fs = get_fs();
+       struct rusage ru;
+       long ret;
+       mm_segment_t old_fs = get_fs();
 
-               set_fs(KERNEL_DS);
-               ret = sys_wait4(pid, stat_addr ? &status : NULL, options, &r);
-               set_fs(old_fs);
-               if (put_rusage (ru, &r)) return -EFAULT;
-               if (stat_addr && put_user (status, stat_addr))
-                       return -EFAULT;
+       set_fs (KERNEL_DS);
+       ret = sys_waitid(which, pid, uinfo, options,
+                        uru ? (struct rusage __user *) &ru : NULL);
+       set_fs (old_fs);
+
+       if (ret < 0 || uinfo->si_signo == 0)
                return ret;
-       }
-}
 
-asmlinkage int
-sys32_waitpid(compat_pid_t pid, unsigned int *stat_addr, int options)
-{
-       return sys32_wait4(pid, stat_addr, options, NULL);
+       if (uru)
+               ret = put_compat_rusage(&ru, uru);
+       return ret;
 }
 
 struct sysinfo32 {
@@ -546,20 +497,20 @@ struct msgbuf32 { s32 mtype; char mtext[1]; };
 struct ipc_perm32
 {
        key_t             key;
-        compat_uid_t  uid;
-        compat_gid_t  gid;
-        compat_uid_t  cuid;
-        compat_gid_t  cgid;
+        __compat_uid_t  uid;
+        __compat_gid_t  gid;
+        __compat_uid_t  cuid;
+        __compat_gid_t  cgid;
         compat_mode_t  mode;
         unsigned short  seq;
 };
 
 struct ipc64_perm32 {
        key_t key;
-       compat_uid_t uid;
-       compat_gid_t gid;
-       compat_uid_t cuid;
-       compat_gid_t cgid;
+       __compat_uid_t uid;
+       __compat_gid_t gid;
+       __compat_uid_t cuid;
+       __compat_gid_t cgid;
        compat_mode_t   mode;
        unsigned short  seq;
        unsigned short __pad1;
@@ -1467,3 +1418,80 @@ asmlinkage long sys32_socketcall(int call, unsigned int *args32)
        }
        return err;
 }
+
+struct sigevent32 {
+       u32 sigev_value;
+       u32 sigev_signo;
+       u32 sigev_notify;
+       u32 payload[(64 / 4) - 3];
+};
+
+extern asmlinkage long
+sys_timer_create(clockid_t which_clock,
+                struct sigevent __user *timer_event_spec,
+                timer_t __user * created_timer_id);
+
+long
+sys32_timer_create(u32 clock, struct sigevent32 __user *se32, timer_t __user *timer_id)
+{
+       struct sigevent __user *p = NULL;
+       if (se32) {
+               struct sigevent se;
+               p = compat_alloc_user_space(sizeof(struct sigevent));
+               memset(&se, 0, sizeof(struct sigevent));
+               if (get_user(se.sigev_value.sival_int,  &se32->sigev_value) ||
+                   __get_user(se.sigev_signo, &se32->sigev_signo) ||
+                   __get_user(se.sigev_notify, &se32->sigev_notify) ||
+                   __copy_from_user(&se._sigev_un._pad, &se32->payload,
+                                    sizeof(se32->payload)) ||
+                   copy_to_user(p, &se, sizeof(se)))
+                       return -EFAULT;
+       }
+       return sys_timer_create(clock, p, timer_id);
+}
+
+asmlinkage long
+sysn32_rt_sigtimedwait(const sigset_t __user *uthese,
+                      siginfo_t __user *uinfo,
+                      const struct compat_timespec __user *uts32,
+                      size_t sigsetsize)
+{
+       struct timespec __user *uts = NULL;
+
+       if (uts32) {
+               struct timespec ts;
+               uts = compat_alloc_user_space(sizeof(struct timespec));
+               if (get_user(ts.tv_sec, &uts32->tv_sec) ||
+                   get_user(ts.tv_nsec, &uts32->tv_nsec) ||
+                   copy_to_user (uts, &ts, sizeof (ts)))
+                       return -EFAULT;
+       }
+       return sys_rt_sigtimedwait(uthese, uinfo, uts, sigsetsize);
+}
+
+save_static_function(sys32_clone);
+__attribute_used__ noinline static int
+_sys32_clone(nabi_no_regargs struct pt_regs regs)
+{
+       unsigned long clone_flags;
+       unsigned long newsp;
+       int __user *parent_tidptr, *child_tidptr;
+
+       clone_flags = regs.regs[4];
+       newsp = regs.regs[5];
+       if (!newsp)
+               newsp = regs.regs[29];
+       parent_tidptr = (int *) regs.regs[6];
+
+       /* Use __dummy4 instead of getting it off the stack, so that
+          syscall() works.  */
+       child_tidptr = (int __user *) __dummy4;
+       return do_fork(clone_flags, newsp, &regs, 0,
+                      parent_tidptr, child_tidptr);
+}
+
+extern asmlinkage void sys_set_thread_area(u32 addr);
+asmlinkage void sys32_set_thread_area(u32 addr)
+{
+       sys_set_thread_area(AA(addr));
+}