diff options
author | Dominik Brodowski <linux@dominikbrodowski.net> | 2018-03-20 15:00:39 -0400 |
---|---|---|
committer | Dominik Brodowski <linux@dominikbrodowski.net> | 2018-04-02 14:15:22 -0400 |
commit | d969c6fa7263c8fc1928f528bb68587872350b6c (patch) | |
tree | ea96ad301cb9b73b87838e925411bb7e4d111ce4 | |
parent | 69894718a515fef7ff633cf354fcd7ed73a88891 (diff) |
ipc: add semctl syscall/compat_syscall wrappers
Provide ksys_semctl() and compat_ksys_semctl() wrappers to avoid in-kernel
calls to these syscalls. The ksys_ prefix denotes that these functions are
meant as a drop-in replacement for the syscalls. In particular, they use
the same calling convention as sys_semctl() and compat_sys_semctl().
This patch is part of a series which removes in-kernel calls to syscalls.
On this basis, the syscall entry path can be streamlined. For details, see
http://lkml.kernel.org/r/20180325162527.GA17492@light.dominikbrodowski.net
Cc: Al Viro <viro@zeniv.linux.org.uk>
Cc: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Dominik Brodowski <linux@dominikbrodowski.net>
-rw-r--r-- | ipc/sem.c | 14 | ||||
-rw-r--r-- | ipc/syscall.c | 4 | ||||
-rw-r--r-- | ipc/util.h | 2 |
3 files changed, 16 insertions, 4 deletions
@@ -1581,7 +1581,7 @@ out_up: | |||
1581 | return err; | 1581 | return err; |
1582 | } | 1582 | } |
1583 | 1583 | ||
1584 | SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, unsigned long, arg) | 1584 | long ksys_semctl(int semid, int semnum, int cmd, unsigned long arg) |
1585 | { | 1585 | { |
1586 | int version; | 1586 | int version; |
1587 | struct ipc_namespace *ns; | 1587 | struct ipc_namespace *ns; |
@@ -1635,6 +1635,11 @@ SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, unsigned long, arg) | |||
1635 | } | 1635 | } |
1636 | } | 1636 | } |
1637 | 1637 | ||
1638 | SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, unsigned long, arg) | ||
1639 | { | ||
1640 | return ksys_semctl(semid, semnum, cmd, arg); | ||
1641 | } | ||
1642 | |||
1638 | #ifdef CONFIG_COMPAT | 1643 | #ifdef CONFIG_COMPAT |
1639 | 1644 | ||
1640 | struct compat_semid_ds { | 1645 | struct compat_semid_ds { |
@@ -1683,7 +1688,7 @@ static int copy_compat_semid_to_user(void __user *buf, struct semid64_ds *in, | |||
1683 | } | 1688 | } |
1684 | } | 1689 | } |
1685 | 1690 | ||
1686 | COMPAT_SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, int, arg) | 1691 | long compat_ksys_semctl(int semid, int semnum, int cmd, int arg) |
1687 | { | 1692 | { |
1688 | void __user *p = compat_ptr(arg); | 1693 | void __user *p = compat_ptr(arg); |
1689 | struct ipc_namespace *ns; | 1694 | struct ipc_namespace *ns; |
@@ -1727,6 +1732,11 @@ COMPAT_SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, int, arg) | |||
1727 | return -EINVAL; | 1732 | return -EINVAL; |
1728 | } | 1733 | } |
1729 | } | 1734 | } |
1735 | |||
1736 | COMPAT_SYSCALL_DEFINE4(semctl, int, semid, int, semnum, int, cmd, int, arg) | ||
1737 | { | ||
1738 | return compat_ksys_semctl(semid, semnum, cmd, arg); | ||
1739 | } | ||
1730 | #endif | 1740 | #endif |
1731 | 1741 | ||
1732 | /* If the task doesn't already have a undo_list, then allocate one | 1742 | /* If the task doesn't already have a undo_list, then allocate one |
diff --git a/ipc/syscall.c b/ipc/syscall.c index 21fcdf0b4836..a536cca37661 100644 --- a/ipc/syscall.c +++ b/ipc/syscall.c | |||
@@ -42,7 +42,7 @@ SYSCALL_DEFINE6(ipc, unsigned int, call, int, first, unsigned long, second, | |||
42 | return -EINVAL; | 42 | return -EINVAL; |
43 | if (get_user(arg, (unsigned long __user *) ptr)) | 43 | if (get_user(arg, (unsigned long __user *) ptr)) |
44 | return -EFAULT; | 44 | return -EFAULT; |
45 | return sys_semctl(first, second, third, arg); | 45 | return ksys_semctl(first, second, third, arg); |
46 | } | 46 | } |
47 | 47 | ||
48 | case MSGSND: | 48 | case MSGSND: |
@@ -138,7 +138,7 @@ COMPAT_SYSCALL_DEFINE6(ipc, u32, call, int, first, int, second, | |||
138 | return -EINVAL; | 138 | return -EINVAL; |
139 | if (get_user(pad, (u32 __user *) compat_ptr(ptr))) | 139 | if (get_user(pad, (u32 __user *) compat_ptr(ptr))) |
140 | return -EFAULT; | 140 | return -EFAULT; |
141 | return compat_sys_semctl(first, second, third, pad); | 141 | return compat_ksys_semctl(first, second, third, pad); |
142 | 142 | ||
143 | case MSGSND: | 143 | case MSGSND: |
144 | return compat_sys_msgsnd(first, ptr, second, third); | 144 | return compat_sys_msgsnd(first, ptr, second, third); |
diff --git a/ipc/util.h b/ipc/util.h index 0f07056e5a73..1f1109b83437 100644 --- a/ipc/util.h +++ b/ipc/util.h | |||
@@ -241,12 +241,14 @@ long ksys_semtimedop(int semid, struct sembuf __user *tsops, | |||
241 | unsigned int nsops, | 241 | unsigned int nsops, |
242 | const struct timespec __user *timeout); | 242 | const struct timespec __user *timeout); |
243 | long ksys_semget(key_t key, int nsems, int semflg); | 243 | long ksys_semget(key_t key, int nsems, int semflg); |
244 | long ksys_semctl(int semid, int semnum, int cmd, unsigned long arg); | ||
244 | 245 | ||
245 | /* for CONFIG_ARCH_WANT_OLD_COMPAT_IPC */ | 246 | /* for CONFIG_ARCH_WANT_OLD_COMPAT_IPC */ |
246 | #ifdef CONFIG_COMPAT | 247 | #ifdef CONFIG_COMPAT |
247 | long compat_ksys_semtimedop(int semid, struct sembuf __user *tsems, | 248 | long compat_ksys_semtimedop(int semid, struct sembuf __user *tsems, |
248 | unsigned int nsops, | 249 | unsigned int nsops, |
249 | const struct compat_timespec __user *timeout); | 250 | const struct compat_timespec __user *timeout); |
251 | long compat_ksys_semctl(int semid, int semnum, int cmd, int arg); | ||
250 | #endif /* CONFIG_COMPAT */ | 252 | #endif /* CONFIG_COMPAT */ |
251 | 253 | ||
252 | #endif | 254 | #endif |