1 /* $Id: sys_sparc32.c,v 1.131 2000/01/21 11:38:54 jj Exp $
2 * sys_sparc32.c: Conversion between 32bit and 64bit native syscalls.
4 * Copyright (C) 1997,1998 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
5 * Copyright (C) 1997 David S. Miller (davem@caip.rutgers.edu)
7 * These routines maintain argument size conversion between 32bit and 64bit
11 #include <linux/config.h>
12 #include <linux/kernel.h>
13 #include <linux/sched.h>
16 #include <linux/file.h>
17 #include <linux/signal.h>
18 #include <linux/utime.h>
19 #include <linux/resource.h>
20 #include <linux/times.h>
21 #include <linux/utsname.h>
22 #include <linux/timex.h>
23 #include <linux/smp.h>
24 #include <linux/smp_lock.h>
25 #include <linux/sem.h>
26 #include <linux/msg.h>
27 #include <linux/shm.h>
28 #include <linux/malloc.h>
29 #include <linux/uio.h>
30 #include <linux/nfs_fs.h>
31 #include <linux/smb_fs.h>
32 #include <linux/smb_mount.h>
33 #include <linux/ncp_fs.h>
34 #include <linux/quota.h>
35 #include <linux/module.h>
36 #include <linux/sunrpc/svc.h>
37 #include <linux/nfsd/nfsd.h>
38 #include <linux/nfsd/cache.h>
39 #include <linux/nfsd/xdr.h>
40 #include <linux/nfsd/syscall.h>
41 #include <linux/poll.h>
42 #include <linux/personality.h>
43 #include <linux/stat.h>
44 #include <linux/filter.h>
45 #include <linux/highmem.h>
46 #include <linux/highuid.h>
48 #include <asm/types.h>
50 #include <asm/uaccess.h>
51 #include <asm/fpumacro.h>
52 #include <asm/semaphore.h>
56 /* Use this to get at 32-bit user passed pointers. */
57 /* Things to consider: the low-level assembly stub does
58 srl x, 0, x for first four arguments, so if you have
59 pointer to something in the first four arguments, just
60 declare it as a pointer, not u32. On the other side,
61 arguments from 5th onwards should be declared as u32
62 for pointers, and need AA() around each usage.
63 A() macro should be used for places where you e.g.
64 have some internal variable u32 and just want to get
65 rid of a compiler warning. AA() has to be used in
66 places where you want to convert a function argument
67 to 32bit pointer or when you e.g. access pt_regs
68 structure and want to consider 32bit registers only.
71 #define A(__x) ((unsigned long)(__x))
73 ({ unsigned long __ret; \
74 __asm__ ("srl %0, 0, %0" \
80 extern asmlinkage
long sys_chown(const char *, uid_t
,gid_t
);
81 extern asmlinkage
long sys_lchown(const char *, uid_t
,gid_t
);
82 extern asmlinkage
long sys_fchown(unsigned int, uid_t
,gid_t
);
83 extern asmlinkage
long sys_setregid(gid_t
, gid_t
);
84 extern asmlinkage
long sys_setgid(gid_t
);
85 extern asmlinkage
long sys_setreuid(uid_t
, uid_t
);
86 extern asmlinkage
long sys_setuid(uid_t
);
87 extern asmlinkage
long sys_setresuid(uid_t
, uid_t
, uid_t
);
88 extern asmlinkage
long sys_setresgid(gid_t
, gid_t
, gid_t
);
89 extern asmlinkage
long sys_setfsuid(uid_t
);
90 extern asmlinkage
long sys_setfsgid(gid_t
);
92 /* For this source file, we want overflow handling. */
100 #undef NEW_TO_OLD_UID
101 #undef NEW_TO_OLD_GID
102 #undef SET_OLDSTAT_UID
103 #undef SET_OLDSTAT_GID
107 #define high2lowuid(uid) ((uid) > 65535) ? (u16)overflowuid : (u16)(uid)
108 #define high2lowgid(gid) ((gid) > 65535) ? (u16)overflowgid : (u16)(gid)
109 #define low2highuid(uid) ((uid) == (u16)-1) ? (uid_t)-1 : (uid_t)(uid)
110 #define low2highgid(gid) ((gid) == (u16)-1) ? (gid_t)-1 : (gid_t)(gid)
111 #define SET_UID16(var, uid) var = high2lowuid(uid)
112 #define SET_GID16(var, gid) var = high2lowgid(gid)
113 #define NEW_TO_OLD_UID(uid) high2lowuid(uid)
114 #define NEW_TO_OLD_GID(gid) high2lowgid(gid)
115 #define SET_OLDSTAT_UID(stat, uid) (stat).st_uid = high2lowuid(uid)
116 #define SET_OLDSTAT_GID(stat, gid) (stat).st_gid = high2lowgid(gid)
117 #define SET_STAT_UID(stat, uid) (stat).st_uid = high2lowuid(uid)
118 #define SET_STAT_GID(stat, gid) (stat).st_gid = high2lowgid(gid)
120 asmlinkage
long sys32_chown16(const char * filename
, u16 user
, u16 group
)
122 return sys_chown(filename
, low2highuid(user
), low2highgid(group
));
125 asmlinkage
long sys32_lchown16(const char * filename
, u16 user
, u16 group
)
127 return sys_lchown(filename
, low2highuid(user
), low2highgid(group
));
130 asmlinkage
long sys32_fchown16(unsigned int fd
, u16 user
, u16 group
)
132 return sys_fchown(fd
, low2highuid(user
), low2highgid(group
));
135 asmlinkage
long sys32_setregid16(u16 rgid
, u16 egid
)
137 return sys_setregid(low2highgid(rgid
), low2highgid(egid
));
140 asmlinkage
long sys32_setgid16(u16 gid
)
142 return sys_setgid((gid_t
)gid
);
145 asmlinkage
long sys32_setreuid16(u16 ruid
, u16 euid
)
147 return sys_setreuid(low2highuid(ruid
), low2highuid(euid
));
150 asmlinkage
long sys32_setuid16(u16 uid
)
152 return sys_setuid((uid_t
)uid
);
155 asmlinkage
long sys32_setresuid16(u16 ruid
, u16 euid
, u16 suid
)
157 return sys_setresuid(low2highuid(ruid
), low2highuid(euid
),
161 asmlinkage
long sys32_getresuid16(u16
*ruid
, u16
*euid
, u16
*suid
)
165 if (!(retval
= put_user(high2lowuid(current
->uid
), ruid
)) &&
166 !(retval
= put_user(high2lowuid(current
->euid
), euid
)))
167 retval
= put_user(high2lowuid(current
->suid
), suid
);
172 asmlinkage
long sys32_setresgid16(u16 rgid
, u16 egid
, u16 sgid
)
174 return sys_setresgid(low2highgid(rgid
), low2highgid(egid
),
178 asmlinkage
long sys32_getresgid16(u16
*rgid
, u16
*egid
, u16
*sgid
)
182 if (!(retval
= put_user(high2lowgid(current
->gid
), rgid
)) &&
183 !(retval
= put_user(high2lowgid(current
->egid
), egid
)))
184 retval
= put_user(high2lowgid(current
->sgid
), sgid
);
189 asmlinkage
long sys32_setfsuid16(u16 uid
)
191 return sys_setfsuid((uid_t
)uid
);
194 asmlinkage
long sys32_setfsgid16(u16 gid
)
196 return sys_setfsgid((gid_t
)gid
);
199 asmlinkage
long sys32_getgroups16(int gidsetsize
, u16
*grouplist
)
206 i
= current
->ngroups
;
211 groups
[j
] = current
->groups
[j
];
212 if (copy_to_user(grouplist
, groups
, sizeof(u16
)*i
))
218 asmlinkage
long sys32_setgroups16(int gidsetsize
, u16
*grouplist
)
223 if (!capable(CAP_SETGID
))
225 if ((unsigned) gidsetsize
> NGROUPS
)
227 if (copy_from_user(groups
, grouplist
, gidsetsize
* sizeof(u16
)))
229 for (i
= 0 ; i
< gidsetsize
; i
++)
230 current
->groups
[i
] = (gid_t
)groups
[i
];
231 current
->ngroups
= gidsetsize
;
235 asmlinkage
long sys32_getuid16(void)
237 return high2lowuid(current
->uid
);
240 asmlinkage
long sys32_geteuid16(void)
242 return high2lowuid(current
->euid
);
245 asmlinkage
long sys32_getgid16(void)
247 return high2lowgid(current
->gid
);
250 asmlinkage
long sys32_getegid16(void)
252 return high2lowgid(current
->egid
);
255 /* In order to reduce some races, while at the same time doing additional
256 * checking and hopefully speeding things up, we copy filenames to the
257 * kernel data space before using them..
259 * POSIX.1 2.4: an empty pathname is invalid (ENOENT).
261 static inline int do_getname32(const char *filename
, char *page
)
265 /* 32bit pointer will be always far below TASK_SIZE :)) */
266 retval
= strncpy_from_user((char *)page
, (char *)filename
, PAGE_SIZE
);
268 if (retval
< PAGE_SIZE
)
270 return -ENAMETOOLONG
;
276 char * getname32(const char *filename
)
280 result
= ERR_PTR(-ENOMEM
);
281 tmp
= (char *)__get_free_page(GFP_KERNEL
);
283 int retval
= do_getname32(filename
, tmp
);
288 result
= ERR_PTR(retval
);
294 /* 32-bit timeval and related flotsam. */
303 struct timeval32 it_interval
;
304 struct timeval32 it_value
;
307 static inline long get_tv32(struct timeval
*o
, struct timeval32
*i
)
309 return (!access_ok(VERIFY_READ
, tv32
, sizeof(*tv32
)) ||
310 (__get_user(o
->tv_sec
, &i
->tv_sec
) |
311 __get_user(o
->tv_usec
, &i
->tv_usec
)));
314 static inline long put_tv32(struct timeval32
*o
, struct timeval
*i
)
316 return (!access_ok(VERIFY_WRITE
, o
, sizeof(*o
)) ||
317 (__put_user(i
->tv_sec
, &o
->tv_sec
) |
318 __put_user(i
->tv_usec
, &o
->tv_usec
)));
321 static inline long get_it32(struct itimerval
*o
, struct itimerval32
*i
)
323 return (!access_ok(VERIFY_READ
, i32
, sizeof(*i32
)) ||
324 (__get_user(o
->it_interval
.tv_sec
, &i
->it_interval
.tv_sec
) |
325 __get_user(o
->it_interval
.tv_usec
, &i
->it_interval
.tv_usec
) |
326 __get_user(o
->it_value
.tv_sec
, &i
->it_value
.tv_sec
) |
327 __get_user(o
->it_value
.tv_usec
, &i
->it_value
.tv_usec
)));
330 static inline long put_it32(struct itimerval32
*o
, struct itimerval
*i
)
332 return (!access_ok(VERIFY_WRITE
, i32
, sizeof(*i32
)) ||
333 (__put_user(i
->it_interval
.tv_sec
, &o
->it_interval
.tv_sec
) |
334 __put_user(i
->it_interval
.tv_usec
, &o
->it_interval
.tv_usec
) |
335 __put_user(i
->it_value
.tv_sec
, &o
->it_value
.tv_sec
) |
336 __put_user(i
->it_value
.tv_usec
, &o
->it_value
.tv_usec
)));
339 extern asmlinkage
int sys_ioperm(unsigned long from
, unsigned long num
, int on
);
341 asmlinkage
int sys32_ioperm(u32 from
, u32 num
, int on
)
343 return sys_ioperm((unsigned long)from
, (unsigned long)num
, on
);
346 struct msgbuf32
{ s32 mtype
; char mtext
[1]; };
351 __kernel_uid_t32 uid
;
352 __kernel_gid_t32 gid
;
353 __kernel_uid_t32 cuid
;
354 __kernel_gid_t32 cgid
;
355 __kernel_mode_t32 mode
;
360 struct ipc_perm32 sem_perm
; /* permissions .. see ipc.h */
361 __kernel_time_t32 sem_otime
; /* last semop time */
362 __kernel_time_t32 sem_ctime
; /* last change time */
363 u32 sem_base
; /* ptr to first semaphore in array */
364 u32 sem_pending
; /* pending operations to be processed */
365 u32 sem_pending_last
; /* last pending operation */
366 u32 undo
; /* undo requests on this array */
367 unsigned short sem_nsems
; /* no. of semaphores in array */
370 struct semid64_ds32
{
371 struct ipc64_perm sem_perm
; /* this structure is the same on sparc32 and sparc64 */
373 __kernel_time_t32 sem_otime
;
375 __kernel_time_t32 sem_ctime
;
383 struct ipc_perm32 msg_perm
;
386 __kernel_time_t32 msg_stime
;
387 __kernel_time_t32 msg_rtime
;
388 __kernel_time_t32 msg_ctime
;
391 unsigned short msg_cbytes
;
392 unsigned short msg_qnum
;
393 unsigned short msg_qbytes
;
394 __kernel_ipc_pid_t32 msg_lspid
;
395 __kernel_ipc_pid_t32 msg_lrpid
;
398 struct msqid64_ds32
{
399 struct ipc64_perm msg_perm
;
401 __kernel_time_t32 msg_stime
;
403 __kernel_time_t32 msg_rtime
;
405 __kernel_time_t32 msg_ctime
;
406 unsigned int msg_cbytes
;
407 unsigned int msg_qnum
;
408 unsigned int msg_qbytes
;
409 __kernel_pid_t32 msg_lspid
;
410 __kernel_pid_t32 msg_lrpid
;
411 unsigned int __unused1
;
412 unsigned int __unused2
;
417 struct ipc_perm32 shm_perm
;
419 __kernel_time_t32 shm_atime
;
420 __kernel_time_t32 shm_dtime
;
421 __kernel_time_t32 shm_ctime
;
422 __kernel_ipc_pid_t32 shm_cpid
;
423 __kernel_ipc_pid_t32 shm_lpid
;
424 unsigned short shm_nattch
;
427 struct shmid64_ds32
{
428 struct ipc64_perm shm_perm
;
430 __kernel_time_t32 shm_atime
;
432 __kernel_time_t32 shm_dtime
;
434 __kernel_time_t32 shm_ctime
;
435 __kernel_size_t32 shm_segsz
;
436 __kernel_pid_t32 shm_cpid
;
437 __kernel_pid_t32 shm_lpid
;
438 unsigned int shm_nattch
;
439 unsigned int __unused1
;
440 unsigned int __unused2
;
445 * sys32_ipc() is the de-multiplexer for the SysV IPC calls in 32bit emulation..
447 * This is really horribly ugly.
449 #define IPCOP_MASK(__x) (1UL << (__x))
450 static int do_sys32_semctl(int first
, int second
, int third
, void *uptr
)
459 if (get_user (pad
, (u32
*)uptr
))
462 fourth
.val
= (int)pad
;
464 fourth
.__pad
= (void *)A(pad
);
465 if (IPCOP_MASK (third
) &
466 (IPCOP_MASK (IPC_INFO
) | IPCOP_MASK (SEM_INFO
) | IPCOP_MASK (GETVAL
) |
467 IPCOP_MASK (GETPID
) | IPCOP_MASK (GETNCNT
) | IPCOP_MASK (GETZCNT
) |
468 IPCOP_MASK (GETALL
) | IPCOP_MASK (SETALL
) | IPCOP_MASK (IPC_RMID
))) {
469 err
= sys_semctl (first
, second
, third
, fourth
);
470 } else if (third
& IPC_64
) {
472 struct semid64_ds32
*usp
= (struct semid64_ds32
*)A(pad
);
474 int need_back_translation
;
476 if (third
== (IPC_SET
|IPC_64
)) {
477 err
= get_user (s
.sem_perm
.uid
, &usp
->sem_perm
.uid
);
478 err
|= __get_user (s
.sem_perm
.gid
, &usp
->sem_perm
.gid
);
479 err
|= __get_user (s
.sem_perm
.mode
, &usp
->sem_perm
.mode
);
484 need_back_translation
=
485 (IPCOP_MASK (third
) &
486 (IPCOP_MASK (SEM_STAT
) | IPCOP_MASK (IPC_STAT
))) != 0;
487 if (need_back_translation
)
491 err
= sys_semctl (first
, second
, third
, fourth
);
493 if (need_back_translation
) {
494 int err2
= copy_to_user (&usp
->sem_perm
, &s
.sem_perm
, sizeof(struct ipc64_perm
) + 2*sizeof(time_t));
495 err2
|= __put_user (s
.sem_nsems
, &usp
->sem_nsems
);
496 if (err2
) err
= -EFAULT
;
500 struct semid_ds32
*usp
= (struct semid_ds32
*)A(pad
);
502 int need_back_translation
;
504 if (third
== IPC_SET
) {
505 err
= get_user (s
.sem_perm
.uid
, &usp
->sem_perm
.uid
);
506 err
|= __get_user (s
.sem_perm
.gid
, &usp
->sem_perm
.gid
);
507 err
|= __get_user (s
.sem_perm
.mode
, &usp
->sem_perm
.mode
);
512 need_back_translation
=
513 (IPCOP_MASK (third
) &
514 (IPCOP_MASK (SEM_STAT
) | IPCOP_MASK (IPC_STAT
))) != 0;
515 if (need_back_translation
)
519 err
= sys_semctl (first
, second
, third
, fourth
);
521 if (need_back_translation
) {
522 int err2
= put_user (s
.sem_perm
.key
, &usp
->sem_perm
.key
);
523 err2
|= __put_user (high2lowuid(s
.sem_perm
.uid
), &usp
->sem_perm
.uid
);
524 err2
|= __put_user (high2lowgid(s
.sem_perm
.gid
), &usp
->sem_perm
.gid
);
525 err2
|= __put_user (high2lowuid(s
.sem_perm
.cuid
), &usp
->sem_perm
.cuid
);
526 err2
|= __put_user (high2lowgid(s
.sem_perm
.cgid
), &usp
->sem_perm
.cgid
);
527 err2
|= __put_user (s
.sem_perm
.mode
, &usp
->sem_perm
.mode
);
528 err2
|= __put_user (s
.sem_perm
.seq
, &usp
->sem_perm
.seq
);
529 err2
|= __put_user (s
.sem_otime
, &usp
->sem_otime
);
530 err2
|= __put_user (s
.sem_ctime
, &usp
->sem_ctime
);
531 err2
|= __put_user (s
.sem_nsems
, &usp
->sem_nsems
);
532 if (err2
) err
= -EFAULT
;
539 static int do_sys32_msgsnd (int first
, int second
, int third
, void *uptr
)
541 struct msgbuf
*p
= kmalloc (second
+ sizeof (struct msgbuf
) + 4, GFP_USER
);
542 struct msgbuf32
*up
= (struct msgbuf32
*)uptr
;
548 err
= get_user (p
->mtype
, &up
->mtype
);
549 err
|= __copy_from_user (p
->mtext
, &up
->mtext
, second
);
554 err
= sys_msgsnd (first
, p
, second
, third
);
561 static int do_sys32_msgrcv (int first
, int second
, int msgtyp
, int third
,
562 int version
, void *uptr
)
570 struct ipc_kludge
*uipck
= (struct ipc_kludge
*)uptr
;
571 struct ipc_kludge ipck
;
577 if (copy_from_user (&ipck
, uipck
, sizeof (struct ipc_kludge
)))
579 uptr
= (void *)A(ipck
.msgp
);
580 msgtyp
= ipck
.msgtyp
;
583 p
= kmalloc (second
+ sizeof (struct msgbuf
) + 4, GFP_USER
);
588 err
= sys_msgrcv (first
, p
, second
+ 4, msgtyp
, third
);
592 up
= (struct msgbuf32
*)uptr
;
593 if (put_user (p
->mtype
, &up
->mtype
) ||
594 __copy_to_user (&up
->mtext
, p
->mtext
, err
))
602 static int do_sys32_msgctl (int first
, int second
, void *uptr
)
606 if (IPCOP_MASK (second
) &
607 (IPCOP_MASK (IPC_INFO
) | IPCOP_MASK (MSG_INFO
) |
608 IPCOP_MASK (IPC_RMID
))) {
609 err
= sys_msgctl (first
, second
, (struct msqid_ds
*)uptr
);
610 } else if (second
& IPC_64
) {
612 struct msqid64_ds32
*up
= (struct msqid64_ds32
*)uptr
;
615 if (second
== (IPC_SET
|IPC_64
)) {
616 err
= get_user (m
.msg_perm
.uid
, &up
->msg_perm
.uid
);
617 err
|= __get_user (m
.msg_perm
.gid
, &up
->msg_perm
.gid
);
618 err
|= __get_user (m
.msg_perm
.mode
, &up
->msg_perm
.mode
);
619 err
|= __get_user (m
.msg_qbytes
, &up
->msg_qbytes
);
625 err
= sys_msgctl (first
, second
, (struct msqid_ds
*)&m
);
627 if (IPCOP_MASK (second
) &
628 (IPCOP_MASK (MSG_STAT
) | IPCOP_MASK (IPC_STAT
))) {
629 int err2
= copy_to_user(&up
->msg_perm
, &m
.msg_perm
, sizeof(struct ipc64_perm
) + 3*sizeof(time_t));
630 err2
|= __put_user (m
.msg_cbytes
, &up
->msg_cbytes
);
631 err2
|= __put_user (m
.msg_qnum
, &up
->msg_qnum
);
632 err2
|= __put_user (m
.msg_qbytes
, &up
->msg_qbytes
);
633 err2
|= __put_user (m
.msg_lspid
, &up
->msg_lspid
);
634 err2
|= __put_user (m
.msg_lrpid
, &up
->msg_lrpid
);
640 struct msqid_ds32
*up
= (struct msqid_ds32
*)uptr
;
643 if (second
== IPC_SET
) {
644 err
= get_user (m
.msg_perm
.uid
, &up
->msg_perm
.uid
);
645 err
|= __get_user (m
.msg_perm
.gid
, &up
->msg_perm
.gid
);
646 err
|= __get_user (m
.msg_perm
.mode
, &up
->msg_perm
.mode
);
647 err
|= __get_user (m
.msg_qbytes
, &up
->msg_qbytes
);
653 err
= sys_msgctl (first
, second
, &m
);
655 if (IPCOP_MASK (second
) &
656 (IPCOP_MASK (MSG_STAT
) | IPCOP_MASK (IPC_STAT
))) {
657 int err2
= put_user (m
.msg_perm
.key
, &up
->msg_perm
.key
);
658 err2
|= __put_user (high2lowuid(m
.msg_perm
.uid
), &up
->msg_perm
.uid
);
659 err2
|= __put_user (high2lowgid(m
.msg_perm
.gid
), &up
->msg_perm
.gid
);
660 err2
|= __put_user (high2lowuid(m
.msg_perm
.cuid
), &up
->msg_perm
.cuid
);
661 err2
|= __put_user (high2lowgid(m
.msg_perm
.cgid
), &up
->msg_perm
.cgid
);
662 err2
|= __put_user (m
.msg_perm
.mode
, &up
->msg_perm
.mode
);
663 err2
|= __put_user (m
.msg_perm
.seq
, &up
->msg_perm
.seq
);
664 err2
|= __put_user (m
.msg_stime
, &up
->msg_stime
);
665 err2
|= __put_user (m
.msg_rtime
, &up
->msg_rtime
);
666 err2
|= __put_user (m
.msg_ctime
, &up
->msg_ctime
);
667 err2
|= __put_user (m
.msg_cbytes
, &up
->msg_cbytes
);
668 err2
|= __put_user (m
.msg_qnum
, &up
->msg_qnum
);
669 err2
|= __put_user (m
.msg_qbytes
, &up
->msg_qbytes
);
670 err2
|= __put_user (m
.msg_lspid
, &up
->msg_lspid
);
671 err2
|= __put_user (m
.msg_lrpid
, &up
->msg_lrpid
);
681 static int do_sys32_shmat (int first
, int second
, int third
, int version
, void *uptr
)
684 u32
*uaddr
= (u32
*)A((u32
)third
);
689 err
= sys_shmat (first
, uptr
, second
, &raddr
);
692 err
= put_user (raddr
, uaddr
);
697 static int do_sys32_shmctl (int first
, int second
, void *uptr
)
701 if (IPCOP_MASK (second
) &
702 (IPCOP_MASK (IPC_INFO
) | IPCOP_MASK (SHM_LOCK
) | IPCOP_MASK (SHM_UNLOCK
) |
703 IPCOP_MASK (IPC_RMID
))) {
704 if (second
== (IPC_INFO
|IPC_64
))
705 second
= IPC_INFO
; /* So that we don't have to translate it */
706 err
= sys_shmctl (first
, second
, (struct shmid_ds
*)uptr
);
707 } else if ((second
& IPC_64
) && second
!= (SHM_INFO
|IPC_64
)) {
709 struct shmid64_ds32
*up
= (struct shmid64_ds32
*)uptr
;
712 if (second
== (IPC_SET
|IPC_64
)) {
713 err
= get_user (s
.shm_perm
.uid
, &up
->shm_perm
.uid
);
714 err
|= __get_user (s
.shm_perm
.gid
, &up
->shm_perm
.gid
);
715 err
|= __get_user (s
.shm_perm
.mode
, &up
->shm_perm
.mode
);
721 err
= sys_shmctl (first
, second
, (struct shmid_ds
*)&s
);
726 /* Mask it even in this case so it becomes a CSE. */
727 if (IPCOP_MASK (second
) &
728 (IPCOP_MASK (SHM_STAT
) | IPCOP_MASK (IPC_STAT
))) {
729 int err2
= copy_to_user (&up
->shm_perm
, &s
.shm_perm
, sizeof(struct ipc64_perm
) + 3*sizeof(time_t));
730 err2
|= __put_user (s
.shm_segsz
, &up
->shm_segsz
);
731 err2
|= __put_user (s
.shm_nattch
, &up
->shm_nattch
);
732 err2
|= __put_user (s
.shm_cpid
, &up
->shm_cpid
);
733 err2
|= __put_user (s
.shm_lpid
, &up
->shm_lpid
);
739 struct shmid_ds32
*up
= (struct shmid_ds32
*)uptr
;
743 if (second
== IPC_SET
) {
744 err
= get_user (s
.shm_perm
.uid
, &up
->shm_perm
.uid
);
745 err
|= __get_user (s
.shm_perm
.gid
, &up
->shm_perm
.gid
);
746 err
|= __get_user (s
.shm_perm
.mode
, &up
->shm_perm
.mode
);
752 err
= sys_shmctl (first
, second
, &s
);
757 /* Mask it even in this case so it becomes a CSE. */
758 if (second
== SHM_INFO
) {
761 u32 shm_tot
, shm_rss
, shm_swp
;
762 u32 swap_attempts
, swap_successes
;
763 } *uip
= (struct shm_info32
*)uptr
;
764 struct shm_info
*kp
= (struct shm_info
*)&s
;
765 int err2
= put_user (kp
->used_ids
, &uip
->used_ids
);
766 err2
|= __put_user (kp
->shm_tot
, &uip
->shm_tot
);
767 err2
|= __put_user (kp
->shm_rss
, &uip
->shm_rss
);
768 err2
|= __put_user (kp
->shm_swp
, &uip
->shm_swp
);
769 err2
|= __put_user (kp
->swap_attempts
, &uip
->swap_attempts
);
770 err2
|= __put_user (kp
->swap_successes
, &uip
->swap_successes
);
773 } else if (IPCOP_MASK (second
) &
774 (IPCOP_MASK (SHM_STAT
) | IPCOP_MASK (IPC_STAT
))) {
775 int err2
= put_user (s
.shm_perm
.key
, &up
->shm_perm
.key
);
776 err2
|= __put_user (high2lowuid(s
.shm_perm
.uid
), &up
->shm_perm
.uid
);
777 err2
|= __put_user (high2lowuid(s
.shm_perm
.gid
), &up
->shm_perm
.gid
);
778 err2
|= __put_user (high2lowuid(s
.shm_perm
.cuid
), &up
->shm_perm
.cuid
);
779 err2
|= __put_user (high2lowuid(s
.shm_perm
.cgid
), &up
->shm_perm
.cgid
);
780 err2
|= __put_user (s
.shm_perm
.mode
, &up
->shm_perm
.mode
);
781 err2
|= __put_user (s
.shm_perm
.seq
, &up
->shm_perm
.seq
);
782 err2
|= __put_user (s
.shm_atime
, &up
->shm_atime
);
783 err2
|= __put_user (s
.shm_dtime
, &up
->shm_dtime
);
784 err2
|= __put_user (s
.shm_ctime
, &up
->shm_ctime
);
785 err2
|= __put_user (s
.shm_segsz
, &up
->shm_segsz
);
786 err2
|= __put_user (s
.shm_nattch
, &up
->shm_nattch
);
787 err2
|= __put_user (s
.shm_cpid
, &up
->shm_cpid
);
788 err2
|= __put_user (s
.shm_lpid
, &up
->shm_lpid
);
797 asmlinkage
int sys32_ipc (u32 call
, int first
, int second
, int third
, u32 ptr
, u32 fifth
)
802 version
= call
>> 16; /* hack for backward compatibility */
808 /* struct sembuf is the same on 32 and 64bit :)) */
809 err
= sys_semop (first
, (struct sembuf
*)AA(ptr
), second
);
812 err
= sys_semget (first
, second
, third
);
815 err
= do_sys32_semctl (first
, second
, third
, (void *)AA(ptr
));
824 err
= do_sys32_msgsnd (first
, second
, third
, (void *)AA(ptr
));
827 err
= do_sys32_msgrcv (first
, second
, fifth
, third
,
828 version
, (void *)AA(ptr
));
831 err
= sys_msgget ((key_t
) first
, second
);
834 err
= do_sys32_msgctl (first
, second
, (void *)AA(ptr
));
843 err
= do_sys32_shmat (first
, second
, third
,
844 version
, (void *)AA(ptr
));
847 err
= sys_shmdt ((char *)AA(ptr
));
850 err
= sys_shmget (first
, second
, third
);
853 err
= do_sys32_shmctl (first
, second
, (void *)AA(ptr
));
867 static inline int get_flock(struct flock
*kfl
, struct flock32
*ufl
)
871 err
= get_user(kfl
->l_type
, &ufl
->l_type
);
872 err
|= __get_user(kfl
->l_whence
, &ufl
->l_whence
);
873 err
|= __get_user(kfl
->l_start
, &ufl
->l_start
);
874 err
|= __get_user(kfl
->l_len
, &ufl
->l_len
);
875 err
|= __get_user(kfl
->l_pid
, &ufl
->l_pid
);
879 static inline int put_flock(struct flock
*kfl
, struct flock32
*ufl
)
883 err
= __put_user(kfl
->l_type
, &ufl
->l_type
);
884 err
|= __put_user(kfl
->l_whence
, &ufl
->l_whence
);
885 err
|= __put_user(kfl
->l_start
, &ufl
->l_start
);
886 err
|= __put_user(kfl
->l_len
, &ufl
->l_len
);
887 err
|= __put_user(kfl
->l_pid
, &ufl
->l_pid
);
891 extern asmlinkage
long sys_fcntl(unsigned int fd
, unsigned int cmd
, unsigned long arg
);
893 asmlinkage
long sys32_fcntl(unsigned int fd
, unsigned int cmd
, unsigned long arg
)
904 if(get_flock(&f
, (struct flock32
*)arg
))
906 old_fs
= get_fs(); set_fs (KERNEL_DS
);
907 ret
= sys_fcntl(fd
, cmd
, (unsigned long)&f
);
909 if(put_flock(&f
, (struct flock32
*)arg
))
914 return sys_fcntl(fd
, cmd
, (unsigned long)arg
);
919 __u32 dqb_bhardlimit
;
920 __u32 dqb_bsoftlimit
;
922 __u32 dqb_ihardlimit
;
923 __u32 dqb_isoftlimit
;
925 __kernel_time_t32 dqb_btime
;
926 __kernel_time_t32 dqb_itime
;
929 extern asmlinkage
int sys_quotactl(int cmd
, const char *special
, int id
, caddr_t addr
);
931 asmlinkage
int sys32_quotactl(int cmd
, const char *special
, int id
, unsigned long addr
)
933 int cmds
= cmd
>> SUBCMDSHIFT
;
945 if (copy_from_user (&d
, (struct dqblk32
*)addr
,
946 sizeof (struct dqblk32
)))
948 d
.dqb_itime
= ((struct dqblk32
*)&d
)->dqb_itime
;
949 d
.dqb_btime
= ((struct dqblk32
*)&d
)->dqb_btime
;
952 return sys_quotactl(cmd
, special
,
955 spec
= getname32 (special
);
957 if (IS_ERR(spec
)) return err
;
960 err
= sys_quotactl(cmd
, (const char *)spec
, id
, (caddr_t
)&d
);
963 if (cmds
== Q_GETQUOTA
) {
964 __kernel_time_t b
= d
.dqb_btime
, i
= d
.dqb_itime
;
965 ((struct dqblk32
*)&d
)->dqb_itime
= i
;
966 ((struct dqblk32
*)&d
)->dqb_btime
= b
;
967 if (copy_to_user ((struct dqblk32
*)addr
, &d
,
968 sizeof (struct dqblk32
)))
974 static inline int put_statfs (struct statfs32
*ubuf
, struct statfs
*kbuf
)
978 err
= put_user (kbuf
->f_type
, &ubuf
->f_type
);
979 err
|= __put_user (kbuf
->f_bsize
, &ubuf
->f_bsize
);
980 err
|= __put_user (kbuf
->f_blocks
, &ubuf
->f_blocks
);
981 err
|= __put_user (kbuf
->f_bfree
, &ubuf
->f_bfree
);
982 err
|= __put_user (kbuf
->f_bavail
, &ubuf
->f_bavail
);
983 err
|= __put_user (kbuf
->f_files
, &ubuf
->f_files
);
984 err
|= __put_user (kbuf
->f_ffree
, &ubuf
->f_ffree
);
985 err
|= __put_user (kbuf
->f_namelen
, &ubuf
->f_namelen
);
986 err
|= __put_user (kbuf
->f_fsid
.val
[0], &ubuf
->f_fsid
.val
[0]);
987 err
|= __put_user (kbuf
->f_fsid
.val
[1], &ubuf
->f_fsid
.val
[1]);
991 extern asmlinkage
int sys_statfs(const char * path
, struct statfs
* buf
);
993 asmlinkage
int sys32_statfs(const char * path
, struct statfs32
*buf
)
997 mm_segment_t old_fs
= get_fs();
1000 pth
= getname32 (path
);
1004 ret
= sys_statfs((const char *)pth
, &s
);
1007 if (put_statfs(buf
, &s
))
1013 extern asmlinkage
int sys_fstatfs(unsigned int fd
, struct statfs
* buf
);
1015 asmlinkage
int sys32_fstatfs(unsigned int fd
, struct statfs32
*buf
)
1019 mm_segment_t old_fs
= get_fs();
1022 ret
= sys_fstatfs(fd
, &s
);
1024 if (put_statfs(buf
, &s
))
1029 extern asmlinkage
long sys_truncate(const char * path
, unsigned long length
);
1030 extern asmlinkage
long sys_ftruncate(unsigned int fd
, unsigned long length
);
1032 asmlinkage
int sys32_truncate64(const char * path
, unsigned long high
, unsigned long low
)
1037 return sys_truncate(path
, (high
<< 32) | low
);
1040 asmlinkage
int sys32_ftruncate64(unsigned int fd
, unsigned long high
, unsigned long low
)
1045 return sys_ftruncate(fd
, (high
<< 32) | low
);
1048 extern asmlinkage
int sys_utime(char * filename
, struct utimbuf
* times
);
1051 __kernel_time_t32 actime
, modtime
;
1054 asmlinkage
int sys32_utime(char * filename
, struct utimbuf32
*times
)
1057 mm_segment_t old_fs
;
1062 return sys_utime(filename
, NULL
);
1063 if (get_user (t
.actime
, ×
->actime
) ||
1064 __get_user (t
.modtime
, ×
->modtime
))
1066 filenam
= getname32 (filename
);
1067 ret
= PTR_ERR(filenam
);
1068 if (!IS_ERR(filenam
)) {
1071 ret
= sys_utime(filenam
, &t
);
1078 struct iovec32
{ u32 iov_base
; __kernel_size_t32 iov_len
; };
1080 typedef ssize_t (*IO_fn_t
)(struct file
*, char *, size_t, loff_t
*);
1082 static long do_readv_writev32(int type
, struct file
*file
,
1083 const struct iovec32
*vector
, u32 count
)
1085 unsigned long tot_len
;
1086 struct iovec iovstack
[UIO_FASTIOV
];
1087 struct iovec
*iov
=iovstack
, *ivp
;
1088 struct inode
*inode
;
1092 /* First get the "struct iovec" from user memory and
1093 * verify all the pointers
1097 if(verify_area(VERIFY_READ
, vector
, sizeof(struct iovec32
)*count
))
1099 if (count
> UIO_MAXIOV
)
1101 if (count
> UIO_FASTIOV
) {
1102 iov
= kmalloc(count
*sizeof(struct iovec
), GFP_KERNEL
);
1114 __get_user(len
, &vector
->iov_len
);
1115 __get_user(buf
, &vector
->iov_base
);
1117 ivp
->iov_base
= (void *)A(buf
);
1118 ivp
->iov_len
= (__kernel_size_t
) len
;
1124 inode
= file
->f_dentry
->d_inode
;
1125 /* VERIFY_WRITE actually means a read, as we write to user space */
1126 retval
= locks_verify_area((type
== VERIFY_WRITE
1127 ? FLOCK_VERIFY_READ
: FLOCK_VERIFY_WRITE
),
1128 inode
, file
, file
->f_pos
, tot_len
);
1130 if (iov
!= iovstack
)
1135 /* Then do the actual IO. Note that sockets need to be handled
1136 * specially as they have atomicity guarantees and can handle
1139 if (inode
->i_sock
) {
1141 err
= sock_readv_writev(type
, inode
, file
, iov
, count
, tot_len
);
1142 if (iov
!= iovstack
)
1148 if (iov
!= iovstack
)
1152 /* VERIFY_WRITE actually means a read, as we write to user space */
1153 fn
= file
->f_op
->read
;
1154 if (type
== VERIFY_READ
)
1155 fn
= (IO_fn_t
) file
->f_op
->write
;
1161 base
= ivp
->iov_base
;
1165 nr
= fn(file
, base
, len
, &file
->f_pos
);
1176 if (iov
!= iovstack
)
1181 asmlinkage
long sys32_readv(int fd
, struct iovec32
*vector
, u32 count
)
1192 if (file
->f_op
&& file
->f_op
->read
&& (file
->f_mode
& FMODE_READ
))
1193 ret
= do_readv_writev32(VERIFY_WRITE
, file
, vector
, count
);
1201 asmlinkage
long sys32_writev(int fd
, struct iovec32
*vector
, u32 count
)
1211 if (file
->f_op
&& file
->f_op
->write
&& (file
->f_mode
& FMODE_WRITE
))
1212 ret
= do_readv_writev32(VERIFY_READ
, file
, vector
, count
);
1220 /* readdir & getdents */
1222 #define NAME_OFFSET(de) ((int) ((de)->d_name - (char *) (de)))
1223 #define ROUND_UP(x) (((x)+sizeof(u32)-1) & ~(sizeof(u32)-1))
1225 struct old_linux_dirent32
{
1228 unsigned short d_namlen
;
1232 struct readdir_callback32
{
1233 struct old_linux_dirent32
* dirent
;
1237 static int fillonedir(void * __buf
, const char * name
, int namlen
,
1238 off_t offset
, ino_t ino
)
1240 struct readdir_callback32
* buf
= (struct readdir_callback32
*) __buf
;
1241 struct old_linux_dirent32
* dirent
;
1246 dirent
= buf
->dirent
;
1247 put_user(ino
, &dirent
->d_ino
);
1248 put_user(offset
, &dirent
->d_offset
);
1249 put_user(namlen
, &dirent
->d_namlen
);
1250 copy_to_user(dirent
->d_name
, name
, namlen
);
1251 put_user(0, dirent
->d_name
+ namlen
);
1255 asmlinkage
int old32_readdir(unsigned int fd
, struct old_linux_dirent32
*dirent
, unsigned int count
)
1259 struct inode
* inode
;
1260 struct readdir_callback32 buf
;
1268 buf
.dirent
= dirent
;
1271 if (!file
->f_op
|| !file
->f_op
->readdir
)
1274 inode
= file
->f_dentry
->d_inode
;
1275 down(&inode
->i_sem
);
1276 error
= file
->f_op
->readdir(file
, &buf
, fillonedir
);
1289 struct linux_dirent32
{
1292 unsigned short d_reclen
;
1296 struct getdents_callback32
{
1297 struct linux_dirent32
* current_dir
;
1298 struct linux_dirent32
* previous
;
1303 static int filldir(void * __buf
, const char * name
, int namlen
, off_t offset
, ino_t ino
)
1305 struct linux_dirent32
* dirent
;
1306 struct getdents_callback32
* buf
= (struct getdents_callback32
*) __buf
;
1307 int reclen
= ROUND_UP(NAME_OFFSET(dirent
) + namlen
+ 1);
1309 buf
->error
= -EINVAL
; /* only used if we fail.. */
1310 if (reclen
> buf
->count
)
1312 dirent
= buf
->previous
;
1314 put_user(offset
, &dirent
->d_off
);
1315 dirent
= buf
->current_dir
;
1316 buf
->previous
= dirent
;
1317 put_user(ino
, &dirent
->d_ino
);
1318 put_user(reclen
, &dirent
->d_reclen
);
1319 copy_to_user(dirent
->d_name
, name
, namlen
);
1320 put_user(0, dirent
->d_name
+ namlen
);
1321 ((char *) dirent
) += reclen
;
1322 buf
->current_dir
= dirent
;
1323 buf
->count
-= reclen
;
1327 asmlinkage
int sys32_getdents(unsigned int fd
, struct linux_dirent32
*dirent
, unsigned int count
)
1330 struct inode
* inode
;
1331 struct linux_dirent32
* lastdirent
;
1332 struct getdents_callback32 buf
;
1340 buf
.current_dir
= dirent
;
1341 buf
.previous
= NULL
;
1346 if (!file
->f_op
|| !file
->f_op
->readdir
)
1349 inode
= file
->f_dentry
->d_inode
;
1350 down(&inode
->i_sem
);
1351 error
= file
->f_op
->readdir(file
, &buf
, filldir
);
1355 lastdirent
= buf
.previous
;
1358 put_user(file
->f_pos
, &lastdirent
->d_off
);
1359 error
= count
- buf
.count
;
1368 /* end of readdir & getdents */
1371 * Ooo, nasty. We need here to frob 32-bit unsigned longs to
1372 * 64-bit unsigned longs.
1376 get_fd_set32(unsigned long n
, unsigned long *fdset
, u32
*ufdset
)
1381 if (verify_area(VERIFY_WRITE
, ufdset
, n
*sizeof(u32
)))
1388 __get_user(l
, ufdset
);
1389 __get_user(h
, ufdset
+1);
1391 *fdset
++ = h
<< 32 | l
;
1395 __get_user(*fdset
, ufdset
);
1397 /* Tricky, must clear full unsigned long in the
1398 * kernel fdset at the end, this makes sure that
1401 memset(fdset
, 0, ((n
+ 1) & ~1)*sizeof(u32
));
1407 set_fd_set32(unsigned long n
, u32
*ufdset
, unsigned long *fdset
)
1420 __put_user(l
, ufdset
);
1421 __put_user(h
, ufdset
+1);
1426 __put_user(*fdset
, ufdset
);
1429 #define MAX_SELECT_SECONDS \
1430 ((unsigned long) (MAX_SCHEDULE_TIMEOUT / HZ)-1)
1432 asmlinkage
int sys32_select(int n
, u32
*inp
, u32
*outp
, u32
*exp
, u32 tvp_x
)
1435 struct timeval32
*tvp
= (struct timeval32
*)AA(tvp_x
);
1441 timeout
= MAX_SCHEDULE_TIMEOUT
;
1445 if ((ret
= verify_area(VERIFY_READ
, tvp
, sizeof(*tvp
)))
1446 || (ret
= __get_user(sec
, &tvp
->tv_sec
))
1447 || (ret
= __get_user(usec
, &tvp
->tv_usec
)))
1451 if(sec
< 0 || usec
< 0)
1454 if ((unsigned long) sec
< MAX_SELECT_SECONDS
) {
1455 timeout
= (usec
+ 1000000/HZ
- 1) / (1000000/HZ
);
1456 timeout
+= sec
* (unsigned long) HZ
;
1463 if (n
> current
->files
->max_fdset
)
1464 n
= current
->files
->max_fdset
;
1467 * We need 6 bitmaps (in/out/ex for both incoming and outgoing),
1468 * since we used fdset we need to allocate memory in units of
1472 size
= FDS_BYTES(n
);
1473 bits
= kmalloc(6 * size
, GFP_KERNEL
);
1476 fds
.in
= (unsigned long *) bits
;
1477 fds
.out
= (unsigned long *) (bits
+ size
);
1478 fds
.ex
= (unsigned long *) (bits
+ 2*size
);
1479 fds
.res_in
= (unsigned long *) (bits
+ 3*size
);
1480 fds
.res_out
= (unsigned long *) (bits
+ 4*size
);
1481 fds
.res_ex
= (unsigned long *) (bits
+ 5*size
);
1483 nn
= (n
+ 8*sizeof(u32
) - 1) / (8*sizeof(u32
));
1484 if ((ret
= get_fd_set32(nn
, fds
.in
, inp
)) ||
1485 (ret
= get_fd_set32(nn
, fds
.out
, outp
)) ||
1486 (ret
= get_fd_set32(nn
, fds
.ex
, exp
)))
1488 zero_fd_set(n
, fds
.res_in
);
1489 zero_fd_set(n
, fds
.res_out
);
1490 zero_fd_set(n
, fds
.res_ex
);
1492 ret
= do_select(n
, &fds
, &timeout
);
1494 if (tvp
&& !(current
->personality
& STICKY_TIMEOUTS
)) {
1495 time_t sec
= 0, usec
= 0;
1498 usec
= timeout
% HZ
;
1499 usec
*= (1000000/HZ
);
1501 put_user(sec
, &tvp
->tv_sec
);
1502 put_user(usec
, &tvp
->tv_usec
);
1508 ret
= -ERESTARTNOHAND
;
1509 if (signal_pending(current
))
1514 set_fd_set32(nn
, inp
, fds
.res_in
);
1515 set_fd_set32(nn
, outp
, fds
.res_out
);
1516 set_fd_set32(nn
, exp
, fds
.res_ex
);
1524 static int cp_new_stat32(struct inode
*inode
, struct stat32
*statbuf
)
1526 unsigned long ino
, blksize
, blocks
;
1533 time_t atime
, mtime
, ctime
;
1536 /* Stream the loads of inode data into the load buffer,
1537 * then we push it all into the store buffer below. This
1538 * should give optimal cache performance.
1542 mode
= inode
->i_mode
;
1543 nlink
= inode
->i_nlink
;
1546 rdev
= inode
->i_rdev
;
1547 size
= inode
->i_size
;
1548 atime
= inode
->i_atime
;
1549 mtime
= inode
->i_mtime
;
1550 ctime
= inode
->i_ctime
;
1551 blksize
= inode
->i_blksize
;
1552 blocks
= inode
->i_blocks
;
1554 err
= put_user(kdev_t_to_nr(dev
), &statbuf
->st_dev
);
1555 err
|= put_user(ino
, &statbuf
->st_ino
);
1556 err
|= put_user(mode
, &statbuf
->st_mode
);
1557 err
|= put_user(nlink
, &statbuf
->st_nlink
);
1558 err
|= put_user(high2lowuid(uid
), &statbuf
->st_uid
);
1559 err
|= put_user(high2lowgid(gid
), &statbuf
->st_gid
);
1560 err
|= put_user(kdev_t_to_nr(rdev
), &statbuf
->st_rdev
);
1561 err
|= put_user(size
, &statbuf
->st_size
);
1562 err
|= put_user(atime
, &statbuf
->st_atime
);
1563 err
|= put_user(0, &statbuf
->__unused1
);
1564 err
|= put_user(mtime
, &statbuf
->st_mtime
);
1565 err
|= put_user(0, &statbuf
->__unused2
);
1566 err
|= put_user(ctime
, &statbuf
->st_ctime
);
1567 err
|= put_user(0, &statbuf
->__unused3
);
1569 err
|= put_user(blksize
, &statbuf
->st_blksize
);
1570 err
|= put_user(blocks
, &statbuf
->st_blocks
);
1572 unsigned int tmp_blocks
;
1575 #define I_B (BLOCK_SIZE / sizeof(unsigned short))
1576 tmp_blocks
= (size
+ BLOCK_SIZE
- 1) / BLOCK_SIZE
;
1577 if (tmp_blocks
> D_B
) {
1578 unsigned int indirect
;
1580 indirect
= (tmp_blocks
- D_B
+ I_B
- 1) / I_B
;
1581 tmp_blocks
+= indirect
;
1583 indirect
= (indirect
- 1 + I_B
- 1) / I_B
;
1584 tmp_blocks
+= indirect
;
1589 err
|= put_user(BLOCK_SIZE
, &statbuf
->st_blksize
);
1590 err
|= put_user((BLOCK_SIZE
/ 512) * tmp_blocks
, &statbuf
->st_blocks
);
1594 err
|= put_user(0, &statbuf
->__unused4
[0]);
1595 err
|= put_user(0, &statbuf
->__unused4
[1]);
1600 asmlinkage
int sys32_newstat(char * filename
, struct stat32
*statbuf
)
1602 struct dentry
*dentry
;
1606 dentry
= namei(filename
);
1608 error
= PTR_ERR(dentry
);
1609 if (!IS_ERR(dentry
)) {
1610 struct inode
*inode
= dentry
->d_inode
;
1613 inode
->i_op
->revalidate
)
1614 error
= inode
->i_op
->revalidate(dentry
);
1618 error
= cp_new_stat32(inode
, statbuf
);
1626 asmlinkage
int sys32_newlstat(char * filename
, struct stat32
*statbuf
)
1628 struct dentry
*dentry
;
1632 dentry
= lnamei(filename
);
1634 error
= PTR_ERR(dentry
);
1635 if (!IS_ERR(dentry
)) {
1636 struct inode
*inode
= dentry
->d_inode
;
1639 inode
->i_op
->revalidate
)
1640 error
= inode
->i_op
->revalidate(dentry
);
1644 error
= cp_new_stat32(inode
, statbuf
);
1652 asmlinkage
int sys32_newfstat(unsigned int fd
, struct stat32
*statbuf
)
1660 struct dentry
*dentry
= f
->f_dentry
;
1661 struct inode
*inode
= dentry
->d_inode
;
1664 inode
->i_op
->revalidate
)
1665 err
= inode
->i_op
->revalidate(dentry
);
1669 err
= cp_new_stat32(inode
, statbuf
);
1677 extern asmlinkage
int sys_sysfs(int option
, unsigned long arg1
, unsigned long arg2
);
1679 asmlinkage
int sys32_sysfs(int option
, u32 arg1
, u32 arg2
)
1681 return sys_sysfs(option
, arg1
, arg2
);
1684 struct ncp_mount_data32
{
1686 unsigned int ncp_fd
;
1687 __kernel_uid_t32 mounted_uid
;
1688 __kernel_pid_t32 wdog_pid
;
1689 unsigned char mounted_vol
[NCP_VOLNAME_LEN
+ 1];
1690 unsigned int time_out
;
1691 unsigned int retry_count
;
1693 __kernel_uid_t32 uid
;
1694 __kernel_gid_t32 gid
;
1695 __kernel_mode_t32 file_mode
;
1696 __kernel_mode_t32 dir_mode
;
1699 static void *do_ncp_super_data_conv(void *raw_data
)
1701 struct ncp_mount_data
*n
= (struct ncp_mount_data
*)raw_data
;
1702 struct ncp_mount_data32
*n32
= (struct ncp_mount_data32
*)raw_data
;
1704 n
->dir_mode
= n32
->dir_mode
;
1705 n
->file_mode
= n32
->file_mode
;
1706 n
->gid
= low2highgid(n32
->gid
);
1707 n
->uid
= low2highuid(n32
->uid
);
1708 memmove (n
->mounted_vol
, n32
->mounted_vol
, (sizeof (n32
->mounted_vol
) + 3 * sizeof (unsigned int)));
1709 n
->wdog_pid
= n32
->wdog_pid
;
1710 n
->mounted_uid
= low2highuid(n32
->mounted_uid
);
1714 struct smb_mount_data32
{
1716 __kernel_uid_t32 mounted_uid
;
1717 __kernel_uid_t32 uid
;
1718 __kernel_gid_t32 gid
;
1719 __kernel_mode_t32 file_mode
;
1720 __kernel_mode_t32 dir_mode
;
1723 static void *do_smb_super_data_conv(void *raw_data
)
1725 struct smb_mount_data
*s
= (struct smb_mount_data
*)raw_data
;
1726 struct smb_mount_data32
*s32
= (struct smb_mount_data32
*)raw_data
;
1728 s
->version
= s32
->version
;
1729 s
->mounted_uid
= low2highuid(s32
->mounted_uid
);
1730 s
->uid
= low2highuid(s32
->uid
);
1731 s
->gid
= low2highgid(s32
->gid
);
1732 s
->file_mode
= s32
->file_mode
;
1733 s
->dir_mode
= s32
->dir_mode
;
1737 static int copy_mount_stuff_to_kernel(const void *user
, unsigned long *kernel
)
1741 struct vm_area_struct
*vma
;
1746 vma
= find_vma(current
->mm
, (unsigned long)user
);
1747 if(!vma
|| (unsigned long)user
< vma
->vm_start
)
1749 if(!(vma
->vm_flags
& VM_READ
))
1751 i
= vma
->vm_end
- (unsigned long) user
;
1752 if(PAGE_SIZE
<= (unsigned long) i
)
1754 if(!(page
= __get_free_page(GFP_KERNEL
)))
1756 if(copy_from_user((void *) page
, user
, i
)) {
1764 extern asmlinkage
int sys_mount(char * dev_name
, char * dir_name
, char * type
,
1765 unsigned long new_flags
, void *data
);
1767 #define SMBFS_NAME "smbfs"
1768 #define NCPFS_NAME "ncpfs"
1770 asmlinkage
int sys32_mount(char *dev_name
, char *dir_name
, char *type
, unsigned long new_flags
, u32 data
)
1772 unsigned long type_page
;
1773 int err
, is_smb
, is_ncp
;
1775 if(!capable(CAP_SYS_ADMIN
))
1777 is_smb
= is_ncp
= 0;
1778 err
= copy_mount_stuff_to_kernel((const void *)type
, &type_page
);
1782 is_smb
= !strcmp((char *)type_page
, SMBFS_NAME
);
1783 is_ncp
= !strcmp((char *)type_page
, NCPFS_NAME
);
1785 if(!is_smb
&& !is_ncp
) {
1787 free_page(type_page
);
1788 return sys_mount(dev_name
, dir_name
, type
, new_flags
, (void *)AA(data
));
1790 unsigned long dev_page
, dir_page
, data_page
;
1791 mm_segment_t old_fs
;
1793 err
= copy_mount_stuff_to_kernel((const void *)dev_name
, &dev_page
);
1796 err
= copy_mount_stuff_to_kernel((const void *)dir_name
, &dir_page
);
1799 err
= copy_mount_stuff_to_kernel((const void *)AA(data
), &data_page
);
1803 do_ncp_super_data_conv((void *)data_page
);
1805 do_smb_super_data_conv((void *)data_page
);
1807 panic("The problem is here...");
1810 err
= sys_mount((char *)dev_page
, (char *)dir_page
,
1811 (char *)type_page
, new_flags
,
1816 free_page(data_page
);
1819 free_page(dir_page
);
1822 free_page(dev_page
);
1825 free_page(type_page
);
1831 struct timeval32 ru_utime
;
1832 struct timeval32 ru_stime
;
1849 static int put_rusage (struct rusage32
*ru
, struct rusage
*r
)
1853 err
= put_user (r
->ru_utime
.tv_sec
, &ru
->ru_utime
.tv_sec
);
1854 err
|= __put_user (r
->ru_utime
.tv_usec
, &ru
->ru_utime
.tv_usec
);
1855 err
|= __put_user (r
->ru_stime
.tv_sec
, &ru
->ru_stime
.tv_sec
);
1856 err
|= __put_user (r
->ru_stime
.tv_usec
, &ru
->ru_stime
.tv_usec
);
1857 err
|= __put_user (r
->ru_maxrss
, &ru
->ru_maxrss
);
1858 err
|= __put_user (r
->ru_ixrss
, &ru
->ru_ixrss
);
1859 err
|= __put_user (r
->ru_idrss
, &ru
->ru_idrss
);
1860 err
|= __put_user (r
->ru_isrss
, &ru
->ru_isrss
);
1861 err
|= __put_user (r
->ru_minflt
, &ru
->ru_minflt
);
1862 err
|= __put_user (r
->ru_majflt
, &ru
->ru_majflt
);
1863 err
|= __put_user (r
->ru_nswap
, &ru
->ru_nswap
);
1864 err
|= __put_user (r
->ru_inblock
, &ru
->ru_inblock
);
1865 err
|= __put_user (r
->ru_oublock
, &ru
->ru_oublock
);
1866 err
|= __put_user (r
->ru_msgsnd
, &ru
->ru_msgsnd
);
1867 err
|= __put_user (r
->ru_msgrcv
, &ru
->ru_msgrcv
);
1868 err
|= __put_user (r
->ru_nsignals
, &ru
->ru_nsignals
);
1869 err
|= __put_user (r
->ru_nvcsw
, &ru
->ru_nvcsw
);
1870 err
|= __put_user (r
->ru_nivcsw
, &ru
->ru_nivcsw
);
1874 extern asmlinkage
int sys_wait4(pid_t pid
,unsigned int * stat_addr
,
1875 int options
, struct rusage
* ru
);
1877 asmlinkage
int sys32_wait4(__kernel_pid_t32 pid
, unsigned int *stat_addr
, int options
, struct rusage32
*ru
)
1880 return sys_wait4(pid
, stat_addr
, options
, NULL
);
1884 unsigned int status
;
1885 mm_segment_t old_fs
= get_fs();
1888 ret
= sys_wait4(pid
, stat_addr
? &status
: NULL
, options
, &r
);
1890 if (put_rusage (ru
, &r
)) return -EFAULT
;
1891 if (stat_addr
&& put_user (status
, stat_addr
))
1906 unsigned short procs
;
1910 extern asmlinkage
int sys_sysinfo(struct sysinfo
*info
);
1912 asmlinkage
int sys32_sysinfo(struct sysinfo32
*info
)
1916 mm_segment_t old_fs
= get_fs ();
1919 ret
= sys_sysinfo(&s
);
1921 err
= put_user (s
.uptime
, &info
->uptime
);
1922 err
|= __put_user (s
.loads
[0], &info
->loads
[0]);
1923 err
|= __put_user (s
.loads
[1], &info
->loads
[1]);
1924 err
|= __put_user (s
.loads
[2], &info
->loads
[2]);
1925 err
|= __put_user (s
.totalram
, &info
->totalram
);
1926 err
|= __put_user (s
.freeram
, &info
->freeram
);
1927 err
|= __put_user (s
.sharedram
, &info
->sharedram
);
1928 err
|= __put_user (s
.bufferram
, &info
->bufferram
);
1929 err
|= __put_user (s
.totalswap
, &info
->totalswap
);
1930 err
|= __put_user (s
.freeswap
, &info
->freeswap
);
1931 err
|= __put_user (s
.procs
, &info
->procs
);
1942 extern asmlinkage
int sys_sched_rr_get_interval(pid_t pid
, struct timespec
*interval
);
1944 asmlinkage
int sys32_sched_rr_get_interval(__kernel_pid_t32 pid
, struct timespec32
*interval
)
1948 mm_segment_t old_fs
= get_fs ();
1951 ret
= sys_sched_rr_get_interval(pid
, &t
);
1953 if (put_user (t
.tv_sec
, &interval
->tv_sec
) ||
1954 __put_user (t
.tv_nsec
, &interval
->tv_nsec
))
1959 extern asmlinkage
int sys_nanosleep(struct timespec
*rqtp
, struct timespec
*rmtp
);
1961 asmlinkage
int sys32_nanosleep(struct timespec32
*rqtp
, struct timespec32
*rmtp
)
1965 mm_segment_t old_fs
= get_fs ();
1967 if (get_user (t
.tv_sec
, &rqtp
->tv_sec
) ||
1968 __get_user (t
.tv_nsec
, &rqtp
->tv_nsec
))
1971 ret
= sys_nanosleep(&t
, rmtp
? &t
: NULL
);
1973 if (rmtp
&& ret
== -EINTR
) {
1974 if (__put_user (t
.tv_sec
, &rmtp
->tv_sec
) ||
1975 __put_user (t
.tv_nsec
, &rmtp
->tv_nsec
))
1981 extern asmlinkage
int sys_sigprocmask(int how
, old_sigset_t
*set
, old_sigset_t
*oset
);
1983 asmlinkage
int sys32_sigprocmask(int how
, old_sigset_t32
*set
, old_sigset_t32
*oset
)
1987 mm_segment_t old_fs
= get_fs();
1989 if (set
&& get_user (s
, set
)) return -EFAULT
;
1991 ret
= sys_sigprocmask(how
, set
? &s
: NULL
, oset
? &s
: NULL
);
1993 if (ret
) return ret
;
1994 if (oset
&& put_user (s
, oset
)) return -EFAULT
;
1998 extern asmlinkage
int sys_rt_sigprocmask(int how
, sigset_t
*set
, sigset_t
*oset
, size_t sigsetsize
);
2000 asmlinkage
int sys32_rt_sigprocmask(int how
, sigset_t32
*set
, sigset_t32
*oset
, __kernel_size_t32 sigsetsize
)
2005 mm_segment_t old_fs
= get_fs();
2008 if (copy_from_user (&s32
, set
, sizeof(sigset_t32
)))
2010 switch (_NSIG_WORDS
) {
2011 case 4: s
.sig
[3] = s32
.sig
[6] | (((long)s32
.sig
[7]) << 32);
2012 case 3: s
.sig
[2] = s32
.sig
[4] | (((long)s32
.sig
[5]) << 32);
2013 case 2: s
.sig
[1] = s32
.sig
[2] | (((long)s32
.sig
[3]) << 32);
2014 case 1: s
.sig
[0] = s32
.sig
[0] | (((long)s32
.sig
[1]) << 32);
2018 ret
= sys_rt_sigprocmask(how
, set
? &s
: NULL
, oset
? &s
: NULL
, sigsetsize
);
2020 if (ret
) return ret
;
2022 switch (_NSIG_WORDS
) {
2023 case 4: s32
.sig
[7] = (s
.sig
[3] >> 32); s32
.sig
[6] = s
.sig
[3];
2024 case 3: s32
.sig
[5] = (s
.sig
[2] >> 32); s32
.sig
[4] = s
.sig
[2];
2025 case 2: s32
.sig
[3] = (s
.sig
[1] >> 32); s32
.sig
[2] = s
.sig
[1];
2026 case 1: s32
.sig
[1] = (s
.sig
[0] >> 32); s32
.sig
[0] = s
.sig
[0];
2028 if (copy_to_user (oset
, &s32
, sizeof(sigset_t32
)))
2034 extern asmlinkage
int sys_sigpending(old_sigset_t
*set
);
2036 asmlinkage
int sys32_sigpending(old_sigset_t32
*set
)
2040 mm_segment_t old_fs
= get_fs();
2043 ret
= sys_sigpending(&s
);
2045 if (put_user (s
, set
)) return -EFAULT
;
2049 extern asmlinkage
int sys_rt_sigpending(sigset_t
*set
, size_t sigsetsize
);
2051 asmlinkage
int sys32_rt_sigpending(sigset_t32
*set
, __kernel_size_t32 sigsetsize
)
2056 mm_segment_t old_fs
= get_fs();
2059 ret
= sys_rt_sigpending(&s
, sigsetsize
);
2062 switch (_NSIG_WORDS
) {
2063 case 4: s32
.sig
[7] = (s
.sig
[3] >> 32); s32
.sig
[6] = s
.sig
[3];
2064 case 3: s32
.sig
[5] = (s
.sig
[2] >> 32); s32
.sig
[4] = s
.sig
[2];
2065 case 2: s32
.sig
[3] = (s
.sig
[1] >> 32); s32
.sig
[2] = s
.sig
[1];
2066 case 1: s32
.sig
[1] = (s
.sig
[0] >> 32); s32
.sig
[0] = s
.sig
[0];
2068 if (copy_to_user (set
, &s32
, sizeof(sigset_t32
)))
2074 extern asmlinkage
int
2075 sys_rt_sigtimedwait(const sigset_t
*uthese
, siginfo_t
*uinfo
,
2076 const struct timespec
*uts
, size_t sigsetsize
);
2079 sys32_rt_sigtimedwait(sigset_t32
*uthese
, siginfo_t32
*uinfo
,
2080 struct timespec32
*uts
, __kernel_size_t32 sigsetsize
)
2086 mm_segment_t old_fs
= get_fs();
2089 if (copy_from_user (&s32
, uthese
, sizeof(sigset_t32
)))
2091 switch (_NSIG_WORDS
) {
2092 case 4: s
.sig
[3] = s32
.sig
[6] | (((long)s32
.sig
[7]) << 32);
2093 case 3: s
.sig
[2] = s32
.sig
[4] | (((long)s32
.sig
[5]) << 32);
2094 case 2: s
.sig
[1] = s32
.sig
[2] | (((long)s32
.sig
[3]) << 32);
2095 case 1: s
.sig
[0] = s32
.sig
[0] | (((long)s32
.sig
[1]) << 32);
2098 ret
= get_user (t
.tv_sec
, &uts
->tv_sec
);
2099 ret
|= __get_user (t
.tv_nsec
, &uts
->tv_nsec
);
2104 ret
= sys_rt_sigtimedwait(&s
, &info
, &t
, sigsetsize
);
2106 if (ret
>= 0 && uinfo
) {
2107 extern int copy_siginfo_to_user32(siginfo_t32
*, siginfo_t
*);
2108 if (copy_siginfo_to_user32(uinfo
, &info
))
2114 extern asmlinkage
int
2115 sys_rt_sigqueueinfo(int pid
, int sig
, siginfo_t
*uinfo
);
2118 sys32_rt_sigqueueinfo(int pid
, int sig
, siginfo_t32
*uinfo
)
2122 mm_segment_t old_fs
= get_fs();
2124 if (copy_from_user (&info
, uinfo
, 3*sizeof(int)) ||
2125 copy_from_user (info
._sifields
._pad
, uinfo
->_sifields
._pad
, SI_PAD_SIZE
))
2128 ret
= sys_rt_sigqueueinfo(pid
, sig
, &info
);
2134 __kernel_clock_t32 tms_utime
;
2135 __kernel_clock_t32 tms_stime
;
2136 __kernel_clock_t32 tms_cutime
;
2137 __kernel_clock_t32 tms_cstime
;
2140 extern asmlinkage
long sys_times(struct tms
* tbuf
);
2142 asmlinkage
long sys32_times(struct tms32
*tbuf
)
2146 mm_segment_t old_fs
= get_fs ();
2150 ret
= sys_times(tbuf
? &t
: NULL
);
2153 err
= put_user (t
.tms_utime
, &tbuf
->tms_utime
);
2154 err
|= __put_user (t
.tms_stime
, &tbuf
->tms_stime
);
2155 err
|= __put_user (t
.tms_cutime
, &tbuf
->tms_cutime
);
2156 err
|= __put_user (t
.tms_cstime
, &tbuf
->tms_cstime
);
2163 #define RLIM_INFINITY32 0x7fffffff
2164 #define RESOURCE32(x) ((x > RLIM_INFINITY32) ? RLIM_INFINITY32 : x)
2171 extern asmlinkage
int sys_getrlimit(unsigned int resource
, struct rlimit
*rlim
);
2173 asmlinkage
int sys32_getrlimit(unsigned int resource
, struct rlimit32
*rlim
)
2177 mm_segment_t old_fs
= get_fs ();
2180 ret
= sys_getrlimit(resource
, &r
);
2183 ret
= put_user (RESOURCE32(r
.rlim_cur
), &rlim
->rlim_cur
);
2184 ret
|= __put_user (RESOURCE32(r
.rlim_max
), &rlim
->rlim_max
);
2189 extern asmlinkage
int sys_setrlimit(unsigned int resource
, struct rlimit
*rlim
);
2191 asmlinkage
int sys32_setrlimit(unsigned int resource
, struct rlimit32
*rlim
)
2195 mm_segment_t old_fs
= get_fs ();
2197 if (resource
>= RLIM_NLIMITS
) return -EINVAL
;
2198 if (get_user (r
.rlim_cur
, &rlim
->rlim_cur
) ||
2199 __get_user (r
.rlim_max
, &rlim
->rlim_max
))
2201 if (r
.rlim_cur
== RLIM_INFINITY32
)
2202 r
.rlim_cur
= RLIM_INFINITY
;
2203 if (r
.rlim_max
== RLIM_INFINITY32
)
2204 r
.rlim_max
= RLIM_INFINITY
;
2206 ret
= sys_setrlimit(resource
, &r
);
2211 extern asmlinkage
int sys_getrusage(int who
, struct rusage
*ru
);
2213 asmlinkage
int sys32_getrusage(int who
, struct rusage32
*ru
)
2217 mm_segment_t old_fs
= get_fs();
2220 ret
= sys_getrusage(who
, &r
);
2222 if (put_rusage (ru
, &r
)) return -EFAULT
;
2226 /* XXX This really belongs in some header file... -DaveM */
2227 #define MAX_SOCK_ADDR 128 /* 108 for Unix domain -
2228 16 for IP, 16 for IPX,
2230 about 80 for AX.25 */
2232 /* XXX These as well... */
2233 extern __inline__
struct socket
*socki_lookup(struct inode
*inode
)
2235 return &inode
->u
.socket_i
;
2238 extern __inline__
struct socket
*sockfd_lookup(int fd
, int *err
)
2241 struct inode
*inode
;
2243 if (!(file
= fget(fd
)))
2249 inode
= file
->f_dentry
->d_inode
;
2250 if (!inode
|| !inode
->i_sock
|| !socki_lookup(inode
))
2257 return socki_lookup(inode
);
2260 extern __inline__
void sockfd_put(struct socket
*sock
)
2269 __kernel_size_t32 msg_iovlen
;
2271 __kernel_size_t32 msg_controllen
;
2276 __kernel_size_t32 cmsg_len
;
2282 #define __CMSG32_NXTHDR(ctl, len, cmsg, cmsglen) __cmsg32_nxthdr((ctl),(len),(cmsg),(cmsglen))
2283 #define CMSG32_NXTHDR(mhdr, cmsg, cmsglen) cmsg32_nxthdr((mhdr), (cmsg), (cmsglen))
2285 #define CMSG32_ALIGN(len) ( ((len)+sizeof(int)-1) & ~(sizeof(int)-1) )
2287 #define CMSG32_DATA(cmsg) ((void *)((char *)(cmsg) + CMSG32_ALIGN(sizeof(struct cmsghdr32))))
2288 #define CMSG32_SPACE(len) (CMSG32_ALIGN(sizeof(struct cmsghdr32)) + CMSG32_ALIGN(len))
2289 #define CMSG32_LEN(len) (CMSG32_ALIGN(sizeof(struct cmsghdr32)) + (len))
2291 #define __CMSG32_FIRSTHDR(ctl,len) ((len) >= sizeof(struct cmsghdr32) ? \
2292 (struct cmsghdr32 *)(ctl) : \
2293 (struct cmsghdr32 *)NULL)
2294 #define CMSG32_FIRSTHDR(msg) __CMSG32_FIRSTHDR((msg)->msg_control, (msg)->msg_controllen)
2296 __inline__
struct cmsghdr32
*__cmsg32_nxthdr(void *__ctl
, __kernel_size_t __size
,
2297 struct cmsghdr32
*__cmsg
, int __cmsg_len
)
2299 struct cmsghdr32
* __ptr
;
2301 __ptr
= (struct cmsghdr32
*)(((unsigned char *) __cmsg
) +
2302 CMSG32_ALIGN(__cmsg_len
));
2303 if ((unsigned long)((char*)(__ptr
+1) - (char *) __ctl
) > __size
)
2309 __inline__
struct cmsghdr32
*cmsg32_nxthdr (struct msghdr
*__msg
,
2310 struct cmsghdr32
*__cmsg
,
2313 return __cmsg32_nxthdr(__msg
->msg_control
, __msg
->msg_controllen
,
2314 __cmsg
, __cmsg_len
);
2317 static inline int iov_from_user32_to_kern(struct iovec
*kiov
,
2318 struct iovec32
*uiov32
,
2326 if(get_user(len
, &uiov32
->iov_len
) ||
2327 get_user(buf
, &uiov32
->iov_base
)) {
2332 kiov
->iov_base
= (void *)A(buf
);
2333 kiov
->iov_len
= (__kernel_size_t
) len
;
2341 static inline int msghdr_from_user32_to_kern(struct msghdr
*kmsg
,
2342 struct msghdr32
*umsg
)
2344 u32 tmp1
, tmp2
, tmp3
;
2347 err
= get_user(tmp1
, &umsg
->msg_name
);
2348 err
|= __get_user(tmp2
, &umsg
->msg_iov
);
2349 err
|= __get_user(tmp3
, &umsg
->msg_control
);
2353 kmsg
->msg_name
= (void *)A(tmp1
);
2354 kmsg
->msg_iov
= (struct iovec
*)A(tmp2
);
2355 kmsg
->msg_control
= (void *)A(tmp3
);
2357 err
= get_user(kmsg
->msg_namelen
, &umsg
->msg_namelen
);
2358 err
|= get_user(kmsg
->msg_iovlen
, &umsg
->msg_iovlen
);
2359 err
|= get_user(kmsg
->msg_controllen
, &umsg
->msg_controllen
);
2360 err
|= get_user(kmsg
->msg_flags
, &umsg
->msg_flags
);
2365 /* I've named the args so it is easy to tell whose space the pointers are in. */
2366 static int verify_iovec32(struct msghdr
*kern_msg
, struct iovec
*kern_iov
,
2367 char *kern_address
, int mode
)
2371 if(kern_msg
->msg_namelen
) {
2372 if(mode
==VERIFY_READ
) {
2373 int err
= move_addr_to_kernel(kern_msg
->msg_name
,
2374 kern_msg
->msg_namelen
,
2379 kern_msg
->msg_name
= kern_address
;
2381 kern_msg
->msg_name
= NULL
;
2383 if(kern_msg
->msg_iovlen
> UIO_FASTIOV
) {
2384 kern_iov
= kmalloc(kern_msg
->msg_iovlen
* sizeof(struct iovec
),
2390 tot_len
= iov_from_user32_to_kern(kern_iov
,
2391 (struct iovec32
*)kern_msg
->msg_iov
,
2392 kern_msg
->msg_iovlen
);
2394 kern_msg
->msg_iov
= kern_iov
;
2395 else if(kern_msg
->msg_iovlen
> UIO_FASTIOV
)
2401 /* There is a lot of hair here because the alignment rules (and
2402 * thus placement) of cmsg headers and length are different for
2403 * 32-bit apps. -DaveM
2405 static int cmsghdr_from_user32_to_kern(struct msghdr
*kmsg
,
2406 unsigned char *stackbuf
, int stackbuf_size
)
2408 struct cmsghdr32
*ucmsg
;
2409 struct cmsghdr
*kcmsg
, *kcmsg_base
;
2410 __kernel_size_t32 ucmlen
;
2411 __kernel_size_t kcmlen
, tmp
;
2414 kcmsg_base
= kcmsg
= (struct cmsghdr
*)stackbuf
;
2415 ucmsg
= CMSG32_FIRSTHDR(kmsg
);
2416 while(ucmsg
!= NULL
) {
2417 if(get_user(ucmlen
, &ucmsg
->cmsg_len
))
2421 if(CMSG32_ALIGN(ucmlen
) <
2422 CMSG32_ALIGN(sizeof(struct cmsghdr32
)))
2424 if((unsigned long)(((char *)ucmsg
- (char *)kmsg
->msg_control
)
2425 + ucmlen
) > kmsg
->msg_controllen
)
2428 tmp
= ((ucmlen
- CMSG32_ALIGN(sizeof(*ucmsg
))) +
2429 CMSG_ALIGN(sizeof(struct cmsghdr
)));
2431 ucmsg
= CMSG32_NXTHDR(kmsg
, ucmsg
, ucmlen
);
2436 /* The kcmlen holds the 64-bit version of the control length.
2437 * It may not be modified as we do not stick it into the kmsg
2438 * until we have successfully copied over all of the data
2441 if(kcmlen
> stackbuf_size
)
2442 kcmsg_base
= kcmsg
= kmalloc(kcmlen
, GFP_KERNEL
);
2446 /* Now copy them over neatly. */
2447 memset(kcmsg
, 0, kcmlen
);
2448 ucmsg
= CMSG32_FIRSTHDR(kmsg
);
2449 while(ucmsg
!= NULL
) {
2450 __get_user(ucmlen
, &ucmsg
->cmsg_len
);
2451 tmp
= ((ucmlen
- CMSG32_ALIGN(sizeof(*ucmsg
))) +
2452 CMSG_ALIGN(sizeof(struct cmsghdr
)));
2453 kcmsg
->cmsg_len
= tmp
;
2454 __get_user(kcmsg
->cmsg_level
, &ucmsg
->cmsg_level
);
2455 __get_user(kcmsg
->cmsg_type
, &ucmsg
->cmsg_type
);
2457 /* Copy over the data. */
2458 if(copy_from_user(CMSG_DATA(kcmsg
),
2460 (ucmlen
- CMSG32_ALIGN(sizeof(*ucmsg
)))))
2461 goto out_free_efault
;
2464 kcmsg
= (struct cmsghdr
*)((char *)kcmsg
+ CMSG_ALIGN(tmp
));
2465 ucmsg
= CMSG32_NXTHDR(kmsg
, ucmsg
, ucmlen
);
2468 /* Ok, looks like we made it. Hook it up and return success. */
2469 kmsg
->msg_control
= kcmsg_base
;
2470 kmsg
->msg_controllen
= kcmlen
;
2474 if(kcmsg_base
!= (struct cmsghdr
*)stackbuf
)
2479 static void put_cmsg32(struct msghdr
*kmsg
, int level
, int type
,
2480 int len
, void *data
)
2482 struct cmsghdr32
*cm
= (struct cmsghdr32
*) kmsg
->msg_control
;
2483 struct cmsghdr32 cmhdr
;
2484 int cmlen
= CMSG32_LEN(len
);
2486 if(cm
== NULL
|| kmsg
->msg_controllen
< sizeof(*cm
)) {
2487 kmsg
->msg_flags
|= MSG_CTRUNC
;
2491 if(kmsg
->msg_controllen
< cmlen
) {
2492 kmsg
->msg_flags
|= MSG_CTRUNC
;
2493 cmlen
= kmsg
->msg_controllen
;
2495 cmhdr
.cmsg_level
= level
;
2496 cmhdr
.cmsg_type
= type
;
2497 cmhdr
.cmsg_len
= cmlen
;
2499 if(copy_to_user(cm
, &cmhdr
, sizeof cmhdr
))
2501 if(copy_to_user(CMSG32_DATA(cm
), data
, cmlen
- sizeof(struct cmsghdr32
)))
2503 cmlen
= CMSG32_SPACE(len
);
2504 kmsg
->msg_control
+= cmlen
;
2505 kmsg
->msg_controllen
-= cmlen
;
2508 static void scm_detach_fds32(struct msghdr
*kmsg
, struct scm_cookie
*scm
)
2510 struct cmsghdr32
*cm
= (struct cmsghdr32
*) kmsg
->msg_control
;
2511 int fdmax
= (kmsg
->msg_controllen
- sizeof(struct cmsghdr32
)) / sizeof(int);
2512 int fdnum
= scm
->fp
->count
;
2513 struct file
**fp
= scm
->fp
->fp
;
2520 for (i
= 0, cmfptr
= (int *) CMSG32_DATA(cm
); i
< fdmax
; i
++, cmfptr
++) {
2522 err
= get_unused_fd();
2526 err
= put_user(new_fd
, cmfptr
);
2528 put_unused_fd(new_fd
);
2531 /* Bump the usage count and install the file. */
2533 fd_install(new_fd
, fp
[i
]);
2537 int cmlen
= CMSG32_LEN(i
* sizeof(int));
2539 err
= put_user(SOL_SOCKET
, &cm
->cmsg_level
);
2541 err
= put_user(SCM_RIGHTS
, &cm
->cmsg_type
);
2543 err
= put_user(cmlen
, &cm
->cmsg_len
);
2545 cmlen
= CMSG32_SPACE(i
* sizeof(int));
2546 kmsg
->msg_control
+= cmlen
;
2547 kmsg
->msg_controllen
-= cmlen
;
2551 kmsg
->msg_flags
|= MSG_CTRUNC
;
2554 * All of the files that fit in the message have had their
2555 * usage counts incremented, so we just free the list.
2560 /* In these cases we (currently) can just copy to data over verbatim
2561 * because all CMSGs created by the kernel have well defined types which
2562 * have the same layout in both the 32-bit and 64-bit API. One must add
2563 * some special cased conversions here if we start sending control messages
2564 * with incompatible types.
2566 * SCM_RIGHTS and SCM_CREDENTIALS are done by hand in recvmsg32 right after
2567 * we do our work. The remaining cases are:
2569 * SOL_IP IP_PKTINFO struct in_pktinfo 32-bit clean
2570 * IP_TTL int 32-bit clean
2571 * IP_TOS __u8 32-bit clean
2572 * IP_RECVOPTS variable length 32-bit clean
2573 * IP_RETOPTS variable length 32-bit clean
2574 * (these last two are clean because the types are defined
2575 * by the IPv4 protocol)
2576 * IP_RECVERR struct sock_extended_err +
2577 * struct sockaddr_in 32-bit clean
2578 * SOL_IPV6 IPV6_RECVERR struct sock_extended_err +
2579 * struct sockaddr_in6 32-bit clean
2580 * IPV6_PKTINFO struct in6_pktinfo 32-bit clean
2581 * IPV6_HOPLIMIT int 32-bit clean
2582 * IPV6_FLOWINFO u32 32-bit clean
2583 * IPV6_HOPOPTS ipv6 hop exthdr 32-bit clean
2584 * IPV6_DSTOPTS ipv6 dst exthdr(s) 32-bit clean
2585 * IPV6_RTHDR ipv6 routing exthdr 32-bit clean
2586 * IPV6_AUTHHDR ipv6 auth exthdr 32-bit clean
2588 static void cmsg32_recvmsg_fixup(struct msghdr
*kmsg
, unsigned long orig_cmsg_uptr
)
2590 unsigned char *workbuf
, *wp
;
2591 unsigned long bufsz
, space_avail
;
2592 struct cmsghdr
*ucmsg
;
2594 bufsz
= ((unsigned long)kmsg
->msg_control
) - orig_cmsg_uptr
;
2595 space_avail
= kmsg
->msg_controllen
+ bufsz
;
2596 wp
= workbuf
= kmalloc(bufsz
, GFP_KERNEL
);
2600 /* To make this more sane we assume the kernel sends back properly
2601 * formatted control messages. Because of how the kernel will truncate
2602 * the cmsg_len for MSG_TRUNC cases, we need not check that case either.
2604 ucmsg
= (struct cmsghdr
*) orig_cmsg_uptr
;
2605 while(((unsigned long)ucmsg
) < ((unsigned long)kmsg
->msg_control
)) {
2606 struct cmsghdr32
*kcmsg32
= (struct cmsghdr32
*) wp
;
2609 /* UCMSG is the 64-bit format CMSG entry in user-space.
2610 * KCMSG32 is within the kernel space temporary buffer
2611 * we use to convert into a 32-bit style CMSG.
2613 __get_user(kcmsg32
->cmsg_len
, &ucmsg
->cmsg_len
);
2614 __get_user(kcmsg32
->cmsg_level
, &ucmsg
->cmsg_level
);
2615 __get_user(kcmsg32
->cmsg_type
, &ucmsg
->cmsg_type
);
2617 clen64
= kcmsg32
->cmsg_len
;
2618 copy_from_user(CMSG32_DATA(kcmsg32
), CMSG_DATA(ucmsg
),
2619 clen64
- CMSG_ALIGN(sizeof(*ucmsg
)));
2620 clen32
= ((clen64
- CMSG_ALIGN(sizeof(*ucmsg
))) +
2621 CMSG32_ALIGN(sizeof(struct cmsghdr32
)));
2622 kcmsg32
->cmsg_len
= clen32
;
2624 ucmsg
= (struct cmsghdr
*) (((char *)ucmsg
) + CMSG_ALIGN(clen64
));
2625 wp
= (((char *)kcmsg32
) + CMSG32_ALIGN(clen32
));
2628 /* Copy back fixed up data, and adjust pointers. */
2629 bufsz
= (wp
- workbuf
);
2630 copy_to_user((void *)orig_cmsg_uptr
, workbuf
, bufsz
);
2632 kmsg
->msg_control
= (struct cmsghdr
*)
2633 (((char *)orig_cmsg_uptr
) + bufsz
);
2634 kmsg
->msg_controllen
= space_avail
- bufsz
;
2640 /* If we leave the 64-bit format CMSG chunks in there,
2641 * the application could get confused and crash. So to
2642 * ensure greater recovery, we report no CMSGs.
2644 kmsg
->msg_controllen
+= bufsz
;
2645 kmsg
->msg_control
= (void *) orig_cmsg_uptr
;
2648 asmlinkage
int sys32_sendmsg(int fd
, struct msghdr32
*user_msg
, unsigned user_flags
)
2650 struct socket
*sock
;
2651 char address
[MAX_SOCK_ADDR
];
2652 struct iovec iov
[UIO_FASTIOV
];
2653 unsigned char ctl
[sizeof(struct cmsghdr
) + 20];
2654 unsigned char *ctl_buf
= ctl
;
2655 struct msghdr kern_msg
;
2658 if(msghdr_from_user32_to_kern(&kern_msg
, user_msg
))
2660 if(kern_msg
.msg_iovlen
> UIO_MAXIOV
)
2662 err
= verify_iovec32(&kern_msg
, iov
, address
, VERIFY_READ
);
2667 if(kern_msg
.msg_controllen
) {
2668 err
= cmsghdr_from_user32_to_kern(&kern_msg
, ctl
, sizeof(ctl
));
2671 ctl_buf
= kern_msg
.msg_control
;
2673 kern_msg
.msg_flags
= user_flags
;
2676 sock
= sockfd_lookup(fd
, &err
);
2678 if (sock
->file
->f_flags
& O_NONBLOCK
)
2679 kern_msg
.msg_flags
|= MSG_DONTWAIT
;
2680 err
= sock_sendmsg(sock
, &kern_msg
, total_len
);
2685 /* N.B. Use kfree here, as kern_msg.msg_controllen might change? */
2689 if(kern_msg
.msg_iov
!= iov
)
2690 kfree(kern_msg
.msg_iov
);
2695 asmlinkage
int sys32_recvmsg(int fd
, struct msghdr32
*user_msg
, unsigned int user_flags
)
2697 struct iovec iovstack
[UIO_FASTIOV
];
2698 struct msghdr kern_msg
;
2699 char addr
[MAX_SOCK_ADDR
];
2700 struct socket
*sock
;
2701 struct iovec
*iov
= iovstack
;
2702 struct sockaddr
*uaddr
;
2704 unsigned long cmsg_ptr
;
2705 int err
, total_len
, len
= 0;
2707 if(msghdr_from_user32_to_kern(&kern_msg
, user_msg
))
2709 if(kern_msg
.msg_iovlen
> UIO_MAXIOV
)
2712 uaddr
= kern_msg
.msg_name
;
2713 uaddr_len
= &user_msg
->msg_namelen
;
2714 err
= verify_iovec32(&kern_msg
, iov
, addr
, VERIFY_WRITE
);
2719 cmsg_ptr
= (unsigned long) kern_msg
.msg_control
;
2720 kern_msg
.msg_flags
= 0;
2723 sock
= sockfd_lookup(fd
, &err
);
2725 struct scm_cookie scm
;
2727 if (sock
->file
->f_flags
& O_NONBLOCK
)
2728 user_flags
|= MSG_DONTWAIT
;
2729 memset(&scm
, 0, sizeof(scm
));
2730 err
= sock
->ops
->recvmsg(sock
, &kern_msg
, total_len
,
2734 if(!kern_msg
.msg_control
) {
2735 if(sock
->passcred
|| scm
.fp
)
2736 kern_msg
.msg_flags
|= MSG_CTRUNC
;
2738 __scm_destroy(&scm
);
2740 /* If recvmsg processing itself placed some
2741 * control messages into user space, it's is
2742 * using 64-bit CMSG processing, so we need
2743 * to fix it up before we tack on more stuff.
2745 if((unsigned long) kern_msg
.msg_control
!= cmsg_ptr
)
2746 cmsg32_recvmsg_fixup(&kern_msg
, cmsg_ptr
);
2750 put_cmsg32(&kern_msg
,
2751 SOL_SOCKET
, SCM_CREDENTIALS
,
2752 sizeof(scm
.creds
), &scm
.creds
);
2754 scm_detach_fds32(&kern_msg
, &scm
);
2761 if(uaddr
!= NULL
&& err
>= 0)
2762 err
= move_addr_to_user(addr
, kern_msg
.msg_namelen
, uaddr
, uaddr_len
);
2763 if(cmsg_ptr
!= 0 && err
>= 0) {
2764 unsigned long ucmsg_ptr
= ((unsigned long)kern_msg
.msg_control
);
2765 __kernel_size_t32 uclen
= (__kernel_size_t32
) (ucmsg_ptr
- cmsg_ptr
);
2766 err
|= __put_user(uclen
, &user_msg
->msg_controllen
);
2769 err
= __put_user(kern_msg
.msg_flags
, &user_msg
->msg_flags
);
2770 if(kern_msg
.msg_iov
!= iov
)
2771 kfree(kern_msg
.msg_iov
);
2778 extern asmlinkage
int sys_setsockopt(int fd
, int level
, int optname
,
2779 char *optval
, int optlen
);
2781 asmlinkage
int sys32_setsockopt(int fd
, int level
, int optname
,
2782 char *optval
, int optlen
)
2784 if (optname
== SO_ATTACH_FILTER
) {
2785 struct sock_fprog32
{
2788 } *fprog32
= (struct sock_fprog32
*)optval
;
2789 struct sock_fprog kfprog
;
2790 struct sock_filter
*kfilter
;
2792 mm_segment_t old_fs
;
2796 if (get_user(kfprog
.len
, &fprog32
->len
) ||
2797 __get_user(uptr
, &fprog32
->filter
))
2799 kfprog
.filter
= (struct sock_filter
*)A(uptr
);
2800 fsize
= kfprog
.len
* sizeof(struct sock_filter
);
2801 kfilter
= (struct sock_filter
*)kmalloc(fsize
, GFP_KERNEL
);
2802 if (kfilter
== NULL
)
2804 if (copy_from_user(kfilter
, kfprog
.filter
, fsize
)) {
2808 kfprog
.filter
= kfilter
;
2811 ret
= sys_setsockopt(fd
, level
, optname
,
2812 (char *)&kfprog
, sizeof(kfprog
));
2817 return sys_setsockopt(fd
, level
, optname
, optval
, optlen
);
2820 /* Argument list sizes for sys_socketcall */
2821 #define AL(x) ((x) * sizeof(u32))
2822 static unsigned char nargs
[18]={AL(0),AL(3),AL(3),AL(3),AL(2),AL(3),
2823 AL(3),AL(3),AL(4),AL(4),AL(4),AL(6),
2824 AL(6),AL(2),AL(5),AL(5),AL(3),AL(3)};
2827 extern asmlinkage
int sys_bind(int fd
, struct sockaddr
*umyaddr
, int addrlen
);
2828 extern asmlinkage
int sys_connect(int fd
, struct sockaddr
*uservaddr
, int addrlen
);
2829 extern asmlinkage
int sys_accept(int fd
, struct sockaddr
*upeer_sockaddr
, int *upeer_addrlen
);
2830 extern asmlinkage
int sys_getsockname(int fd
, struct sockaddr
*usockaddr
, int *usockaddr_len
);
2831 extern asmlinkage
int sys_getpeername(int fd
, struct sockaddr
*usockaddr
, int *usockaddr_len
);
2832 extern asmlinkage
int sys_send(int fd
, void *buff
, size_t len
, unsigned flags
);
2833 extern asmlinkage
int sys32_sendto(int fd
, u32 buff
, __kernel_size_t32 len
,
2834 unsigned flags
, u32 addr
, int addr_len
);
2835 extern asmlinkage
int sys_recv(int fd
, void *ubuf
, size_t size
, unsigned flags
);
2836 extern asmlinkage
int sys32_recvfrom(int fd
, u32 ubuf
, __kernel_size_t32 size
,
2837 unsigned flags
, u32 addr
, u32 addr_len
);
2838 extern asmlinkage
int sys32_getsockopt(int fd
, int level
, int optname
,
2839 u32 optval
, u32 optlen
);
2841 extern asmlinkage
int sys_socket(int family
, int type
, int protocol
);
2842 extern asmlinkage
int sys_socketpair(int family
, int type
, int protocol
,
2844 extern asmlinkage
int sys_shutdown(int fd
, int how
);
2845 extern asmlinkage
int sys_listen(int fd
, int backlog
);
2847 asmlinkage
int sys32_socketcall(int call
, u32
*args
)
2852 if (call
<SYS_SOCKET
||call
>SYS_RECVMSG
)
2854 if (copy_from_user(a
, args
, nargs
[call
]))
2862 return sys_socket(a0
, a1
, a
[2]);
2864 return sys_bind(a0
, (struct sockaddr
*)A(a1
), a
[2]);
2866 return sys_connect(a0
, (struct sockaddr
*)A(a1
), a
[2]);
2868 return sys_listen(a0
, a1
);
2870 return sys_accept(a0
, (struct sockaddr
*)A(a1
), (int *)A(a
[2]));
2871 case SYS_GETSOCKNAME
:
2872 return sys_getsockname(a0
, (struct sockaddr
*)A(a1
), (int *)A(a
[2]));
2873 case SYS_GETPEERNAME
:
2874 return sys_getpeername(a0
, (struct sockaddr
*)A(a1
), (int *)A(a
[2]));
2875 case SYS_SOCKETPAIR
:
2876 return sys_socketpair(a0
, a1
, a
[2], (int *)A(a
[3]));
2878 return sys_send(a0
, (void *)A(a1
), a
[2], a
[3]);
2880 return sys32_sendto(a0
, a1
, a
[2], a
[3], a
[4], a
[5]);
2882 return sys_recv(a0
, (void *)A(a1
), a
[2], a
[3]);
2884 return sys32_recvfrom(a0
, a1
, a
[2], a
[3], a
[4], a
[5]);
2886 return sys_shutdown(a0
,a1
);
2887 case SYS_SETSOCKOPT
:
2888 return sys32_setsockopt(a0
, a1
, a
[2], (char *)A(a
[3]), a
[4]);
2889 case SYS_GETSOCKOPT
:
2890 return sys32_getsockopt(a0
, a1
, a
[2], a
[3], a
[4]);
2892 return sys32_sendmsg(a0
, (struct msghdr32
*)A(a1
), a
[2]);
2894 return sys32_recvmsg(a0
, (struct msghdr32
*)A(a1
), a
[2]);
2899 extern void check_pending(int signum
);
2901 asmlinkage
int sys32_sigaction (int sig
, struct old_sigaction32
*act
, struct old_sigaction32
*oact
)
2903 struct k_sigaction new_ka
, old_ka
;
2907 current
->thread
.flags
|= SPARC_FLAG_NEWSIGNALS
;
2912 old_sigset_t32 mask
;
2914 ret
= get_user((long)new_ka
.sa
.sa_handler
, &act
->sa_handler
);
2915 ret
|= __get_user((long)new_ka
.sa
.sa_restorer
, &act
->sa_restorer
);
2916 ret
|= __get_user(new_ka
.sa
.sa_flags
, &act
->sa_flags
);
2917 ret
|= __get_user(mask
, &act
->sa_mask
);
2920 new_ka
.ka_restorer
= NULL
;
2921 siginitset(&new_ka
.sa
.sa_mask
, mask
);
2924 ret
= do_sigaction(sig
, act
? &new_ka
: NULL
, oact
? &old_ka
: NULL
);
2927 ret
= put_user((long)old_ka
.sa
.sa_handler
, &oact
->sa_handler
);
2928 ret
|= __put_user((long)old_ka
.sa
.sa_restorer
, &oact
->sa_restorer
);
2929 ret
|= __put_user(old_ka
.sa
.sa_flags
, &oact
->sa_flags
);
2930 ret
|= __put_user(old_ka
.sa
.sa_mask
.sig
[0], &oact
->sa_mask
);
2937 sys32_rt_sigaction(int sig
, struct sigaction32
*act
, struct sigaction32
*oact
,
2938 void *restorer
, __kernel_size_t32 sigsetsize
)
2940 struct k_sigaction new_ka
, old_ka
;
2944 /* XXX: Don't preclude handling different sized sigset_t's. */
2945 if (sigsetsize
!= sizeof(sigset_t32
))
2948 /* All tasks which use RT signals (effectively) use
2949 * new style signals.
2951 current
->thread
.flags
|= SPARC_FLAG_NEWSIGNALS
;
2954 new_ka
.ka_restorer
= restorer
;
2955 ret
= get_user((long)new_ka
.sa
.sa_handler
, &act
->sa_handler
);
2956 ret
|= __copy_from_user(&set32
, &act
->sa_mask
, sizeof(sigset_t32
));
2957 switch (_NSIG_WORDS
) {
2958 case 4: new_ka
.sa
.sa_mask
.sig
[3] = set32
.sig
[6] | (((long)set32
.sig
[7]) << 32);
2959 case 3: new_ka
.sa
.sa_mask
.sig
[2] = set32
.sig
[4] | (((long)set32
.sig
[5]) << 32);
2960 case 2: new_ka
.sa
.sa_mask
.sig
[1] = set32
.sig
[2] | (((long)set32
.sig
[3]) << 32);
2961 case 1: new_ka
.sa
.sa_mask
.sig
[0] = set32
.sig
[0] | (((long)set32
.sig
[1]) << 32);
2963 ret
|= __get_user(new_ka
.sa
.sa_flags
, &act
->sa_flags
);
2964 ret
|= __get_user((long)new_ka
.sa
.sa_restorer
, &act
->sa_restorer
);
2969 ret
= do_sigaction(sig
, act
? &new_ka
: NULL
, oact
? &old_ka
: NULL
);
2972 switch (_NSIG_WORDS
) {
2973 case 4: set32
.sig
[7] = (old_ka
.sa
.sa_mask
.sig
[3] >> 32); set32
.sig
[6] = old_ka
.sa
.sa_mask
.sig
[3];
2974 case 3: set32
.sig
[5] = (old_ka
.sa
.sa_mask
.sig
[2] >> 32); set32
.sig
[4] = old_ka
.sa
.sa_mask
.sig
[2];
2975 case 2: set32
.sig
[3] = (old_ka
.sa
.sa_mask
.sig
[1] >> 32); set32
.sig
[2] = old_ka
.sa
.sa_mask
.sig
[1];
2976 case 1: set32
.sig
[1] = (old_ka
.sa
.sa_mask
.sig
[0] >> 32); set32
.sig
[0] = old_ka
.sa
.sa_mask
.sig
[0];
2978 ret
= put_user((long)old_ka
.sa
.sa_handler
, &oact
->sa_handler
);
2979 ret
|= __copy_to_user(&oact
->sa_mask
, &set32
, sizeof(sigset_t32
));
2980 ret
|= __put_user(old_ka
.sa
.sa_flags
, &oact
->sa_flags
);
2981 ret
|= __put_user((long)old_ka
.sa
.sa_restorer
, &oact
->sa_restorer
);
2989 * count32() counts the number of arguments/envelopes
2991 static int count32(u32
* argv
)
2999 error
= get_user(p
,argv
);
3000 if (error
) return error
;
3009 * 'copy_string32()' copies argument/envelope strings from user
3010 * memory to free pages in kernel mem. These are in a format ready
3011 * to be put directly into the top of new user memory.
3013 static int copy_strings32(int argc
, u32
* argv
, struct linux_binprm
*bprm
)
3015 while (argc
-- > 0) {
3020 if (get_user(str
, argv
+ argc
) ||
3022 !(len
= strnlen_user((char *)A(str
), bprm
->p
)))
3034 int offset
, bytes_to_copy
, new, err
;
3036 offset
= pos
% PAGE_SIZE
;
3037 page
= bprm
->page
[pos
/ PAGE_SIZE
];
3040 page
= alloc_page(GFP_USER
);
3041 bprm
->page
[pos
/ PAGE_SIZE
] = page
;
3046 kaddr
= (char *)kmap(page
);
3049 memset(kaddr
, 0, offset
);
3050 bytes_to_copy
= PAGE_SIZE
- offset
;
3051 if (bytes_to_copy
> len
) {
3052 bytes_to_copy
= len
;
3054 memset(kaddr
+offset
+len
, 0,
3055 PAGE_SIZE
-offset
-len
);
3058 err
= copy_from_user(kaddr
+ offset
, (char *)A(str
),
3060 flush_page_to_ram(page
);
3061 kunmap((unsigned long)kaddr
);
3066 pos
+= bytes_to_copy
;
3067 str
+= bytes_to_copy
;
3068 len
-= bytes_to_copy
;
3075 * sys32_execve() executes a new program.
3078 do_execve32(char * filename
, u32
* argv
, u32
* envp
, struct pt_regs
* regs
)
3080 struct linux_binprm bprm
;
3081 struct dentry
* dentry
;
3085 bprm
.p
= PAGE_SIZE
*MAX_ARG_PAGES
-sizeof(void *);
3086 memset(bprm
.page
, 0, MAX_ARG_PAGES
* sizeof(bprm
.page
[0]));
3088 dentry
= open_namei(filename
, 0, 0);
3089 retval
= PTR_ERR(dentry
);
3093 bprm
.dentry
= dentry
;
3094 bprm
.filename
= filename
;
3098 if ((bprm
.argc
= count32(argv
)) < 0) {
3102 if ((bprm
.envc
= count32(envp
)) < 0) {
3107 retval
= prepare_binprm(&bprm
);
3111 retval
= copy_strings_kernel(1, &bprm
.filename
, &bprm
);
3116 retval
= copy_strings32(bprm
.envc
, envp
, &bprm
);
3120 retval
= copy_strings32(bprm
.argc
, argv
, &bprm
);
3124 retval
= search_binary_handler(&bprm
, regs
);
3126 /* execve success */
3130 /* Something went wrong, return the inode and free the argument pages*/
3134 for (i
=0 ; i
<MAX_ARG_PAGES
; i
++)
3136 __free_page(bprm
.page
[i
]);
3142 * sparc32_execve() executes a new program after the asm stub has set
3143 * things up for us. This should basically do what I want it to.
3145 asmlinkage
int sparc32_execve(struct pt_regs
*regs
)
3147 int error
, base
= 0;
3150 /* User register window flush is done by entry.S */
3152 /* Check for indirect call. */
3153 if((u32
)regs
->u_regs
[UREG_G1
] == 0)
3157 filename
= getname32((char *)AA(regs
->u_regs
[base
+ UREG_I0
]));
3158 error
= PTR_ERR(filename
);
3159 if(IS_ERR(filename
))
3161 error
= do_execve32(filename
,
3162 (u32
*)AA((u32
)regs
->u_regs
[base
+ UREG_I1
]),
3163 (u32
*)AA((u32
)regs
->u_regs
[base
+ UREG_I2
]), regs
);
3168 current
->thread
.xfsr
[0] = 0;
3169 current
->thread
.fpsaved
[0] = 0;
3170 regs
->tstate
&= ~TSTATE_PEF
;
3177 #ifdef CONFIG_MODULES
3179 extern asmlinkage
unsigned long sys_create_module(const char *name_user
, size_t size
);
3181 asmlinkage
unsigned long sys32_create_module(const char *name_user
, __kernel_size_t32 size
)
3183 return sys_create_module(name_user
, (size_t)size
);
3186 extern asmlinkage
int sys_init_module(const char *name_user
, struct module
*mod_user
);
3188 /* Hey, when you're trying to init module, take time and prepare us a nice 64bit
3189 * module structure, even if from 32bit modutils... Why to pollute kernel... :))
3191 asmlinkage
int sys32_init_module(const char *name_user
, struct module
*mod_user
)
3193 return sys_init_module(name_user
, mod_user
);
3196 extern asmlinkage
int sys_delete_module(const char *name_user
);
3198 asmlinkage
int sys32_delete_module(const char *name_user
)
3200 return sys_delete_module(name_user
);
3203 struct module_info32
{
3210 /* Query various bits about modules. */
3213 get_mod_name(const char *user_name
, char **buf
)
3218 if ((unsigned long)user_name
>= TASK_SIZE
3219 && !segment_eq(get_fs (), KERNEL_DS
))
3222 page
= __get_free_page(GFP_KERNEL
);
3226 retval
= strncpy_from_user((char *)page
, user_name
, PAGE_SIZE
);
3228 if (retval
< PAGE_SIZE
) {
3229 *buf
= (char *)page
;
3232 retval
= -ENAMETOOLONG
;
3241 put_mod_name(char *buf
)
3243 free_page((unsigned long)buf
);
3246 static __inline__
struct module
*find_module(const char *name
)
3250 for (mod
= module_list
; mod
; mod
= mod
->next
) {
3251 if (mod
->flags
& MOD_DELETED
)
3253 if (!strcmp(mod
->name
, name
))
3261 qm_modules(char *buf
, size_t bufsize
, __kernel_size_t32
*ret
)
3264 size_t nmod
, space
, len
;
3268 for (mod
= module_list
; mod
->next
!= NULL
; mod
= mod
->next
, ++nmod
) {
3269 len
= strlen(mod
->name
)+1;
3271 goto calc_space_needed
;
3272 if (copy_to_user(buf
, mod
->name
, len
))
3279 if (put_user(nmod
, ret
))
3286 while ((mod
= mod
->next
)->next
!= NULL
)
3287 space
+= strlen(mod
->name
)+1;
3289 if (put_user(space
, ret
))
3296 qm_deps(struct module
*mod
, char *buf
, size_t bufsize
, __kernel_size_t32
*ret
)
3298 size_t i
, space
, len
;
3300 if (mod
->next
== NULL
)
3302 if (!MOD_CAN_QUERY(mod
))
3303 return put_user(0, ret
);
3306 for (i
= 0; i
< mod
->ndeps
; ++i
) {
3307 const char *dep_name
= mod
->deps
[i
].dep
->name
;
3309 len
= strlen(dep_name
)+1;
3311 goto calc_space_needed
;
3312 if (copy_to_user(buf
, dep_name
, len
))
3319 return put_user(i
, ret
);
3323 while (++i
< mod
->ndeps
)
3324 space
+= strlen(mod
->deps
[i
].dep
->name
)+1;
3326 if (put_user(space
, ret
))
3333 qm_refs(struct module
*mod
, char *buf
, size_t bufsize
, __kernel_size_t32
*ret
)
3335 size_t nrefs
, space
, len
;
3336 struct module_ref
*ref
;
3338 if (mod
->next
== NULL
)
3340 if (!MOD_CAN_QUERY(mod
))
3341 if (put_user(0, ret
))
3347 for (nrefs
= 0, ref
= mod
->refs
; ref
; ++nrefs
, ref
= ref
->next_ref
) {
3348 const char *ref_name
= ref
->ref
->name
;
3350 len
= strlen(ref_name
)+1;
3352 goto calc_space_needed
;
3353 if (copy_to_user(buf
, ref_name
, len
))
3360 if (put_user(nrefs
, ret
))
3367 while ((ref
= ref
->next_ref
) != NULL
)
3368 space
+= strlen(ref
->ref
->name
)+1;
3370 if (put_user(space
, ret
))
3377 qm_symbols(struct module
*mod
, char *buf
, size_t bufsize
, __kernel_size_t32
*ret
)
3379 size_t i
, space
, len
;
3380 struct module_symbol
*s
;
3384 if (!MOD_CAN_QUERY(mod
))
3385 if (put_user(0, ret
))
3390 space
= mod
->nsyms
* 2*sizeof(u32
);
3395 if (space
> bufsize
)
3396 goto calc_space_needed
;
3398 if (!access_ok(VERIFY_WRITE
, buf
, space
))
3402 vals
= (unsigned *)buf
;
3403 strings
= buf
+space
;
3405 for (; i
< mod
->nsyms
; ++i
, ++s
, vals
+= 2) {
3406 len
= strlen(s
->name
)+1;
3408 goto calc_space_needed
;
3410 if (copy_to_user(strings
, s
->name
, len
)
3411 || __put_user(s
->value
, vals
+0)
3412 || __put_user(space
, vals
+1))
3420 if (put_user(i
, ret
))
3426 for (; i
< mod
->nsyms
; ++i
, ++s
)
3427 space
+= strlen(s
->name
)+1;
3429 if (put_user(space
, ret
))
3436 qm_info(struct module
*mod
, char *buf
, size_t bufsize
, __kernel_size_t32
*ret
)
3440 if (mod
->next
== NULL
)
3443 if (sizeof(struct module_info32
) <= bufsize
) {
3444 struct module_info32 info
;
3445 info
.addr
= (unsigned long)mod
;
3446 info
.size
= mod
->size
;
3447 info
.flags
= mod
->flags
;
3449 ((mod_member_present(mod
, can_unload
)
3451 ? -1 : atomic_read(&mod
->uc
.usecount
));
3453 if (copy_to_user(buf
, &info
, sizeof(struct module_info32
)))
3458 if (put_user(sizeof(struct module_info32
), ret
))
3464 asmlinkage
int sys32_query_module(char *name_user
, int which
, char *buf
, __kernel_size_t32 bufsize
, u32 ret
)
3470 if (name_user
== 0) {
3471 /* This finds "kernel_module" which is not exported. */
3472 for(mod
= module_list
; mod
->next
!= NULL
; mod
= mod
->next
)
3478 if ((namelen
= get_mod_name(name_user
, &name
)) < 0) {
3484 /* This finds "kernel_module" which is not exported. */
3485 for(mod
= module_list
; mod
->next
!= NULL
; mod
= mod
->next
)
3487 } else if ((mod
= find_module(name
)) == NULL
) {
3500 err
= qm_modules(buf
, bufsize
, (__kernel_size_t32
*)AA(ret
));
3503 err
= qm_deps(mod
, buf
, bufsize
, (__kernel_size_t32
*)AA(ret
));
3506 err
= qm_refs(mod
, buf
, bufsize
, (__kernel_size_t32
*)AA(ret
));
3509 err
= qm_symbols(mod
, buf
, bufsize
, (__kernel_size_t32
*)AA(ret
));
3512 err
= qm_info(mod
, buf
, bufsize
, (__kernel_size_t32
*)AA(ret
));
3523 struct kernel_sym32
{
3528 extern asmlinkage
int sys_get_kernel_syms(struct kernel_sym
*table
);
3530 asmlinkage
int sys32_get_kernel_syms(struct kernel_sym32
*table
)
3533 struct kernel_sym
*tbl
;
3534 mm_segment_t old_fs
;
3536 len
= sys_get_kernel_syms(NULL
);
3537 if (!table
) return len
;
3538 tbl
= kmalloc (len
* sizeof (struct kernel_sym
), GFP_KERNEL
);
3539 if (!tbl
) return -ENOMEM
;
3542 sys_get_kernel_syms(tbl
);
3544 for (i
= 0; i
< len
; i
++, table
+= sizeof (struct kernel_sym32
)) {
3545 if (put_user (tbl
[i
].value
, &table
->value
) ||
3546 copy_to_user (table
->name
, tbl
[i
].name
, 60))
3553 #else /* CONFIG_MODULES */
3555 asmlinkage
unsigned long
3556 sys32_create_module(const char *name_user
, size_t size
)
3562 sys32_init_module(const char *name_user
, struct module
*mod_user
)
3568 sys32_delete_module(const char *name_user
)
3574 sys32_query_module(const char *name_user
, int which
, char *buf
, size_t bufsize
,
3577 /* Let the program know about the new interface. Not that
3578 it'll do them much good. */
3586 sys32_get_kernel_syms(struct kernel_sym
*table
)
3591 #endif /* CONFIG_MODULES */
3593 /* Stuff for NFS server syscalls... */
3594 struct nfsctl_svc32
{
3599 struct nfsctl_client32
{
3600 s8 cl32_ident
[NFSCLNT_IDMAX
+1];
3602 struct in_addr cl32_addrlist
[NFSCLNT_ADDRMAX
];
3605 u8 cl32_fhkey
[NFSCLNT_KEYMAX
];
3608 struct nfsctl_export32
{
3609 s8 ex32_client
[NFSCLNT_IDMAX
+1];
3610 s8 ex32_path
[NFS_MAXPATHLEN
+1];
3611 __kernel_dev_t32 ex32_dev
;
3612 __kernel_ino_t32 ex32_ino
;
3614 __kernel_uid_t32 ex32_anon_uid
;
3615 __kernel_gid_t32 ex32_anon_gid
;
3618 struct nfsctl_uidmap32
{
3619 u32 ug32_ident
; /* char * */
3620 __kernel_uid_t32 ug32_uidbase
;
3622 u32 ug32_udimap
; /* uid_t * */
3623 __kernel_uid_t32 ug32_gidbase
;
3625 u32 ug32_gdimap
; /* gid_t * */
3628 struct nfsctl_fhparm32
{
3629 struct sockaddr gf32_addr
;
3630 __kernel_dev_t32 gf32_dev
;
3631 __kernel_ino_t32 gf32_ino
;
3635 struct nfsctl_arg32
{
3636 s32 ca32_version
; /* safeguard */
3638 struct nfsctl_svc32 u32_svc
;
3639 struct nfsctl_client32 u32_client
;
3640 struct nfsctl_export32 u32_export
;
3641 struct nfsctl_uidmap32 u32_umap
;
3642 struct nfsctl_fhparm32 u32_getfh
;
3645 #define ca32_svc u.u32_svc
3646 #define ca32_client u.u32_client
3647 #define ca32_export u.u32_export
3648 #define ca32_umap u.u32_umap
3649 #define ca32_getfh u.u32_getfh
3650 #define ca32_authd u.u32_authd
3651 #define ca32_debug u.u32_debug
3654 union nfsctl_res32
{
3655 struct knfs_fh cr32_getfh
;
3659 static int nfs_svc32_trans(struct nfsctl_arg
*karg
, struct nfsctl_arg32
*arg32
)
3663 err
= __get_user(karg
->ca_version
, &arg32
->ca32_version
);
3664 err
|= __get_user(karg
->ca_svc
.svc_port
, &arg32
->ca32_svc
.svc32_port
);
3665 err
|= __get_user(karg
->ca_svc
.svc_nthreads
, &arg32
->ca32_svc
.svc32_nthreads
);
3669 static int nfs_clnt32_trans(struct nfsctl_arg
*karg
, struct nfsctl_arg32
*arg32
)
3673 err
= __get_user(karg
->ca_version
, &arg32
->ca32_version
);
3674 err
|= copy_from_user(&karg
->ca_client
.cl_ident
[0],
3675 &arg32
->ca32_client
.cl32_ident
[0],
3677 err
|= __get_user(karg
->ca_client
.cl_naddr
, &arg32
->ca32_client
.cl32_naddr
);
3678 err
|= copy_from_user(&karg
->ca_client
.cl_addrlist
[0],
3679 &arg32
->ca32_client
.cl32_addrlist
[0],
3680 (sizeof(struct in_addr
) * NFSCLNT_ADDRMAX
));
3681 err
|= __get_user(karg
->ca_client
.cl_fhkeytype
,
3682 &arg32
->ca32_client
.cl32_fhkeytype
);
3683 err
|= __get_user(karg
->ca_client
.cl_fhkeylen
,
3684 &arg32
->ca32_client
.cl32_fhkeylen
);
3685 err
|= copy_from_user(&karg
->ca_client
.cl_fhkey
[0],
3686 &arg32
->ca32_client
.cl32_fhkey
[0],
3691 static int nfs_exp32_trans(struct nfsctl_arg
*karg
, struct nfsctl_arg32
*arg32
)
3695 err
= __get_user(karg
->ca_version
, &arg32
->ca32_version
);
3696 err
|= copy_from_user(&karg
->ca_export
.ex_client
[0],
3697 &arg32
->ca32_export
.ex32_client
[0],
3699 err
|= copy_from_user(&karg
->ca_export
.ex_path
[0],
3700 &arg32
->ca32_export
.ex32_path
[0],
3702 err
|= __get_user(karg
->ca_export
.ex_dev
,
3703 &arg32
->ca32_export
.ex32_dev
);
3704 err
|= __get_user(karg
->ca_export
.ex_ino
,
3705 &arg32
->ca32_export
.ex32_ino
);
3706 err
|= __get_user(karg
->ca_export
.ex_flags
,
3707 &arg32
->ca32_export
.ex32_flags
);
3708 err
|= __get_user(karg
->ca_export
.ex_anon_uid
,
3709 &arg32
->ca32_export
.ex32_anon_uid
);
3710 err
|= __get_user(karg
->ca_export
.ex_anon_gid
,
3711 &arg32
->ca32_export
.ex32_anon_gid
);
3712 karg
->ca_export
.ex_anon_uid
= high2lowuid(karg
->ca_export
.ex_anon_uid
);
3713 karg
->ca_export
.ex_anon_gid
= high2lowgid(karg
->ca_export
.ex_anon_gid
);
3717 static int nfs_uud32_trans(struct nfsctl_arg
*karg
, struct nfsctl_arg32
*arg32
)
3723 memset(karg
, 0, sizeof(*karg
));
3724 if(__get_user(karg
->ca_version
, &arg32
->ca32_version
))
3726 karg
->ca_umap
.ug_ident
= (char *)get_free_page(GFP_USER
);
3727 if(!karg
->ca_umap
.ug_ident
)
3729 err
= __get_user(uaddr
, &arg32
->ca32_umap
.ug32_ident
);
3730 if(strncpy_from_user(karg
->ca_umap
.ug_ident
,
3731 (char *)A(uaddr
), PAGE_SIZE
) <= 0)
3733 err
|= __get_user(karg
->ca_umap
.ug_uidbase
,
3734 &arg32
->ca32_umap
.ug32_uidbase
);
3735 err
|= __get_user(karg
->ca_umap
.ug_uidlen
,
3736 &arg32
->ca32_umap
.ug32_uidlen
);
3737 err
|= __get_user(uaddr
, &arg32
->ca32_umap
.ug32_udimap
);
3740 karg
->ca_umap
.ug_udimap
= kmalloc((sizeof(uid_t
) * karg
->ca_umap
.ug_uidlen
),
3742 if(!karg
->ca_umap
.ug_udimap
)
3744 for(i
= 0; i
< karg
->ca_umap
.ug_uidlen
; i
++)
3745 err
|= __get_user(karg
->ca_umap
.ug_udimap
[i
],
3746 &(((__kernel_uid_t32
*)A(uaddr
))[i
]));
3747 err
|= __get_user(karg
->ca_umap
.ug_gidbase
,
3748 &arg32
->ca32_umap
.ug32_gidbase
);
3749 err
|= __get_user(karg
->ca_umap
.ug_uidlen
,
3750 &arg32
->ca32_umap
.ug32_gidlen
);
3751 err
|= __get_user(uaddr
, &arg32
->ca32_umap
.ug32_gdimap
);
3754 karg
->ca_umap
.ug_gdimap
= kmalloc((sizeof(gid_t
) * karg
->ca_umap
.ug_uidlen
),
3756 if(!karg
->ca_umap
.ug_gdimap
)
3758 for(i
= 0; i
< karg
->ca_umap
.ug_gidlen
; i
++)
3759 err
|= __get_user(karg
->ca_umap
.ug_gdimap
[i
],
3760 &(((__kernel_gid_t32
*)A(uaddr
))[i
]));
3765 static int nfs_getfh32_trans(struct nfsctl_arg
*karg
, struct nfsctl_arg32
*arg32
)
3769 err
= __get_user(karg
->ca_version
, &arg32
->ca32_version
);
3770 err
|= copy_from_user(&karg
->ca_getfh
.gf_addr
,
3771 &arg32
->ca32_getfh
.gf32_addr
,
3772 (sizeof(struct sockaddr
)));
3773 err
|= __get_user(karg
->ca_getfh
.gf_dev
,
3774 &arg32
->ca32_getfh
.gf32_dev
);
3775 err
|= __get_user(karg
->ca_getfh
.gf_ino
,
3776 &arg32
->ca32_getfh
.gf32_ino
);
3777 err
|= __get_user(karg
->ca_getfh
.gf_version
,
3778 &arg32
->ca32_getfh
.gf32_version
);
3782 static int nfs_getfh32_res_trans(union nfsctl_res
*kres
, union nfsctl_res32
*res32
)
3786 err
= copy_to_user(&res32
->cr32_getfh
,
3788 sizeof(res32
->cr32_getfh
));
3789 err
|= __put_user(kres
->cr_debug
, &res32
->cr32_debug
);
3793 extern asmlinkage
int sys_nfsservctl(int cmd
, void *arg
, void *resp
);
3795 int asmlinkage
sys32_nfsservctl(int cmd
, struct nfsctl_arg32
*arg32
, union nfsctl_res32
*res32
)
3797 struct nfsctl_arg
*karg
= NULL
;
3798 union nfsctl_res
*kres
= NULL
;
3802 karg
= kmalloc(sizeof(*karg
), GFP_USER
);
3806 kres
= kmalloc(sizeof(*kres
), GFP_USER
);
3814 err
= nfs_svc32_trans(karg
, arg32
);
3816 case NFSCTL_ADDCLIENT
:
3817 err
= nfs_clnt32_trans(karg
, arg32
);
3819 case NFSCTL_DELCLIENT
:
3820 err
= nfs_clnt32_trans(karg
, arg32
);
3823 err
= nfs_exp32_trans(karg
, arg32
);
3825 /* This one is unimplemented, be we're ready for it. */
3826 case NFSCTL_UGIDUPDATE
:
3827 err
= nfs_uud32_trans(karg
, arg32
);
3830 err
= nfs_getfh32_trans(karg
, arg32
);
3840 err
= sys_nfsservctl(cmd
, karg
, kres
);
3843 if(!err
&& cmd
== NFSCTL_GETFH
)
3844 err
= nfs_getfh32_res_trans(kres
, res32
);
3848 if(cmd
== NFSCTL_UGIDUPDATE
) {
3849 if(karg
->ca_umap
.ug_ident
)
3850 kfree(karg
->ca_umap
.ug_ident
);
3851 if(karg
->ca_umap
.ug_udimap
)
3852 kfree(karg
->ca_umap
.ug_udimap
);
3853 if(karg
->ca_umap
.ug_gdimap
)
3854 kfree(karg
->ca_umap
.ug_gdimap
);
3863 /* Translations due to time_t size differences. Which affects all
3864 sorts of things, like timeval and itimerval. */
3866 extern struct timezone sys_tz
;
3867 extern int do_sys_settimeofday(struct timeval
*tv
, struct timezone
*tz
);
3869 asmlinkage
int sys32_gettimeofday(struct timeval32
*tv
, struct timezone
*tz
)
3873 do_gettimeofday(&ktv
);
3874 if (put_tv32(tv
, &ktv
))
3878 if (copy_to_user(tz
, &sys_tz
, sizeof(sys_tz
)))
3884 asmlinkage
int sys32_settimeofday(struct timeval32
*tv
, struct timezone
*tz
)
3887 struct timezone ktz
;
3890 if (get_tv32(&ktv
, tv
))
3894 if (copy_from_user(&ktz
, tz
, sizeof(ktz
)))
3898 return do_sys_settimeofday(tv
? &ktv
: NULL
, tz
? &ktz
: NULL
);
3901 extern int do_getitimer(int which
, struct itimerval
*value
);
3903 asmlinkage
int sys32_getitimer(int which
, struct itimerval32
*it
)
3905 struct itimerval kit
;
3908 error
= do_getitimer(which
, &kit
);
3909 if (!error
&& put_it32(it
, &kit
))
3915 extern int do_setitimer(int which
, struct itimerval
*, struct itimerval
*);
3917 asmlinkage
int sys32_setitimer(int which
, struct itimerval32
*in
, struct itimerval32
*out
)
3919 struct itimerval kin
, kout
;
3923 if (get_it32(&kin
, in
))
3926 memset(&kin
, 0, sizeof(kin
));
3928 error
= do_setitimer(which
, &kin
, out
? &kout
: NULL
);
3931 if (put_it32(out
, &kout
))
3938 asmlinkage
int sys_utimes(char *, struct timeval
*);
3940 asmlinkage
int sys32_utimes(char *filename
, struct timeval32
*tvs
)
3943 struct timeval ktvs
[2];
3944 mm_segment_t old_fs
;
3947 kfilename
= getname32(filename
);
3948 ret
= PTR_ERR(kfilename
);
3949 if (!IS_ERR(kfilename
)) {
3951 if (get_tv32(&ktvs
[0], tvs
) ||
3952 get_tv32(&ktvs
[1], 1+tvs
))
3958 ret
= sys_utimes(kfilename
, &ktvs
[0]);
3966 /* These are here just in case some old sparc32 binary calls it. */
3967 asmlinkage
int sys32_pause(void)
3969 current
->state
= TASK_INTERRUPTIBLE
;
3971 return -ERESTARTNOHAND
;
3974 /* PCI config space poking. */
3975 extern asmlinkage
int sys_pciconfig_read(unsigned long bus
,
3979 unsigned char *buf
);
3981 extern asmlinkage
int sys_pciconfig_write(unsigned long bus
,
3985 unsigned char *buf
);
3987 asmlinkage
int sys32_pciconfig_read(u32 bus
, u32 dfn
, u32 off
, u32 len
, u32 ubuf
)
3989 return sys_pciconfig_read((unsigned long) bus
,
3990 (unsigned long) dfn
,
3991 (unsigned long) off
,
3992 (unsigned long) len
,
3993 (unsigned char *)AA(ubuf
));
3996 asmlinkage
int sys32_pciconfig_write(u32 bus
, u32 dfn
, u32 off
, u32 len
, u32 ubuf
)
3998 return sys_pciconfig_write((unsigned long) bus
,
3999 (unsigned long) dfn
,
4000 (unsigned long) off
,
4001 (unsigned long) len
,
4002 (unsigned char *)AA(ubuf
));
4005 extern asmlinkage
int sys_prctl(int option
, unsigned long arg2
, unsigned long arg3
,
4006 unsigned long arg4
, unsigned long arg5
);
4008 asmlinkage
int sys32_prctl(int option
, u32 arg2
, u32 arg3
, u32 arg4
, u32 arg5
)
4010 return sys_prctl(option
,
4011 (unsigned long) arg2
,
4012 (unsigned long) arg3
,
4013 (unsigned long) arg4
,
4014 (unsigned long) arg5
);
4018 extern asmlinkage
int sys_newuname(struct new_utsname
* name
);
4020 asmlinkage
int sys32_newuname(struct new_utsname
* name
)
4022 int ret
= sys_newuname(name
);
4024 if (current
->personality
== PER_LINUX32
&& !ret
) {
4025 ret
= copy_to_user(name
->machine
, "sparc\0\0", 8);
4030 extern asmlinkage ssize_t
sys_pread(unsigned int fd
, char * buf
,
4031 size_t count
, loff_t pos
);
4033 extern asmlinkage ssize_t
sys_pwrite(unsigned int fd
, const char * buf
,
4034 size_t count
, loff_t pos
);
4036 typedef __kernel_ssize_t32 ssize_t32
;
4038 asmlinkage ssize_t32
sys32_pread(unsigned int fd
, char *ubuf
,
4039 __kernel_size_t32 count
, u32 poshi
, u32 poslo
)
4041 return sys_pread(fd
, ubuf
, count
, ((loff_t
)AA(poshi
) << 32) | AA(poslo
));
4044 asmlinkage ssize_t32
sys32_pwrite(unsigned int fd
, char *ubuf
,
4045 __kernel_size_t32 count
, u32 poshi
, u32 poslo
)
4047 return sys_pwrite(fd
, ubuf
, count
, ((loff_t
)AA(poshi
) << 32) | AA(poslo
));
4051 extern asmlinkage
long sys_personality(unsigned long);
4053 asmlinkage
int sys32_personality(unsigned long personality
)
4057 if (current
->personality
== PER_LINUX32
&& personality
== PER_LINUX
)
4058 personality
= PER_LINUX32
;
4059 ret
= sys_personality(personality
);
4061 if (ret
== PER_LINUX32
)
4066 extern asmlinkage ssize_t
sys_sendfile(int out_fd
, int in_fd
, off_t
*offset
, size_t count
);
4068 asmlinkage
int sys32_sendfile(int out_fd
, int in_fd
, __kernel_off_t32
*offset
, s32 count
)
4070 mm_segment_t old_fs
= get_fs();
4074 if (offset
&& get_user(of
, offset
))
4078 ret
= sys_sendfile(out_fd
, in_fd
, offset
? &of
: NULL
, count
);
4081 if (!ret
&& offset
&& put_user(of
, offset
))
4087 /* Handle adjtimex compatability. */
4091 s32 offset
, freq
, maxerror
, esterror
;
4092 s32 status
, constant
, precision
, tolerance
;
4093 struct timeval32 time
;
4095 s32 ppsfreq
, jitter
, shift
, stabil
;
4096 s32 jitcnt
, calcnt
, errcnt
, stbcnt
;
4097 s32
:32; s32
:32; s32
:32; s32
:32;
4098 s32
:32; s32
:32; s32
:32; s32
:32;
4099 s32
:32; s32
:32; s32
:32; s32
:32;
4102 extern int do_adjtimex(struct timex
*);
4104 asmlinkage
int sys32_adjtimex(struct timex32
*utp
)
4109 memset(&txc
, 0, sizeof(struct timex
));
4111 if(get_user(txc
.modes
, &utp
->modes
) ||
4112 __get_user(txc
.offset
, &utp
->offset
) ||
4113 __get_user(txc
.freq
, &utp
->freq
) ||
4114 __get_user(txc
.maxerror
, &utp
->maxerror
) ||
4115 __get_user(txc
.esterror
, &utp
->esterror
) ||
4116 __get_user(txc
.status
, &utp
->status
) ||
4117 __get_user(txc
.constant
, &utp
->constant
) ||
4118 __get_user(txc
.precision
, &utp
->precision
) ||
4119 __get_user(txc
.tolerance
, &utp
->tolerance
) ||
4120 __get_user(txc
.time
.tv_sec
, &utp
->time
.tv_sec
) ||
4121 __get_user(txc
.time
.tv_usec
, &utp
->time
.tv_usec
) ||
4122 __get_user(txc
.tick
, &utp
->tick
) ||
4123 __get_user(txc
.ppsfreq
, &utp
->ppsfreq
) ||
4124 __get_user(txc
.jitter
, &utp
->jitter
) ||
4125 __get_user(txc
.shift
, &utp
->shift
) ||
4126 __get_user(txc
.stabil
, &utp
->stabil
) ||
4127 __get_user(txc
.jitcnt
, &utp
->jitcnt
) ||
4128 __get_user(txc
.calcnt
, &utp
->calcnt
) ||
4129 __get_user(txc
.errcnt
, &utp
->errcnt
) ||
4130 __get_user(txc
.stbcnt
, &utp
->stbcnt
))
4133 ret
= do_adjtimex(&txc
);
4135 if(put_user(txc
.modes
, &utp
->modes
) ||
4136 __put_user(txc
.offset
, &utp
->offset
) ||
4137 __put_user(txc
.freq
, &utp
->freq
) ||
4138 __put_user(txc
.maxerror
, &utp
->maxerror
) ||
4139 __put_user(txc
.esterror
, &utp
->esterror
) ||
4140 __put_user(txc
.status
, &utp
->status
) ||
4141 __put_user(txc
.constant
, &utp
->constant
) ||
4142 __put_user(txc
.precision
, &utp
->precision
) ||
4143 __put_user(txc
.tolerance
, &utp
->tolerance
) ||
4144 __put_user(txc
.time
.tv_sec
, &utp
->time
.tv_sec
) ||
4145 __put_user(txc
.time
.tv_usec
, &utp
->time
.tv_usec
) ||
4146 __put_user(txc
.tick
, &utp
->tick
) ||
4147 __put_user(txc
.ppsfreq
, &utp
->ppsfreq
) ||
4148 __put_user(txc
.jitter
, &utp
->jitter
) ||
4149 __put_user(txc
.shift
, &utp
->shift
) ||
4150 __put_user(txc
.stabil
, &utp
->stabil
) ||
4151 __put_user(txc
.jitcnt
, &utp
->jitcnt
) ||
4152 __put_user(txc
.calcnt
, &utp
->calcnt
) ||
4153 __put_user(txc
.errcnt
, &utp
->errcnt
) ||
4154 __put_user(txc
.stbcnt
, &utp
->stbcnt
))
4160 /* This is just a version for 32-bit applications which does
4161 * not force O_LARGEFILE on.
4164 asmlinkage
long sparc32_open(const char * filename
, int flags
, int mode
)
4169 tmp
= getname(filename
);
4172 fd
= get_unused_fd();
4176 f
= filp_open(tmp
, flags
, mode
);