summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2008-04-23 14:05:15 -0400
committerAl Viro <viro@zeniv.linux.org.uk>2008-05-01 13:07:28 -0400
commita2dcb44c3c5a8151d2d9f6ac8ad0789efcdbe184 (patch)
tree8711fc210dc58372a859e6a6cf78dc638d768600
parentbf7da7bcfb38409b4cdea34b0905bdf344f1b36d (diff)
[PATCH] make osf_select() use core_sys_select()
... instead of open-coding it Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
-rw-r--r--arch/alpha/kernel/osf_sys.c69
-rw-r--r--fs/select.c2
-rw-r--r--include/linux/poll.h2
3 files changed, 7 insertions, 66 deletions
diff --git a/arch/alpha/kernel/osf_sys.c b/arch/alpha/kernel/osf_sys.c
index 9fee37e2596..32ca1b92730 100644
--- a/arch/alpha/kernel/osf_sys.c
+++ b/arch/alpha/kernel/osf_sys.c
@@ -981,27 +981,18 @@ asmlinkage int
osf_select(int n, fd_set __user *inp, fd_set __user *outp, fd_set __user *exp,
struct timeval32 __user *tvp)
{
- fd_set_bits fds;
- char *bits;
- size_t size;
- long timeout;
- int ret = -EINVAL;
- struct fdtable *fdt;
- int max_fds;
-
- timeout = MAX_SCHEDULE_TIMEOUT;
+ s64 timeout = MAX_SCHEDULE_TIMEOUT;
if (tvp) {
time_t sec, usec;
if (!access_ok(VERIFY_READ, tvp, sizeof(*tvp))
|| __get_user(sec, &tvp->tv_sec)
|| __get_user(usec, &tvp->tv_usec)) {
- ret = -EFAULT;
- goto out_nofds;
+ return -EFAULT;
}
if (sec < 0 || usec < 0)
- goto out_nofds;
+ return -EINVAL;
if ((unsigned long) sec < MAX_SELECT_SECONDS) {
timeout = (usec + 1000000/HZ - 1) / (1000000/HZ);
@@ -1009,60 +1000,8 @@ osf_select(int n, fd_set __user *inp, fd_set __user *outp, fd_set __user *exp,
}
}
- rcu_read_lock();
- fdt = files_fdtable(current->files);
- max_fds = fdt->max_fds;
- rcu_read_unlock();
- if (n < 0 || n > max_fds)
- goto out_nofds;
-
- /*
- * We need 6 bitmaps (in/out/ex for both incoming and outgoing),
- * since we used fdset we need to allocate memory in units of
- * long-words.
- */
- ret = -ENOMEM;
- size = FDS_BYTES(n);
- bits = kmalloc(6 * size, GFP_KERNEL);
- if (!bits)
- goto out_nofds;
- fds.in = (unsigned long *) bits;
- fds.out = (unsigned long *) (bits + size);
- fds.ex = (unsigned long *) (bits + 2*size);
- fds.res_in = (unsigned long *) (bits + 3*size);
- fds.res_out = (unsigned long *) (bits + 4*size);
- fds.res_ex = (unsigned long *) (bits + 5*size);
-
- if ((ret = get_fd_set(n, inp->fds_bits, fds.in)) ||
- (ret = get_fd_set(n, outp->fds_bits, fds.out)) ||
- (ret = get_fd_set(n, exp->fds_bits, fds.ex)))
- goto out;
- zero_fd_set(n, fds.res_in);
- zero_fd_set(n, fds.res_out);
- zero_fd_set(n, fds.res_ex);
-
- ret = do_select(n, &fds, &timeout);
-
/* OSF does not copy back the remaining time. */
-
- if (ret < 0)
- goto out;
- if (!ret) {
- ret = -ERESTARTNOHAND;
- if (signal_pending(current))
- goto out;
- ret = 0;
- }
-
- if (set_fd_set(n, inp->fds_bits, fds.res_in) ||
- set_fd_set(n, outp->fds_bits, fds.res_out) ||
- set_fd_set(n, exp->fds_bits, fds.res_ex))
- ret = -EFAULT;
-
- out:
- kfree(bits);
- out_nofds:
- return ret;
+ return core_sys_select(n, inp, outp, exp, &timeout);
}
struct rusage32 {
diff --git a/fs/select.c b/fs/select.c
index 2c292146e24..80d70387e79 100644
--- a/fs/select.c
+++ b/fs/select.c
@@ -298,7 +298,7 @@ int do_select(int n, fd_set_bits *fds, s64 *timeout)
#define MAX_SELECT_SECONDS \
((unsigned long) (MAX_SCHEDULE_TIMEOUT / HZ)-1)
-static int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
+int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
fd_set __user *exp, s64 *timeout)
{
fd_set_bits fds;
diff --git a/include/linux/poll.h b/include/linux/poll.h
index 16d813b364e..ef453828877 100644
--- a/include/linux/poll.h
+++ b/include/linux/poll.h
@@ -117,6 +117,8 @@ void zero_fd_set(unsigned long nr, unsigned long *fdset)
extern int do_select(int n, fd_set_bits *fds, s64 *timeout);
extern int do_sys_poll(struct pollfd __user * ufds, unsigned int nfds,
s64 *timeout);
+extern int core_sys_select(int n, fd_set __user *inp, fd_set __user *outp,
+ fd_set __user *exp, s64 *timeout);
#endif /* KERNEL */