diff options
Diffstat (limited to 'ipc/compat.c')
-rw-r--r-- | ipc/compat.c | 46 |
1 files changed, 20 insertions, 26 deletions
diff --git a/ipc/compat.c b/ipc/compat.c index ad9518eb26e0..2547f29dcd1b 100644 --- a/ipc/compat.c +++ b/ipc/compat.c | |||
@@ -306,6 +306,20 @@ static long do_compat_semctl(int first, int second, int third, u32 pad) | |||
306 | return err; | 306 | return err; |
307 | } | 307 | } |
308 | 308 | ||
309 | long compat_do_msg_fill(void __user *dest, struct msg_msg *msg, size_t bufsz) | ||
310 | { | ||
311 | struct compat_msgbuf __user *msgp = dest; | ||
312 | size_t msgsz; | ||
313 | |||
314 | if (put_user(msg->m_type, &msgp->mtype)) | ||
315 | return -EFAULT; | ||
316 | |||
317 | msgsz = (bufsz > msg->m_ts) ? msg->m_ts : bufsz; | ||
318 | if (store_msg(msgp->mtext, msg, msgsz)) | ||
319 | return -EFAULT; | ||
320 | return msgsz; | ||
321 | } | ||
322 | |||
309 | #ifdef CONFIG_ARCH_WANT_OLD_COMPAT_IPC | 323 | #ifdef CONFIG_ARCH_WANT_OLD_COMPAT_IPC |
310 | long compat_sys_semctl(int first, int second, int third, void __user *uptr) | 324 | long compat_sys_semctl(int first, int second, int third, void __user *uptr) |
311 | { | 325 | { |
@@ -337,10 +351,6 @@ long compat_sys_msgsnd(int first, int second, int third, void __user *uptr) | |||
337 | long compat_sys_msgrcv(int first, int second, int msgtyp, int third, | 351 | long compat_sys_msgrcv(int first, int second, int msgtyp, int third, |
338 | int version, void __user *uptr) | 352 | int version, void __user *uptr) |
339 | { | 353 | { |
340 | struct compat_msgbuf __user *up; | ||
341 | long type; | ||
342 | int err; | ||
343 | |||
344 | if (first < 0) | 354 | if (first < 0) |
345 | return -EINVAL; | 355 | return -EINVAL; |
346 | if (second < 0) | 356 | if (second < 0) |
@@ -348,23 +358,15 @@ long compat_sys_msgrcv(int first, int second, int msgtyp, int third, | |||
348 | 358 | ||
349 | if (!version) { | 359 | if (!version) { |
350 | struct compat_ipc_kludge ipck; | 360 | struct compat_ipc_kludge ipck; |
351 | err = -EINVAL; | ||
352 | if (!uptr) | 361 | if (!uptr) |
353 | goto out; | 362 | return -EINVAL; |
354 | err = -EFAULT; | ||
355 | if (copy_from_user (&ipck, uptr, sizeof(ipck))) | 363 | if (copy_from_user (&ipck, uptr, sizeof(ipck))) |
356 | goto out; | 364 | return -EFAULT; |
357 | uptr = compat_ptr(ipck.msgp); | 365 | uptr = compat_ptr(ipck.msgp); |
358 | msgtyp = ipck.msgtyp; | 366 | msgtyp = ipck.msgtyp; |
359 | } | 367 | } |
360 | up = uptr; | 368 | return do_msgrcv(first, uptr, second, msgtyp, third, |
361 | err = do_msgrcv(first, &type, up->mtext, second, msgtyp, third); | 369 | compat_do_msg_fill); |
362 | if (err < 0) | ||
363 | goto out; | ||
364 | if (put_user(type, &up->mtype)) | ||
365 | err = -EFAULT; | ||
366 | out: | ||
367 | return err; | ||
368 | } | 370 | } |
369 | #else | 371 | #else |
370 | long compat_sys_semctl(int semid, int semnum, int cmd, int arg) | 372 | long compat_sys_semctl(int semid, int semnum, int cmd, int arg) |
@@ -385,16 +387,8 @@ long compat_sys_msgsnd(int msqid, struct compat_msgbuf __user *msgp, | |||
385 | long compat_sys_msgrcv(int msqid, struct compat_msgbuf __user *msgp, | 387 | long compat_sys_msgrcv(int msqid, struct compat_msgbuf __user *msgp, |
386 | compat_ssize_t msgsz, long msgtyp, int msgflg) | 388 | compat_ssize_t msgsz, long msgtyp, int msgflg) |
387 | { | 389 | { |
388 | long err, mtype; | 390 | return do_msgrcv(msqid, msgp, (ssize_t)msgsz, msgtyp, msgflg, |
389 | 391 | compat_do_msg_fill); | |
390 | err = do_msgrcv(msqid, &mtype, msgp->mtext, (ssize_t)msgsz, msgtyp, msgflg); | ||
391 | if (err < 0) | ||
392 | goto out; | ||
393 | |||
394 | if (put_user(mtype, &msgp->mtype)) | ||
395 | err = -EFAULT; | ||
396 | out: | ||
397 | return err; | ||
398 | } | 392 | } |
399 | #endif | 393 | #endif |
400 | 394 | ||