diff options
author | marcel <marcel@FreeBSD.org> | 2001-09-26 05:39:59 +0000 |
---|---|---|
committer | marcel <marcel@FreeBSD.org> | 2001-09-26 05:39:59 +0000 |
commit | 5d88a24f8b514d22f631be64b067e9e1f33cd8fb (patch) | |
tree | 049c3f612250d4e89d104fee3925a1878a2e7262 | |
parent | 6dd5e71c087c216fc2c384ce29c0501899cbaf05 (diff) | |
download | FreeBSD-src-5d88a24f8b514d22f631be64b067e9e1f33cd8fb.zip FreeBSD-src-5d88a24f8b514d22f631be64b067e9e1f33cd8fb.tar.gz |
The arg parameter is passed by value in Linux, but not in FreeBSD.
We still have to account for a copyin. Make sure the copyin will
succeed by passing the FreeBSD syscall a pointer to userspace,
albeit one that's automagically mapped into kernel space.
Reported by: mr, Mitsuru IWASAKI <iwasaki@jp.FreeBSD.org>
Tested by: Mitsuru IWASAKI <iwasaki@jp.FreeBSD.org>
-rw-r--r-- | sys/compat/linux/linux_ipc.c | 11 |
1 files changed, 6 insertions, 5 deletions
diff --git a/sys/compat/linux/linux_ipc.c b/sys/compat/linux/linux_ipc.c index 300c67a..a26871b 100644 --- a/sys/compat/linux/linux_ipc.c +++ b/sys/compat/linux/linux_ipc.c @@ -224,9 +224,14 @@ linux_semctl(struct thread *td, struct linux_semctl_args *args) caddr_t sg; sg = stackgap_init(); + + /* Make sure the arg parameter can be copied in. */ + unptr = stackgap_alloc(&sg, sizeof(union semun)); + bcopy(unptr, &args->arg, sizeof(union semun)); + bsd_args.semid = args->semid; bsd_args.semnum = args->semnum; - bsd_args.arg = (union semun *)&args->arg; + bsd_args.arg = unptr; switch (args->cmd) { case LINUX_IPC_RMID: @@ -253,10 +258,8 @@ linux_semctl(struct thread *td, struct linux_semctl_args *args) sizeof(linux_semid)); if (error) return (error); - unptr = stackgap_alloc(&sg, sizeof(union semun)); unptr->buf = stackgap_alloc(&sg, sizeof(struct semid_ds)); linux_to_bsd_semid_ds(&linux_semid, unptr->buf); - bsd_args.arg = unptr; return __semctl(td, &bsd_args); case LINUX_IPC_STAT: case LINUX_SEM_STAT: @@ -264,9 +267,7 @@ linux_semctl(struct thread *td, struct linux_semctl_args *args) bsd_args.cmd = IPC_STAT; else bsd_args.cmd = SEM_STAT; - unptr = stackgap_alloc(&sg, sizeof(union semun)); unptr->buf = stackgap_alloc(&sg, sizeof(struct semid_ds)); - bsd_args.arg = unptr; error = __semctl(td, &bsd_args); if (error) return error; |