source: rtems-libbsd/freebsd/sys/kern/sys_generic.c @ b3169c2

55-freebsd-126-freebsd-12
Last change on this file since b3169c2 was b3169c2, checked in by Sebastian Huber <sebastian.huber@…>, on Oct 23, 2018 at 6:22:44 AM

Update to FreeBSD head 2018-10-23

Git mirror commit 59f44d20be3f99d181ca742e636d45fc39ec982b.

This commit updates OpenSSL to version 1.1.1. This required an update
of racoon which uses some internal stuff from OpenSSL and seems to be
mostly unmaintained, e.g. there is update in the FreeBSD ports to cope
with OpenSSL 1.1.1.

Update #3472.

  • Property mode set to 100644
File size: 44.9 KB
Line 
1#include <machine/rtems-bsd-kernel-space.h>
2
3/*-
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 * Copyright (c) 1982, 1986, 1989, 1993
7 *      The Regents of the University of California.  All rights reserved.
8 * (c) UNIX System Laboratories, Inc.
9 * All or some portions of this file are derived from material licensed
10 * to the University of California by American Telephone and Telegraph
11 * Co. or Unix System Laboratories, Inc. and are reproduced herein with
12 * the permission of UNIX System Laboratories, Inc.
13 *
14 * Redistribution and use in source and binary forms, with or without
15 * modification, are permitted provided that the following conditions
16 * are met:
17 * 1. Redistributions of source code must retain the above copyright
18 *    notice, this list of conditions and the following disclaimer.
19 * 2. Redistributions in binary form must reproduce the above copyright
20 *    notice, this list of conditions and the following disclaimer in the
21 *    documentation and/or other materials provided with the distribution.
22 * 3. Neither the name of the University nor the names of its contributors
23 *    may be used to endorse or promote products derived from this software
24 *    without specific prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
27 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
30 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 * SUCH DAMAGE.
37 *
38 *      @(#)sys_generic.c       8.5 (Berkeley) 1/21/94
39 */
40
41#include <sys/cdefs.h>
42__FBSDID("$FreeBSD$");
43
44#include <rtems/bsd/local/opt_capsicum.h>
45#include <rtems/bsd/local/opt_ktrace.h>
46
47#include <sys/param.h>
48#include <sys/systm.h>
49#include <sys/sysproto.h>
50#include <sys/capsicum.h>
51#include <sys/filedesc.h>
52#include <sys/filio.h>
53#include <sys/fcntl.h>
54#include <sys/file.h>
55#include <sys/lock.h>
56#include <sys/proc.h>
57#include <sys/signalvar.h>
58#include <sys/socketvar.h>
59#include <sys/uio.h>
60#include <sys/kernel.h>
61#include <sys/ktr.h>
62#include <sys/limits.h>
63#include <sys/malloc.h>
64#include <sys/poll.h>
65#include <sys/resourcevar.h>
66#include <sys/selinfo.h>
67#include <sys/sleepqueue.h>
68#include <sys/syscallsubr.h>
69#include <sys/sysctl.h>
70#include <sys/sysent.h>
71#include <sys/vnode.h>
72#include <sys/bio.h>
73#include <sys/buf.h>
74#include <sys/condvar.h>
75#ifdef KTRACE
76#include <sys/ktrace.h>
77#endif
78
79#include <security/audit/audit.h>
80#ifdef __rtems__
81#include <machine/rtems-bsd-syscall-api.h>
82#endif /* __rtems__ */
83
84/*
85 * The following macro defines how many bytes will be allocated from
86 * the stack instead of memory allocated when passing the IOCTL data
87 * structures from userspace and to the kernel. Some IOCTLs having
88 * small data structures are used very frequently and this small
89 * buffer on the stack gives a significant speedup improvement for
90 * those requests. The value of this define should be greater or equal
91 * to 64 bytes and should also be power of two. The data structure is
92 * currently hard-aligned to a 8-byte boundary on the stack. This
93 * should currently be sufficient for all supported platforms.
94 */
95#define SYS_IOCTL_SMALL_SIZE    128     /* bytes */
96#define SYS_IOCTL_SMALL_ALIGN   8       /* bytes */
97
98#ifndef __rtems__
99#ifdef __LP64__
100static int iosize_max_clamp = 0;
101SYSCTL_INT(_debug, OID_AUTO, iosize_max_clamp, CTLFLAG_RW,
102    &iosize_max_clamp, 0, "Clamp max i/o size to INT_MAX");
103static int devfs_iosize_max_clamp = 1;
104SYSCTL_INT(_debug, OID_AUTO, devfs_iosize_max_clamp, CTLFLAG_RW,
105    &devfs_iosize_max_clamp, 0, "Clamp max i/o size to INT_MAX for devices");
106#endif
107
108/*
109 * Assert that the return value of read(2) and write(2) syscalls fits
110 * into a register.  If not, an architecture will need to provide the
111 * usermode wrappers to reconstruct the result.
112 */
113CTASSERT(sizeof(register_t) >= sizeof(size_t));
114
115static MALLOC_DEFINE(M_IOCTLOPS, "ioctlops", "ioctl data buffer");
116#endif /* __rtems__ */
117static MALLOC_DEFINE(M_SELECT, "select", "select() buffer");
118#ifndef __rtems__
119MALLOC_DEFINE(M_IOV, "iov", "large iov's");
120#endif /* __rtems__ */
121
122static int      pollout(struct thread *, struct pollfd *, struct pollfd *,
123                    u_int);
124static int      pollscan(struct thread *, struct pollfd *, u_int);
125static int      pollrescan(struct thread *);
126static int      selscan(struct thread *, fd_mask **, fd_mask **, int);
127static int      selrescan(struct thread *, fd_mask **, fd_mask **);
128static void     selfdalloc(struct thread *, void *);
129static void     selfdfree(struct seltd *, struct selfd *);
130#ifndef __rtems__
131static int      dofileread(struct thread *, int, struct file *, struct uio *,
132                    off_t, int);
133static int      dofilewrite(struct thread *, int, struct file *, struct uio *,
134                    off_t, int);
135#endif /* __rtems__ */
136static void     doselwakeup(struct selinfo *, int);
137static void     seltdinit(struct thread *);
138static int      seltdwait(struct thread *, sbintime_t, sbintime_t);
139static void     seltdclear(struct thread *);
140
141/*
142 * One seltd per-thread allocated on demand as needed.
143 *
144 *      t - protected by st_mtx
145 *      k - Only accessed by curthread or read-only
146 */
147struct seltd {
148        STAILQ_HEAD(, selfd)    st_selq;        /* (k) List of selfds. */
149        struct selfd            *st_free1;      /* (k) free fd for read set. */
150        struct selfd            *st_free2;      /* (k) free fd for write set. */
151        struct mtx              st_mtx;         /* Protects struct seltd */
152        struct cv               st_wait;        /* (t) Wait channel. */
153        int                     st_flags;       /* (t) SELTD_ flags. */
154};
155
156#define SELTD_PENDING   0x0001                  /* We have pending events. */
157#define SELTD_RESCAN    0x0002                  /* Doing a rescan. */
158
159/*
160 * One selfd allocated per-thread per-file-descriptor.
161 *      f - protected by sf_mtx
162 */
163struct selfd {
164        STAILQ_ENTRY(selfd)     sf_link;        /* (k) fds owned by this td. */
165        TAILQ_ENTRY(selfd)      sf_threads;     /* (f) fds on this selinfo. */
166        struct selinfo          *sf_si;         /* (f) selinfo when linked. */
167        struct mtx              *sf_mtx;        /* Pointer to selinfo mtx. */
168        struct seltd            *sf_td;         /* (k) owning seltd. */
169        void                    *sf_cookie;     /* (k) fd or pollfd. */
170        u_int                   sf_refs;
171};
172
173static uma_zone_t selfd_zone;
174static struct mtx_pool *mtxpool_select;
175
176#ifndef __rtems__
177#ifdef __LP64__
178size_t
179devfs_iosize_max(void)
180{
181
182        return (devfs_iosize_max_clamp || SV_CURPROC_FLAG(SV_ILP32) ?
183            INT_MAX : SSIZE_MAX);
184}
185
186size_t
187iosize_max(void)
188{
189
190        return (iosize_max_clamp || SV_CURPROC_FLAG(SV_ILP32) ?
191            INT_MAX : SSIZE_MAX);
192}
193#endif
194
195#ifndef _SYS_SYSPROTO_H_
196struct read_args {
197        int     fd;
198        void    *buf;
199        size_t  nbyte;
200};
201#endif
202int
203sys_read(struct thread *td, struct read_args *uap)
204{
205        struct uio auio;
206        struct iovec aiov;
207        int error;
208
209        if (uap->nbyte > IOSIZE_MAX)
210                return (EINVAL);
211        aiov.iov_base = uap->buf;
212        aiov.iov_len = uap->nbyte;
213        auio.uio_iov = &aiov;
214        auio.uio_iovcnt = 1;
215        auio.uio_resid = uap->nbyte;
216        auio.uio_segflg = UIO_USERSPACE;
217        error = kern_readv(td, uap->fd, &auio);
218        return (error);
219}
220
221/*
222 * Positioned read system call
223 */
224#ifndef _SYS_SYSPROTO_H_
225struct pread_args {
226        int     fd;
227        void    *buf;
228        size_t  nbyte;
229        int     pad;
230        off_t   offset;
231};
232#endif
233int
234sys_pread(struct thread *td, struct pread_args *uap)
235{
236
237        return (kern_pread(td, uap->fd, uap->buf, uap->nbyte, uap->offset));
238}
239
240int
241kern_pread(struct thread *td, int fd, void *buf, size_t nbyte, off_t offset)
242{
243        struct uio auio;
244        struct iovec aiov;
245        int error;
246
247        if (nbyte > IOSIZE_MAX)
248                return (EINVAL);
249        aiov.iov_base = buf;
250        aiov.iov_len = nbyte;
251        auio.uio_iov = &aiov;
252        auio.uio_iovcnt = 1;
253        auio.uio_resid = nbyte;
254        auio.uio_segflg = UIO_USERSPACE;
255        error = kern_preadv(td, fd, &auio, offset);
256        return (error);
257}
258
259#if defined(COMPAT_FREEBSD6)
260int
261freebsd6_pread(struct thread *td, struct freebsd6_pread_args *uap)
262{
263
264        return (kern_pread(td, uap->fd, uap->buf, uap->nbyte, uap->offset));
265}
266#endif
267
268/*
269 * Scatter read system call.
270 */
271#ifndef _SYS_SYSPROTO_H_
272struct readv_args {
273        int     fd;
274        struct  iovec *iovp;
275        u_int   iovcnt;
276};
277#endif
278int
279sys_readv(struct thread *td, struct readv_args *uap)
280{
281        struct uio *auio;
282        int error;
283
284        error = copyinuio(uap->iovp, uap->iovcnt, &auio);
285        if (error)
286                return (error);
287        error = kern_readv(td, uap->fd, auio);
288        free(auio, M_IOV);
289        return (error);
290}
291
292int
293kern_readv(struct thread *td, int fd, struct uio *auio)
294{
295        struct file *fp;
296        int error;
297
298        error = fget_read(td, fd, &cap_read_rights, &fp);
299        if (error)
300                return (error);
301        error = dofileread(td, fd, fp, auio, (off_t)-1, 0);
302        fdrop(fp, td);
303        return (error);
304}
305
306/*
307 * Scatter positioned read system call.
308 */
309#ifndef _SYS_SYSPROTO_H_
310struct preadv_args {
311        int     fd;
312        struct  iovec *iovp;
313        u_int   iovcnt;
314        off_t   offset;
315};
316#endif
317int
318sys_preadv(struct thread *td, struct preadv_args *uap)
319{
320        struct uio *auio;
321        int error;
322
323        error = copyinuio(uap->iovp, uap->iovcnt, &auio);
324        if (error)
325                return (error);
326        error = kern_preadv(td, uap->fd, auio, uap->offset);
327        free(auio, M_IOV);
328        return (error);
329}
330
331int
332kern_preadv(struct thread *td, int fd, struct uio *auio, off_t offset)
333{
334        struct file *fp;
335        int error;
336
337        error = fget_read(td, fd, &cap_pread_rights, &fp);
338        if (error)
339                return (error);
340        if (!(fp->f_ops->fo_flags & DFLAG_SEEKABLE))
341                error = ESPIPE;
342        else if (offset < 0 &&
343            (fp->f_vnode == NULL || fp->f_vnode->v_type != VCHR))
344                error = EINVAL;
345        else
346                error = dofileread(td, fd, fp, auio, offset, FOF_OFFSET);
347        fdrop(fp, td);
348        return (error);
349}
350
351/*
352 * Common code for readv and preadv that reads data in
353 * from a file using the passed in uio, offset, and flags.
354 */
355static int
356dofileread(struct thread *td, int fd, struct file *fp, struct uio *auio,
357    off_t offset, int flags)
358{
359        ssize_t cnt;
360        int error;
361#ifdef KTRACE
362        struct uio *ktruio = NULL;
363#endif
364
365        AUDIT_ARG_FD(fd);
366
367        /* Finish zero length reads right here */
368        if (auio->uio_resid == 0) {
369                td->td_retval[0] = 0;
370                return (0);
371        }
372        auio->uio_rw = UIO_READ;
373        auio->uio_offset = offset;
374        auio->uio_td = td;
375#ifdef KTRACE
376        if (KTRPOINT(td, KTR_GENIO)) 
377                ktruio = cloneuio(auio);
378#endif
379        cnt = auio->uio_resid;
380        if ((error = fo_read(fp, auio, td->td_ucred, flags, td))) {
381                if (auio->uio_resid != cnt && (error == ERESTART ||
382                    error == EINTR || error == EWOULDBLOCK))
383                        error = 0;
384        }
385        cnt -= auio->uio_resid;
386#ifdef KTRACE
387        if (ktruio != NULL) {
388                ktruio->uio_resid = cnt;
389                ktrgenio(fd, UIO_READ, ktruio, error);
390        }
391#endif
392        td->td_retval[0] = cnt;
393        return (error);
394}
395
396#ifndef _SYS_SYSPROTO_H_
397struct write_args {
398        int     fd;
399        const void *buf;
400        size_t  nbyte;
401};
402#endif
403int
404sys_write(struct thread *td, struct write_args *uap)
405{
406        struct uio auio;
407        struct iovec aiov;
408        int error;
409
410        if (uap->nbyte > IOSIZE_MAX)
411                return (EINVAL);
412        aiov.iov_base = (void *)(uintptr_t)uap->buf;
413        aiov.iov_len = uap->nbyte;
414        auio.uio_iov = &aiov;
415        auio.uio_iovcnt = 1;
416        auio.uio_resid = uap->nbyte;
417        auio.uio_segflg = UIO_USERSPACE;
418        error = kern_writev(td, uap->fd, &auio);
419        return (error);
420}
421
422/*
423 * Positioned write system call.
424 */
425#ifndef _SYS_SYSPROTO_H_
426struct pwrite_args {
427        int     fd;
428        const void *buf;
429        size_t  nbyte;
430        int     pad;
431        off_t   offset;
432};
433#endif
434int
435sys_pwrite(struct thread *td, struct pwrite_args *uap)
436{
437
438        return (kern_pwrite(td, uap->fd, uap->buf, uap->nbyte, uap->offset));
439}
440
441int
442kern_pwrite(struct thread *td, int fd, const void *buf, size_t nbyte,
443    off_t offset)
444{
445        struct uio auio;
446        struct iovec aiov;
447        int error;
448
449        if (nbyte > IOSIZE_MAX)
450                return (EINVAL);
451        aiov.iov_base = (void *)(uintptr_t)buf;
452        aiov.iov_len = nbyte;
453        auio.uio_iov = &aiov;
454        auio.uio_iovcnt = 1;
455        auio.uio_resid = nbyte;
456        auio.uio_segflg = UIO_USERSPACE;
457        error = kern_pwritev(td, fd, &auio, offset);
458        return (error);
459}
460
461#if defined(COMPAT_FREEBSD6)
462int
463freebsd6_pwrite(struct thread *td, struct freebsd6_pwrite_args *uap)
464{
465
466        return (kern_pwrite(td, uap->fd, uap->buf, uap->nbyte, uap->offset));
467}
468#endif
469
470/*
471 * Gather write system call.
472 */
473#ifndef _SYS_SYSPROTO_H_
474struct writev_args {
475        int     fd;
476        struct  iovec *iovp;
477        u_int   iovcnt;
478};
479#endif
480int
481sys_writev(struct thread *td, struct writev_args *uap)
482{
483        struct uio *auio;
484        int error;
485
486        error = copyinuio(uap->iovp, uap->iovcnt, &auio);
487        if (error)
488                return (error);
489        error = kern_writev(td, uap->fd, auio);
490        free(auio, M_IOV);
491        return (error);
492}
493
494int
495kern_writev(struct thread *td, int fd, struct uio *auio)
496{
497        struct file *fp;
498        int error;
499
500        error = fget_write(td, fd, &cap_write_rights, &fp);
501        if (error)
502                return (error);
503        error = dofilewrite(td, fd, fp, auio, (off_t)-1, 0);
504        fdrop(fp, td);
505        return (error);
506}
507
508/*
509 * Gather positioned write system call.
510 */
511#ifndef _SYS_SYSPROTO_H_
512struct pwritev_args {
513        int     fd;
514        struct  iovec *iovp;
515        u_int   iovcnt;
516        off_t   offset;
517};
518#endif
519int
520sys_pwritev(struct thread *td, struct pwritev_args *uap)
521{
522        struct uio *auio;
523        int error;
524
525        error = copyinuio(uap->iovp, uap->iovcnt, &auio);
526        if (error)
527                return (error);
528        error = kern_pwritev(td, uap->fd, auio, uap->offset);
529        free(auio, M_IOV);
530        return (error);
531}
532
533int
534kern_pwritev(struct thread *td, int fd, struct uio *auio, off_t offset)
535{
536        struct file *fp;
537        int error;
538
539        error = fget_write(td, fd, &cap_pwrite_rights, &fp);
540        if (error)
541                return (error);
542        if (!(fp->f_ops->fo_flags & DFLAG_SEEKABLE))
543                error = ESPIPE;
544        else if (offset < 0 &&
545            (fp->f_vnode == NULL || fp->f_vnode->v_type != VCHR))
546                error = EINVAL;
547        else
548                error = dofilewrite(td, fd, fp, auio, offset, FOF_OFFSET);
549        fdrop(fp, td);
550        return (error);
551}
552
553/*
554 * Common code for writev and pwritev that writes data to
555 * a file using the passed in uio, offset, and flags.
556 */
557static int
558dofilewrite(struct thread *td, int fd, struct file *fp, struct uio *auio,
559    off_t offset, int flags)
560{
561        ssize_t cnt;
562        int error;
563#ifdef KTRACE
564        struct uio *ktruio = NULL;
565#endif
566
567        AUDIT_ARG_FD(fd);
568        auio->uio_rw = UIO_WRITE;
569        auio->uio_td = td;
570        auio->uio_offset = offset;
571#ifdef KTRACE
572        if (KTRPOINT(td, KTR_GENIO))
573                ktruio = cloneuio(auio);
574#endif
575        cnt = auio->uio_resid;
576        if (fp->f_type == DTYPE_VNODE &&
577            (fp->f_vnread_flags & FDEVFS_VNODE) == 0)
578                bwillwrite();
579        if ((error = fo_write(fp, auio, td->td_ucred, flags, td))) {
580                if (auio->uio_resid != cnt && (error == ERESTART ||
581                    error == EINTR || error == EWOULDBLOCK))
582                        error = 0;
583                /* Socket layer is responsible for issuing SIGPIPE. */
584                if (fp->f_type != DTYPE_SOCKET && error == EPIPE) {
585                        PROC_LOCK(td->td_proc);
586                        tdsignal(td, SIGPIPE);
587                        PROC_UNLOCK(td->td_proc);
588                }
589        }
590        cnt -= auio->uio_resid;
591#ifdef KTRACE
592        if (ktruio != NULL) {
593                ktruio->uio_resid = cnt;
594                ktrgenio(fd, UIO_WRITE, ktruio, error);
595        }
596#endif
597        td->td_retval[0] = cnt;
598        return (error);
599}
600
601/*
602 * Truncate a file given a file descriptor.
603 *
604 * Can't use fget_write() here, since must return EINVAL and not EBADF if the
605 * descriptor isn't writable.
606 */
607int
608kern_ftruncate(struct thread *td, int fd, off_t length)
609{
610        struct file *fp;
611        int error;
612
613        AUDIT_ARG_FD(fd);
614        if (length < 0)
615                return (EINVAL);
616        error = fget(td, fd, &cap_ftruncate_rights, &fp);
617        if (error)
618                return (error);
619        AUDIT_ARG_FILE(td->td_proc, fp);
620        if (!(fp->f_flag & FWRITE)) {
621                fdrop(fp, td);
622                return (EINVAL);
623        }
624        error = fo_truncate(fp, length, td->td_ucred, td);
625        fdrop(fp, td);
626        return (error);
627}
628
629#ifndef _SYS_SYSPROTO_H_
630struct ftruncate_args {
631        int     fd;
632        int     pad;
633        off_t   length;
634};
635#endif
636int
637sys_ftruncate(struct thread *td, struct ftruncate_args *uap)
638{
639
640        return (kern_ftruncate(td, uap->fd, uap->length));
641}
642
643#if defined(COMPAT_43)
644#ifndef _SYS_SYSPROTO_H_
645struct oftruncate_args {
646        int     fd;
647        long    length;
648};
649#endif
650int
651oftruncate(struct thread *td, struct oftruncate_args *uap)
652{
653
654        return (kern_ftruncate(td, uap->fd, uap->length));
655}
656#endif /* COMPAT_43 */
657
658#ifndef _SYS_SYSPROTO_H_
659struct ioctl_args {
660        int     fd;
661        u_long  com;
662        caddr_t data;
663};
664#endif
665/* ARGSUSED */
666int
667sys_ioctl(struct thread *td, struct ioctl_args *uap)
668{
669        u_char smalldata[SYS_IOCTL_SMALL_SIZE] __aligned(SYS_IOCTL_SMALL_ALIGN);
670        u_long com;
671        int arg, error;
672        u_int size;
673        caddr_t data;
674
675        if (uap->com > 0xffffffff) {
676                printf(
677                    "WARNING pid %d (%s): ioctl sign-extension ioctl %lx\n",
678                    td->td_proc->p_pid, td->td_name, uap->com);
679                uap->com &= 0xffffffff;
680        }
681        com = uap->com;
682
683        /*
684         * Interpret high order word to find amount of data to be
685         * copied to/from the user's address space.
686         */
687        size = IOCPARM_LEN(com);
688        if ((size > IOCPARM_MAX) ||
689            ((com & (IOC_VOID  | IOC_IN | IOC_OUT)) == 0) ||
690#if defined(COMPAT_FREEBSD5) || defined(COMPAT_FREEBSD4) || defined(COMPAT_43)
691            ((com & IOC_OUT) && size == 0) ||
692#else
693            ((com & (IOC_IN | IOC_OUT)) && size == 0) ||
694#endif
695            ((com & IOC_VOID) && size > 0 && size != sizeof(int)))
696                return (ENOTTY);
697
698        if (size > 0) {
699                if (com & IOC_VOID) {
700                        /* Integer argument. */
701                        arg = (intptr_t)uap->data;
702                        data = (void *)&arg;
703                        size = 0;
704                } else {
705                        if (size > SYS_IOCTL_SMALL_SIZE)
706                                data = malloc((u_long)size, M_IOCTLOPS, M_WAITOK);
707                        else
708                                data = smalldata;
709                }
710        } else
711                data = (void *)&uap->data;
712        if (com & IOC_IN) {
713                error = copyin(uap->data, data, (u_int)size);
714                if (error != 0)
715                        goto out;
716        } else if (com & IOC_OUT) {
717                /*
718                 * Zero the buffer so the user always
719                 * gets back something deterministic.
720                 */
721                bzero(data, size);
722        }
723
724        error = kern_ioctl(td, uap->fd, com, data);
725
726        if (error == 0 && (com & IOC_OUT))
727                error = copyout(data, uap->data, (u_int)size);
728
729out:
730        if (size > SYS_IOCTL_SMALL_SIZE)
731                free(data, M_IOCTLOPS);
732        return (error);
733}
734
735int
736kern_ioctl(struct thread *td, int fd, u_long com, caddr_t data)
737{
738        struct file *fp;
739        struct filedesc *fdp;
740        int error, tmp, locked;
741
742        AUDIT_ARG_FD(fd);
743        AUDIT_ARG_CMD(com);
744
745        fdp = td->td_proc->p_fd;
746
747        switch (com) {
748        case FIONCLEX:
749        case FIOCLEX:
750                FILEDESC_XLOCK(fdp);
751                locked = LA_XLOCKED;
752                break;
753        default:
754#ifdef CAPABILITIES
755                FILEDESC_SLOCK(fdp);
756                locked = LA_SLOCKED;
757#else
758                locked = LA_UNLOCKED;
759#endif
760                break;
761        }
762
763#ifdef CAPABILITIES
764        if ((fp = fget_locked(fdp, fd)) == NULL) {
765                error = EBADF;
766                goto out;
767        }
768        if ((error = cap_ioctl_check(fdp, fd, com)) != 0) {
769                fp = NULL;      /* fhold() was not called yet */
770                goto out;
771        }
772        fhold(fp);
773        if (locked == LA_SLOCKED) {
774                FILEDESC_SUNLOCK(fdp);
775                locked = LA_UNLOCKED;
776        }
777#else
778        error = fget(td, fd, &cap_ioctl_rights, &fp);
779        if (error != 0) {
780                fp = NULL;
781                goto out;
782        }
783#endif
784        if ((fp->f_flag & (FREAD | FWRITE)) == 0) {
785                error = EBADF;
786                goto out;
787        }
788
789        switch (com) {
790        case FIONCLEX:
791                fdp->fd_ofiles[fd].fde_flags &= ~UF_EXCLOSE;
792                goto out;
793        case FIOCLEX:
794                fdp->fd_ofiles[fd].fde_flags |= UF_EXCLOSE;
795                goto out;
796        case FIONBIO:
797                if ((tmp = *(int *)data))
798                        atomic_set_int(&fp->f_flag, FNONBLOCK);
799                else
800                        atomic_clear_int(&fp->f_flag, FNONBLOCK);
801                data = (void *)&tmp;
802                break;
803        case FIOASYNC:
804                if ((tmp = *(int *)data))
805                        atomic_set_int(&fp->f_flag, FASYNC);
806                else
807                        atomic_clear_int(&fp->f_flag, FASYNC);
808                data = (void *)&tmp;
809                break;
810        }
811
812        error = fo_ioctl(fp, com, data, td->td_ucred, td);
813out:
814        switch (locked) {
815        case LA_XLOCKED:
816                FILEDESC_XUNLOCK(fdp);
817                break;
818#ifdef CAPABILITIES
819        case LA_SLOCKED:
820                FILEDESC_SUNLOCK(fdp);
821                break;
822#endif
823        default:
824                FILEDESC_UNLOCK_ASSERT(fdp);
825                break;
826        }
827        if (fp != NULL)
828                fdrop(fp, td);
829        return (error);
830}
831#endif /* __rtems__ */
832
833int
834poll_no_poll(int events)
835{
836        /*
837         * Return true for read/write.  If the user asked for something
838         * special, return POLLNVAL, so that clients have a way of
839         * determining reliably whether or not the extended
840         * functionality is present without hard-coding knowledge
841         * of specific filesystem implementations.
842         */
843        if (events & ~POLLSTANDARD)
844                return (POLLNVAL);
845
846        return (events & (POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM));
847}
848
849#ifndef __rtems__
850int
851sys_pselect(struct thread *td, struct pselect_args *uap)
852{
853        struct timespec ts;
854        struct timeval tv, *tvp;
855        sigset_t set, *uset;
856        int error;
857
858        if (uap->ts != NULL) {
859                error = copyin(uap->ts, &ts, sizeof(ts));
860                if (error != 0)
861                    return (error);
862                TIMESPEC_TO_TIMEVAL(&tv, &ts);
863                tvp = &tv;
864        } else
865                tvp = NULL;
866        if (uap->sm != NULL) {
867                error = copyin(uap->sm, &set, sizeof(set));
868                if (error != 0)
869                        return (error);
870                uset = &set;
871        } else
872                uset = NULL;
873        return (kern_pselect(td, uap->nd, uap->in, uap->ou, uap->ex, tvp,
874            uset, NFDBITS));
875}
876
877int
878kern_pselect(struct thread *td, int nd, fd_set *in, fd_set *ou, fd_set *ex,
879    struct timeval *tvp, sigset_t *uset, int abi_nfdbits)
880{
881        int error;
882
883        if (uset != NULL) {
884                error = kern_sigprocmask(td, SIG_SETMASK, uset,
885                    &td->td_oldsigmask, 0);
886                if (error != 0)
887                        return (error);
888                td->td_pflags |= TDP_OLDMASK;
889                /*
890                 * Make sure that ast() is called on return to
891                 * usermode and TDP_OLDMASK is cleared, restoring old
892                 * sigmask.
893                 */
894                thread_lock(td);
895                td->td_flags |= TDF_ASTPENDING;
896                thread_unlock(td);
897        }
898        error = kern_select(td, nd, in, ou, ex, tvp, abi_nfdbits);
899        return (error);
900}
901
902#ifndef _SYS_SYSPROTO_H_
903struct select_args {
904        int     nd;
905        fd_set  *in, *ou, *ex;
906        struct  timeval *tv;
907};
908#endif
909int
910sys_select(struct thread *td, struct select_args *uap)
911{
912        struct timeval tv, *tvp;
913        int error;
914
915        if (uap->tv != NULL) {
916                error = copyin(uap->tv, &tv, sizeof(tv));
917                if (error)
918                        return (error);
919                tvp = &tv;
920        } else
921                tvp = NULL;
922
923        return (kern_select(td, uap->nd, uap->in, uap->ou, uap->ex, tvp,
924            NFDBITS));
925}
926#endif /* __rtems__ */
927
928/*
929 * In the unlikely case when user specified n greater then the last
930 * open file descriptor, check that no bits are set after the last
931 * valid fd.  We must return EBADF if any is set.
932 *
933 * There are applications that rely on the behaviour.
934 *
935 * nd is fd_lastfile + 1.
936 */
937static int
938select_check_badfd(fd_set *fd_in, int nd, int ndu, int abi_nfdbits)
939{
940        char *addr, *oaddr;
941        int b, i, res;
942        uint8_t bits;
943
944        if (nd >= ndu || fd_in == NULL)
945                return (0);
946
947        oaddr = NULL;
948        bits = 0; /* silence gcc */
949        for (i = nd; i < ndu; i++) {
950                b = i / NBBY;
951#if BYTE_ORDER == LITTLE_ENDIAN
952                addr = (char *)fd_in + b;
953#else
954                addr = (char *)fd_in;
955                if (abi_nfdbits == NFDBITS) {
956                        addr += rounddown(b, sizeof(fd_mask)) +
957                            sizeof(fd_mask) - 1 - b % sizeof(fd_mask);
958                } else {
959                        addr += rounddown(b, sizeof(uint32_t)) +
960                            sizeof(uint32_t) - 1 - b % sizeof(uint32_t);
961                }
962#endif
963                if (addr != oaddr) {
964                        res = fubyte(addr);
965                        if (res == -1)
966                                return (EFAULT);
967                        oaddr = addr;
968                        bits = res;
969                }
970                if ((bits & (1 << (i % NBBY))) != 0)
971                        return (EBADF);
972        }
973        return (0);
974}
975
976int
977kern_select(struct thread *td, int nd, fd_set *fd_in, fd_set *fd_ou,
978    fd_set *fd_ex, struct timeval *tvp, int abi_nfdbits)
979{
980        struct filedesc *fdp;
981        /*
982         * The magic 2048 here is chosen to be just enough for FD_SETSIZE
983         * infds with the new FD_SETSIZE of 1024, and more than enough for
984         * FD_SETSIZE infds, outfds and exceptfds with the old FD_SETSIZE
985         * of 256.
986         */
987        fd_mask s_selbits[howmany(2048, NFDBITS)];
988        fd_mask *ibits[3], *obits[3], *selbits, *sbp;
989        struct timeval rtv;
990        sbintime_t asbt, precision, rsbt;
991        u_int nbufbytes, ncpbytes, ncpubytes, nfdbits;
992        int error, lf, ndu;
993
994        if (nd < 0)
995                return (EINVAL);
996#ifndef __rtems__
997        fdp = td->td_proc->p_fd;
998#endif /* __rtems__ */
999        ndu = nd;
1000#ifndef __rtems__
1001        lf = fdp->fd_lastfile;
1002#else /* __rtems__ */
1003        (void) fdp;
1004        lf = rtems_libio_number_iops;
1005#endif /* __rtems__ */
1006        if (nd > lf + 1)
1007                nd = lf + 1;
1008
1009        error = select_check_badfd(fd_in, nd, ndu, abi_nfdbits);
1010        if (error != 0)
1011                return (error);
1012        error = select_check_badfd(fd_ou, nd, ndu, abi_nfdbits);
1013        if (error != 0)
1014                return (error);
1015        error = select_check_badfd(fd_ex, nd, ndu, abi_nfdbits);
1016        if (error != 0)
1017                return (error);
1018
1019        /*
1020         * Allocate just enough bits for the non-null fd_sets.  Use the
1021         * preallocated auto buffer if possible.
1022         */
1023        nfdbits = roundup(nd, NFDBITS);
1024        ncpbytes = nfdbits / NBBY;
1025        ncpubytes = roundup(nd, abi_nfdbits) / NBBY;
1026        nbufbytes = 0;
1027        if (fd_in != NULL)
1028                nbufbytes += 2 * ncpbytes;
1029        if (fd_ou != NULL)
1030                nbufbytes += 2 * ncpbytes;
1031        if (fd_ex != NULL)
1032                nbufbytes += 2 * ncpbytes;
1033        if (nbufbytes <= sizeof s_selbits)
1034                selbits = &s_selbits[0];
1035        else
1036                selbits = malloc(nbufbytes, M_SELECT, M_WAITOK);
1037
1038        /*
1039         * Assign pointers into the bit buffers and fetch the input bits.
1040         * Put the output buffers together so that they can be bzeroed
1041         * together.
1042         */
1043        sbp = selbits;
1044#define getbits(name, x) \
1045        do {                                                            \
1046                if (name == NULL) {                                     \
1047                        ibits[x] = NULL;                                \
1048                        obits[x] = NULL;                                \
1049                } else {                                                \
1050                        ibits[x] = sbp + nbufbytes / 2 / sizeof *sbp;   \
1051                        obits[x] = sbp;                                 \
1052                        sbp += ncpbytes / sizeof *sbp;                  \
1053                        error = copyin(name, ibits[x], ncpubytes);      \
1054                        if (error != 0)                                 \
1055                                goto done;                              \
1056                        if (ncpbytes != ncpubytes)                      \
1057                                bzero((char *)ibits[x] + ncpubytes,     \
1058                                    ncpbytes - ncpubytes);              \
1059                }                                                       \
1060        } while (0)
1061        getbits(fd_in, 0);
1062        getbits(fd_ou, 1);
1063        getbits(fd_ex, 2);
1064#undef  getbits
1065
1066#if BYTE_ORDER == BIG_ENDIAN && defined(__LP64__)
1067        /*
1068         * XXX: swizzle_fdset assumes that if abi_nfdbits != NFDBITS,
1069         * we are running under 32-bit emulation. This should be more
1070         * generic.
1071         */
1072#define swizzle_fdset(bits)                                             \
1073        if (abi_nfdbits != NFDBITS && bits != NULL) {                   \
1074                int i;                                                  \
1075                for (i = 0; i < ncpbytes / sizeof *sbp; i++)            \
1076                        bits[i] = (bits[i] >> 32) | (bits[i] << 32);    \
1077        }
1078#else
1079#define swizzle_fdset(bits)
1080#endif
1081
1082        /* Make sure the bit order makes it through an ABI transition */
1083        swizzle_fdset(ibits[0]);
1084        swizzle_fdset(ibits[1]);
1085        swizzle_fdset(ibits[2]);
1086       
1087        if (nbufbytes != 0)
1088                bzero(selbits, nbufbytes / 2);
1089
1090        precision = 0;
1091        if (tvp != NULL) {
1092                rtv = *tvp;
1093                if (rtv.tv_sec < 0 || rtv.tv_usec < 0 ||
1094                    rtv.tv_usec >= 1000000) {
1095                        error = EINVAL;
1096                        goto done;
1097                }
1098                if (!timevalisset(&rtv))
1099                        asbt = 0;
1100                else if (rtv.tv_sec <= INT32_MAX) {
1101                        rsbt = tvtosbt(rtv);
1102                        precision = rsbt;
1103                        precision >>= tc_precexp;
1104                        if (TIMESEL(&asbt, rsbt))
1105                                asbt += tc_tick_sbt;
1106                        if (asbt <= SBT_MAX - rsbt)
1107                                asbt += rsbt;
1108                        else
1109                                asbt = -1;
1110                } else
1111                        asbt = -1;
1112        } else
1113                asbt = -1;
1114        seltdinit(td);
1115        /* Iterate until the timeout expires or descriptors become ready. */
1116        for (;;) {
1117                error = selscan(td, ibits, obits, nd);
1118                if (error || td->td_retval[0] != 0)
1119                        break;
1120                error = seltdwait(td, asbt, precision);
1121                if (error)
1122                        break;
1123                error = selrescan(td, ibits, obits);
1124                if (error || td->td_retval[0] != 0)
1125                        break;
1126        }
1127        seltdclear(td);
1128
1129done:
1130        /* select is not restarted after signals... */
1131        if (error == ERESTART)
1132                error = EINTR;
1133        if (error == EWOULDBLOCK)
1134                error = 0;
1135
1136        /* swizzle bit order back, if necessary */
1137        swizzle_fdset(obits[0]);
1138        swizzle_fdset(obits[1]);
1139        swizzle_fdset(obits[2]);
1140#undef swizzle_fdset
1141
1142#define putbits(name, x) \
1143        if (name && (error2 = copyout(obits[x], name, ncpubytes))) \
1144                error = error2;
1145        if (error == 0) {
1146                int error2;
1147
1148                putbits(fd_in, 0);
1149                putbits(fd_ou, 1);
1150                putbits(fd_ex, 2);
1151#undef putbits
1152        }
1153        if (selbits != &s_selbits[0])
1154                free(selbits, M_SELECT);
1155
1156        return (error);
1157}
1158#ifdef __rtems__
1159int
1160select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *errorfds,
1161    struct timeval *timeout)
1162{
1163        struct thread *td = rtems_bsd_get_curthread_or_null();
1164        int error;
1165
1166        if (td != NULL) {
1167                error = kern_select(td, nfds, readfds, writefds, errorfds,
1168                    timeout, NFDBITS);
1169        } else {
1170                error = ENOMEM;
1171        }
1172
1173        if (error == 0) {
1174                return td->td_retval[0];
1175        } else {
1176                rtems_set_errno_and_return_minus_one(error);
1177        }
1178}
1179#endif /* __rtems__ */
1180
1181/*
1182 * Convert a select bit set to poll flags.
1183 *
1184 * The backend always returns POLLHUP/POLLERR if appropriate and we
1185 * return this as a set bit in any set.
1186 */
1187static int select_flags[3] = {
1188    POLLRDNORM | POLLHUP | POLLERR,
1189    POLLWRNORM | POLLHUP | POLLERR,
1190    POLLRDBAND | POLLERR
1191};
1192
1193/*
1194 * Compute the fo_poll flags required for a fd given by the index and
1195 * bit position in the fd_mask array.
1196 */
1197static __inline int
1198selflags(fd_mask **ibits, int idx, fd_mask bit)
1199{
1200        int flags;
1201        int msk;
1202
1203        flags = 0;
1204        for (msk = 0; msk < 3; msk++) {
1205                if (ibits[msk] == NULL)
1206                        continue;
1207                if ((ibits[msk][idx] & bit) == 0)
1208                        continue;
1209                flags |= select_flags[msk];
1210        }
1211        return (flags);
1212}
1213
1214/*
1215 * Set the appropriate output bits given a mask of fired events and the
1216 * input bits originally requested.
1217 */
1218static __inline int
1219selsetbits(fd_mask **ibits, fd_mask **obits, int idx, fd_mask bit, int events)
1220{
1221        int msk;
1222        int n;
1223
1224        n = 0;
1225        for (msk = 0; msk < 3; msk++) {
1226                if ((events & select_flags[msk]) == 0)
1227                        continue;
1228                if (ibits[msk] == NULL)
1229                        continue;
1230                if ((ibits[msk][idx] & bit) == 0)
1231                        continue;
1232                /*
1233                 * XXX Check for a duplicate set.  This can occur because a
1234                 * socket calls selrecord() twice for each poll() call
1235                 * resulting in two selfds per real fd.  selrescan() will
1236                 * call selsetbits twice as a result.
1237                 */
1238                if ((obits[msk][idx] & bit) != 0)
1239                        continue;
1240                obits[msk][idx] |= bit;
1241                n++;
1242        }
1243
1244        return (n);
1245}
1246
1247static __inline int
1248getselfd_cap(struct filedesc *fdp, int fd, struct file **fpp)
1249{
1250
1251        return (fget_unlocked(fdp, fd, &cap_event_rights, fpp, NULL));
1252}
1253
1254/*
1255 * Traverse the list of fds attached to this thread's seltd and check for
1256 * completion.
1257 */
1258static int
1259selrescan(struct thread *td, fd_mask **ibits, fd_mask **obits)
1260{
1261        struct filedesc *fdp;
1262        struct selinfo *si;
1263        struct seltd *stp;
1264        struct selfd *sfp;
1265        struct selfd *sfn;
1266        struct file *fp;
1267        fd_mask bit;
1268        int fd, ev, n, idx;
1269        int error;
1270
1271#ifndef __rtems__
1272        fdp = td->td_proc->p_fd;
1273#else /* __rtems__ */
1274        fdp = NULL;
1275#endif /* __rtems__ */
1276        stp = td->td_sel;
1277        n = 0;
1278        STAILQ_FOREACH_SAFE(sfp, &stp->st_selq, sf_link, sfn) {
1279                fd = (int)(uintptr_t)sfp->sf_cookie;
1280                si = sfp->sf_si;
1281                selfdfree(stp, sfp);
1282                /* If the selinfo wasn't cleared the event didn't fire. */
1283                if (si != NULL)
1284                        continue;
1285                error = getselfd_cap(fdp, fd, &fp);
1286                if (error)
1287                        return (error);
1288                idx = fd / NFDBITS;
1289                bit = (fd_mask)1 << (fd % NFDBITS);
1290                ev = fo_poll(fp, selflags(ibits, idx, bit), td->td_ucred, td);
1291                fdrop(fp, td);
1292                if (ev != 0)
1293                        n += selsetbits(ibits, obits, idx, bit, ev);
1294        }
1295        stp->st_flags = 0;
1296        td->td_retval[0] = n;
1297        return (0);
1298}
1299
1300/*
1301 * Perform the initial filedescriptor scan and register ourselves with
1302 * each selinfo.
1303 */
1304static int
1305selscan(struct thread *td, fd_mask **ibits, fd_mask **obits, int nfd)
1306{
1307        struct filedesc *fdp;
1308        struct file *fp;
1309        fd_mask bit;
1310        int ev, flags, end, fd;
1311        int n, idx;
1312        int error;
1313
1314#ifndef __rtems__
1315        fdp = td->td_proc->p_fd;
1316#else /* __rtems__ */
1317        fdp = NULL;
1318#endif /* __rtems__ */
1319        n = 0;
1320        for (idx = 0, fd = 0; fd < nfd; idx++) {
1321                end = imin(fd + NFDBITS, nfd);
1322                for (bit = 1; fd < end; bit <<= 1, fd++) {
1323                        /* Compute the list of events we're interested in. */
1324                        flags = selflags(ibits, idx, bit);
1325                        if (flags == 0)
1326                                continue;
1327                        error = getselfd_cap(fdp, fd, &fp);
1328                        if (error)
1329                                return (error);
1330                        selfdalloc(td, (void *)(uintptr_t)fd);
1331                        ev = fo_poll(fp, flags, td->td_ucred, td);
1332                        fdrop(fp, td);
1333                        if (ev != 0)
1334                                n += selsetbits(ibits, obits, idx, bit, ev);
1335                }
1336        }
1337
1338        td->td_retval[0] = n;
1339        return (0);
1340}
1341
1342#ifdef __rtems__
1343static int kern_poll(struct thread *td, struct pollfd *fds, u_int nfds,
1344    struct timespec *tsp, sigset_t *uset);
1345
1346static
1347#endif /* __rtems__ */
1348int
1349sys_poll(struct thread *td, struct poll_args *uap)
1350{
1351        struct timespec ts, *tsp;
1352
1353        if (uap->timeout != INFTIM) {
1354                if (uap->timeout < 0)
1355                        return (EINVAL);
1356                ts.tv_sec = uap->timeout / 1000;
1357                ts.tv_nsec = (uap->timeout % 1000) * 1000000;
1358                tsp = &ts;
1359        } else
1360                tsp = NULL;
1361
1362        return (kern_poll(td, uap->fds, uap->nfds, tsp, NULL));
1363}
1364
1365int
1366kern_poll(struct thread *td, struct pollfd *fds, u_int nfds,
1367    struct timespec *tsp, sigset_t *uset)
1368{
1369        struct pollfd *bits;
1370        struct pollfd smallbits[32];
1371        sbintime_t sbt, precision, tmp;
1372        time_t over;
1373        struct timespec ts;
1374        int error;
1375        size_t ni;
1376
1377        precision = 0;
1378        if (tsp != NULL) {
1379                if (tsp->tv_sec < 0)
1380                        return (EINVAL);
1381                if (tsp->tv_nsec < 0 || tsp->tv_nsec >= 1000000000)
1382                        return (EINVAL);
1383                if (tsp->tv_sec == 0 && tsp->tv_nsec == 0)
1384                        sbt = 0;
1385                else {
1386                        ts = *tsp;
1387                        if (ts.tv_sec > INT32_MAX / 2) {
1388                                over = ts.tv_sec - INT32_MAX / 2;
1389                                ts.tv_sec -= over;
1390                        } else
1391                                over = 0;
1392                        tmp = tstosbt(ts);
1393                        precision = tmp;
1394                        precision >>= tc_precexp;
1395                        if (TIMESEL(&sbt, tmp))
1396                                sbt += tc_tick_sbt;
1397                        sbt += tmp;
1398                }
1399        } else
1400                sbt = -1;
1401
1402#ifndef __rtems__
1403        if (nfds > maxfilesperproc && nfds > FD_SETSIZE) 
1404#else /* __rtems__ */
1405        if (nfds > rtems_libio_number_iops)
1406#endif /* __rtems__ */
1407                return (EINVAL);
1408        ni = nfds * sizeof(struct pollfd);
1409        if (ni > sizeof(smallbits))
1410                bits = malloc(ni, M_TEMP, M_WAITOK);
1411        else
1412                bits = smallbits;
1413        error = copyin(fds, bits, ni);
1414        if (error)
1415                goto done;
1416
1417#ifndef __rtems__
1418        if (uset != NULL) {
1419                error = kern_sigprocmask(td, SIG_SETMASK, uset,
1420                    &td->td_oldsigmask, 0);
1421                if (error)
1422                        goto done;
1423                td->td_pflags |= TDP_OLDMASK;
1424                /*
1425                 * Make sure that ast() is called on return to
1426                 * usermode and TDP_OLDMASK is cleared, restoring old
1427                 * sigmask.
1428                 */
1429                thread_lock(td);
1430                td->td_flags |= TDF_ASTPENDING;
1431                thread_unlock(td);
1432        }
1433#endif /* __rtems__ */
1434
1435        seltdinit(td);
1436        /* Iterate until the timeout expires or descriptors become ready. */
1437        for (;;) {
1438                error = pollscan(td, bits, nfds);
1439                if (error || td->td_retval[0] != 0)
1440                        break;
1441                error = seltdwait(td, sbt, precision);
1442                if (error)
1443                        break;
1444                error = pollrescan(td);
1445                if (error || td->td_retval[0] != 0)
1446                        break;
1447        }
1448        seltdclear(td);
1449
1450done:
1451        /* poll is not restarted after signals... */
1452        if (error == ERESTART)
1453                error = EINTR;
1454        if (error == EWOULDBLOCK)
1455                error = 0;
1456        if (error == 0) {
1457                error = pollout(td, bits, fds, nfds);
1458                if (error)
1459                        goto out;
1460        }
1461out:
1462        if (ni > sizeof(smallbits))
1463                free(bits, M_TEMP);
1464        return (error);
1465}
1466#ifdef __rtems__
1467int
1468poll(struct pollfd fds[], nfds_t nfds, int timeout)
1469{
1470        struct thread *td = rtems_bsd_get_curthread_or_null();
1471        struct poll_args ua = {
1472                .fds = &fds[0],
1473                .nfds = nfds,
1474                .timeout = timeout
1475        };
1476        int error;
1477
1478        if (td != NULL) {
1479                error = sys_poll(td, &ua);
1480        } else {
1481                error = ENOMEM;
1482        }
1483
1484        if (error == 0) {
1485                return td->td_retval[0];
1486        } else {
1487                rtems_set_errno_and_return_minus_one(error);
1488        }
1489}
1490#endif /* __rtems__ */
1491
1492#ifndef __rtems__
1493int
1494sys_ppoll(struct thread *td, struct ppoll_args *uap)
1495{
1496        struct timespec ts, *tsp;
1497        sigset_t set, *ssp;
1498        int error;
1499
1500        if (uap->ts != NULL) {
1501                error = copyin(uap->ts, &ts, sizeof(ts));
1502                if (error)
1503                        return (error);
1504                tsp = &ts;
1505        } else
1506                tsp = NULL;
1507        if (uap->set != NULL) {
1508                error = copyin(uap->set, &set, sizeof(set));
1509                if (error)
1510                        return (error);
1511                ssp = &set;
1512        } else
1513                ssp = NULL;
1514        /*
1515         * fds is still a pointer to user space. kern_poll() will
1516         * take care of copyin that array to the kernel space.
1517         */
1518
1519        return (kern_poll(td, uap->fds, uap->nfds, tsp, ssp));
1520}
1521#endif /* __rtems__ */
1522
1523static int
1524pollrescan(struct thread *td)
1525{
1526        struct seltd *stp;
1527        struct selfd *sfp;
1528        struct selfd *sfn;
1529        struct selinfo *si;
1530        struct filedesc *fdp;
1531        struct file *fp;
1532        struct pollfd *fd;
1533        int n;
1534
1535        n = 0;
1536#ifndef __rtems__
1537        fdp = td->td_proc->p_fd;
1538#else /* __rtems__ */
1539        fdp = NULL;
1540#endif /* __rtems__ */
1541        stp = td->td_sel;
1542        FILEDESC_SLOCK(fdp);
1543        STAILQ_FOREACH_SAFE(sfp, &stp->st_selq, sf_link, sfn) {
1544                fd = (struct pollfd *)sfp->sf_cookie;
1545                si = sfp->sf_si;
1546                selfdfree(stp, sfp);
1547                /* If the selinfo wasn't cleared the event didn't fire. */
1548                if (si != NULL)
1549                        continue;
1550#ifndef __rtems__
1551                fp = fdp->fd_ofiles[fd->fd].fde_file;
1552#else /* __rtems__ */
1553                fget_unlocked(fdp, fd->fd, NULL, &fp, NULL);
1554#endif /* __rtems__ */
1555#ifdef CAPABILITIES
1556                if (fp == NULL ||
1557                    cap_check(cap_rights(fdp, fd->fd), &cap_event_rights) != 0)
1558#else
1559                if (fp == NULL)
1560#endif
1561                {
1562                        fd->revents = POLLNVAL;
1563                        n++;
1564                        continue;
1565                }
1566
1567                /*
1568                 * Note: backend also returns POLLHUP and
1569                 * POLLERR if appropriate.
1570                 */
1571                fd->revents = fo_poll(fp, fd->events, td->td_ucred, td);
1572#ifdef __rtems__
1573                rtems_libio_iop_drop(&fp->f_io);
1574#endif /* __rtems__ */
1575                if (fd->revents != 0)
1576                        n++;
1577        }
1578        FILEDESC_SUNLOCK(fdp);
1579        stp->st_flags = 0;
1580        td->td_retval[0] = n;
1581        return (0);
1582}
1583
1584
1585static int
1586pollout(struct thread *td, struct pollfd *fds, struct pollfd *ufds, u_int nfd)
1587{
1588        int error = 0;
1589        u_int i = 0;
1590        u_int n = 0;
1591
1592        for (i = 0; i < nfd; i++) {
1593                error = copyout(&fds->revents, &ufds->revents,
1594                    sizeof(ufds->revents));
1595                if (error)
1596                        return (error);
1597                if (fds->revents != 0)
1598                        n++;
1599                fds++;
1600                ufds++;
1601        }
1602        td->td_retval[0] = n;
1603        return (0);
1604}
1605
1606static int
1607pollscan(struct thread *td, struct pollfd *fds, u_int nfd)
1608{
1609#ifndef __rtems__
1610        struct filedesc *fdp = td->td_proc->p_fd;
1611#else /* __rtems__ */
1612        struct filedesc *fdp = NULL;
1613#endif /* __rtems__ */
1614        struct file *fp;
1615        int i, n = 0;
1616
1617        FILEDESC_SLOCK(fdp);
1618        for (i = 0; i < nfd; i++, fds++) {
1619#ifndef __rtems__
1620                if (fds->fd > fdp->fd_lastfile) {
1621#else /* __rtems__ */
1622                if ((uint32_t)fds->fd >= rtems_libio_number_iops) {
1623#endif /* __rtems__ */
1624                        fds->revents = POLLNVAL;
1625                        n++;
1626                } else if (fds->fd < 0) {
1627                        fds->revents = 0;
1628                } else {
1629#ifndef __rtems__
1630                        fp = fdp->fd_ofiles[fds->fd].fde_file;
1631#else /* __rtems__ */
1632                        fget_unlocked(fdp, fds->fd, NULL, &fp, NULL);
1633#endif /* __rtems__ */
1634#ifdef CAPABILITIES
1635                        if (fp == NULL ||
1636                            cap_check(cap_rights(fdp, fds->fd), &cap_event_rights) != 0)
1637#else
1638                        if (fp == NULL)
1639#endif
1640                        {
1641                                fds->revents = POLLNVAL;
1642                                n++;
1643                        } else {
1644                                /*
1645                                 * Note: backend also returns POLLHUP and
1646                                 * POLLERR if appropriate.
1647                                 */
1648                                selfdalloc(td, fds);
1649                                fds->revents = fo_poll(fp, fds->events,
1650                                    td->td_ucred, td);
1651#ifdef __rtems__
1652                                rtems_libio_iop_drop(&fp->f_io);
1653#endif /* __rtems__ */
1654                                /*
1655                                 * POSIX requires POLLOUT to be never
1656                                 * set simultaneously with POLLHUP.
1657                                 */
1658                                if ((fds->revents & POLLHUP) != 0)
1659                                        fds->revents &= ~POLLOUT;
1660
1661                                if (fds->revents != 0)
1662                                        n++;
1663                        }
1664                }
1665        }
1666        FILEDESC_SUNLOCK(fdp);
1667        td->td_retval[0] = n;
1668        return (0);
1669}
1670
1671#ifndef __rtems__
1672/*
1673 * XXX This was created specifically to support netncp and netsmb.  This
1674 * allows the caller to specify a socket to wait for events on.  It returns
1675 * 0 if any events matched and an error otherwise.  There is no way to
1676 * determine which events fired.
1677 */
1678int
1679selsocket(struct socket *so, int events, struct timeval *tvp, struct thread *td)
1680{
1681        struct timeval rtv;
1682        sbintime_t asbt, precision, rsbt;
1683        int error;
1684
1685        precision = 0;  /* stupid gcc! */
1686        if (tvp != NULL) {
1687                rtv = *tvp;
1688                if (rtv.tv_sec < 0 || rtv.tv_usec < 0 || 
1689                    rtv.tv_usec >= 1000000)
1690                        return (EINVAL);
1691                if (!timevalisset(&rtv))
1692                        asbt = 0;
1693                else if (rtv.tv_sec <= INT32_MAX) {
1694                        rsbt = tvtosbt(rtv);
1695                        precision = rsbt;
1696                        precision >>= tc_precexp;
1697                        if (TIMESEL(&asbt, rsbt))
1698                                asbt += tc_tick_sbt;
1699                        if (asbt <= SBT_MAX - rsbt)
1700                                asbt += rsbt;
1701                        else
1702                                asbt = -1;
1703                } else
1704                        asbt = -1;
1705        } else
1706                asbt = -1;
1707        seltdinit(td);
1708        /*
1709         * Iterate until the timeout expires or the socket becomes ready.
1710         */
1711        for (;;) {
1712                selfdalloc(td, NULL);
1713                error = sopoll(so, events, NULL, td);
1714                /* error here is actually the ready events. */
1715                if (error)
1716                        return (0);
1717                error = seltdwait(td, asbt, precision);
1718                if (error)
1719                        break;
1720        }
1721        seltdclear(td);
1722        /* XXX Duplicates ncp/smb behavior. */
1723        if (error == ERESTART)
1724                error = 0;
1725        return (error);
1726}
1727#endif /* __rtems__ */
1728
1729/*
1730 * Preallocate two selfds associated with 'cookie'.  Some fo_poll routines
1731 * have two select sets, one for read and another for write.
1732 */
1733static void
1734selfdalloc(struct thread *td, void *cookie)
1735{
1736        struct seltd *stp;
1737
1738        stp = td->td_sel;
1739        if (stp->st_free1 == NULL)
1740                stp->st_free1 = uma_zalloc(selfd_zone, M_WAITOK|M_ZERO);
1741        stp->st_free1->sf_td = stp;
1742        stp->st_free1->sf_cookie = cookie;
1743        if (stp->st_free2 == NULL)
1744                stp->st_free2 = uma_zalloc(selfd_zone, M_WAITOK|M_ZERO);
1745        stp->st_free2->sf_td = stp;
1746        stp->st_free2->sf_cookie = cookie;
1747}
1748
1749static void
1750selfdfree(struct seltd *stp, struct selfd *sfp)
1751{
1752        STAILQ_REMOVE(&stp->st_selq, sfp, selfd, sf_link);
1753        if (sfp->sf_si != NULL) {
1754                mtx_lock(sfp->sf_mtx);
1755                if (sfp->sf_si != NULL) {
1756                        TAILQ_REMOVE(&sfp->sf_si->si_tdlist, sfp, sf_threads);
1757                        refcount_release(&sfp->sf_refs);
1758                }
1759                mtx_unlock(sfp->sf_mtx);
1760        }
1761        if (refcount_release(&sfp->sf_refs))
1762                uma_zfree(selfd_zone, sfp);
1763}
1764
1765/* Drain the waiters tied to all the selfd belonging the specified selinfo. */
1766void
1767seldrain(struct selinfo *sip)
1768{
1769
1770        /*
1771         * This feature is already provided by doselwakeup(), thus it is
1772         * enough to go for it.
1773         * Eventually, the context, should take care to avoid races
1774         * between thread calling select()/poll() and file descriptor
1775         * detaching, but, again, the races are just the same as
1776         * selwakeup().
1777         */
1778        doselwakeup(sip, -1);
1779}
1780
1781/*
1782 * Record a select request.
1783 */
1784void
1785selrecord(struct thread *selector, struct selinfo *sip)
1786{
1787        struct selfd *sfp;
1788        struct seltd *stp;
1789        struct mtx *mtxp;
1790
1791        stp = selector->td_sel;
1792        /*
1793         * Don't record when doing a rescan.
1794         */
1795        if (stp->st_flags & SELTD_RESCAN)
1796                return;
1797        /*
1798         * Grab one of the preallocated descriptors.
1799         */
1800        sfp = NULL;
1801        if ((sfp = stp->st_free1) != NULL)
1802                stp->st_free1 = NULL;
1803        else if ((sfp = stp->st_free2) != NULL)
1804                stp->st_free2 = NULL;
1805        else
1806                panic("selrecord: No free selfd on selq");
1807        mtxp = sip->si_mtx;
1808        if (mtxp == NULL)
1809                mtxp = mtx_pool_find(mtxpool_select, sip);
1810        /*
1811         * Initialize the sfp and queue it in the thread.
1812         */
1813        sfp->sf_si = sip;
1814        sfp->sf_mtx = mtxp;
1815        refcount_init(&sfp->sf_refs, 2);
1816        STAILQ_INSERT_TAIL(&stp->st_selq, sfp, sf_link);
1817        /*
1818         * Now that we've locked the sip, check for initialization.
1819         */
1820        mtx_lock(mtxp);
1821        if (sip->si_mtx == NULL) {
1822                sip->si_mtx = mtxp;
1823                TAILQ_INIT(&sip->si_tdlist);
1824        }
1825        /*
1826         * Add this thread to the list of selfds listening on this selinfo.
1827         */
1828        TAILQ_INSERT_TAIL(&sip->si_tdlist, sfp, sf_threads);
1829        mtx_unlock(sip->si_mtx);
1830}
1831
1832/* Wake up a selecting thread. */
1833void
1834selwakeup(struct selinfo *sip)
1835{
1836        doselwakeup(sip, -1);
1837}
1838
1839/* Wake up a selecting thread, and set its priority. */
1840void
1841selwakeuppri(struct selinfo *sip, int pri)
1842{
1843        doselwakeup(sip, pri);
1844}
1845
1846/*
1847 * Do a wakeup when a selectable event occurs.
1848 */
1849static void
1850doselwakeup(struct selinfo *sip, int pri)
1851{
1852        struct selfd *sfp;
1853        struct selfd *sfn;
1854        struct seltd *stp;
1855
1856        /* If it's not initialized there can't be any waiters. */
1857        if (sip->si_mtx == NULL)
1858                return;
1859        /*
1860         * Locking the selinfo locks all selfds associated with it.
1861         */
1862        mtx_lock(sip->si_mtx);
1863        TAILQ_FOREACH_SAFE(sfp, &sip->si_tdlist, sf_threads, sfn) {
1864                /*
1865                 * Once we remove this sfp from the list and clear the
1866                 * sf_si seltdclear will know to ignore this si.
1867                 */
1868                TAILQ_REMOVE(&sip->si_tdlist, sfp, sf_threads);
1869                sfp->sf_si = NULL;
1870                stp = sfp->sf_td;
1871                mtx_lock(&stp->st_mtx);
1872                stp->st_flags |= SELTD_PENDING;
1873                cv_broadcastpri(&stp->st_wait, pri);
1874                mtx_unlock(&stp->st_mtx);
1875                if (refcount_release(&sfp->sf_refs))
1876                        uma_zfree(selfd_zone, sfp);
1877        }
1878        mtx_unlock(sip->si_mtx);
1879}
1880
1881static void
1882seltdinit(struct thread *td)
1883{
1884        struct seltd *stp;
1885
1886        if ((stp = td->td_sel) != NULL)
1887                goto out;
1888        td->td_sel = stp = malloc(sizeof(*stp), M_SELECT, M_WAITOK|M_ZERO);
1889        mtx_init(&stp->st_mtx, "sellck", NULL, MTX_DEF);
1890        cv_init(&stp->st_wait, "select");
1891out:
1892        stp->st_flags = 0;
1893        STAILQ_INIT(&stp->st_selq);
1894}
1895
1896static int
1897seltdwait(struct thread *td, sbintime_t sbt, sbintime_t precision)
1898{
1899        struct seltd *stp;
1900        int error;
1901
1902        stp = td->td_sel;
1903        /*
1904         * An event of interest may occur while we do not hold the seltd
1905         * locked so check the pending flag before we sleep.
1906         */
1907        mtx_lock(&stp->st_mtx);
1908        /*
1909         * Any further calls to selrecord will be a rescan.
1910         */
1911        stp->st_flags |= SELTD_RESCAN;
1912        if (stp->st_flags & SELTD_PENDING) {
1913                mtx_unlock(&stp->st_mtx);
1914                return (0);
1915        }
1916        if (sbt == 0)
1917                error = EWOULDBLOCK;
1918        else if (sbt != -1)
1919                error = cv_timedwait_sig_sbt(&stp->st_wait, &stp->st_mtx,
1920                    sbt, precision, C_ABSOLUTE);
1921        else
1922                error = cv_wait_sig(&stp->st_wait, &stp->st_mtx);
1923        mtx_unlock(&stp->st_mtx);
1924
1925        return (error);
1926}
1927
1928void
1929seltdfini(struct thread *td)
1930{
1931        struct seltd *stp;
1932
1933        stp = td->td_sel;
1934        if (stp == NULL)
1935                return;
1936        if (stp->st_free1)
1937                uma_zfree(selfd_zone, stp->st_free1);
1938        if (stp->st_free2)
1939                uma_zfree(selfd_zone, stp->st_free2);
1940        td->td_sel = NULL;
1941        cv_destroy(&stp->st_wait);
1942        mtx_destroy(&stp->st_mtx);
1943        free(stp, M_SELECT);
1944}
1945
1946/*
1947 * Remove the references to the thread from all of the objects we were
1948 * polling.
1949 */
1950static void
1951seltdclear(struct thread *td)
1952{
1953        struct seltd *stp;
1954        struct selfd *sfp;
1955        struct selfd *sfn;
1956
1957        stp = td->td_sel;
1958        STAILQ_FOREACH_SAFE(sfp, &stp->st_selq, sf_link, sfn)
1959                selfdfree(stp, sfp);
1960        stp->st_flags = 0;
1961}
1962
1963static void selectinit(void *);
1964SYSINIT(select, SI_SUB_SYSCALLS, SI_ORDER_ANY, selectinit, NULL);
1965static void
1966selectinit(void *dummy __unused)
1967{
1968
1969        selfd_zone = uma_zcreate("selfd", sizeof(struct selfd), NULL, NULL,
1970            NULL, NULL, UMA_ALIGN_PTR, 0);
1971        mtxpool_select = mtx_pool_create("select mtxpool", 128, MTX_DEF);
1972}
1973
1974#ifndef __rtems__
1975/*
1976 * Set up a syscall return value that follows the convention specified for
1977 * posix_* functions.
1978 */
1979int
1980kern_posix_error(struct thread *td, int error)
1981{
1982
1983        if (error <= 0)
1984                return (error);
1985        td->td_errno = error;
1986        td->td_pflags |= TDP_NERRNO;
1987        td->td_retval[0] = error;
1988        return (0);
1989}
1990#endif /* __rtems__ */
1991#ifdef __rtems__
1992#include <machine/rtems-bsd-thread.h>
1993
1994#undef ticks
1995
1996#include <rtems/score/objectimpl.h>
1997#include <rtems/score/threadimpl.h>
1998
1999#include <rtems/bsd/util.h>
2000
2001static void
2002force_select_timeout(Thread_Control *thread)
2003{
2004        struct thread *td = rtems_bsd_get_thread(thread);
2005
2006        if (td != NULL) {
2007                struct seltd *stp = td->td_sel;
2008
2009                cv_broadcastpri(&stp->st_wait, 0);
2010        }
2011}
2012
2013rtems_status_code rtems_bsd_force_select_timeout(rtems_id task_id)
2014{
2015        Thread_Control *thread;
2016        ISR_lock_Context lock_context;
2017
2018        thread = _Thread_Get(task_id, &lock_context);
2019        if (thread == NULL) {
2020#if defined(RTEMS_MULTIPROCESSING)
2021                if (_Thread_MP_Is_remote(id)) {
2022                        return (RTEMS_ILLEGAL_ON_REMOTE_OBJECT);
2023                }
2024#endif
2025
2026                return (RTEMS_INVALID_ID);
2027        }
2028
2029        _ISR_lock_ISR_enable(&lock_context);
2030        force_select_timeout(thread);
2031        return (RTEMS_SUCCESSFUL);
2032}
2033#endif /* __rtems__ */
Note: See TracBrowser for help on using the repository browser.