Skip to content

Commit

Permalink
[PATCH] make osf_select() use core_sys_select()
Browse files Browse the repository at this point in the history
... instead of open-coding it

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
  • Loading branch information
Al Viro committed May 1, 2008
1 parent bf7da7b commit a2dcb44
Show file tree
Hide file tree
Showing 3 changed files with 7 additions and 66 deletions.
69 changes: 4 additions & 65 deletions arch/alpha/kernel/osf_sys.c
Original file line number Diff line number Diff line change
Expand Up @@ -981,88 +981,27 @@ 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);
timeout += sec * (unsigned long) HZ;
}
}

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 {
Expand Down
2 changes: 1 addition & 1 deletion fs/select.c
Original file line number Diff line number Diff line change
Expand Up @@ -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;
Expand Down
2 changes: 2 additions & 0 deletions include/linux/poll.h
Original file line number Diff line number Diff line change
Expand Up @@ -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 */

Expand Down

0 comments on commit a2dcb44

Please sign in to comment.