Remove FreeBSD file descriptors due to performance and code complexity reasons.
Update #4475. --- freebsd/sys/kern/kern_descrip.c | 58 +-- freebsd/sys/kern/kern_event.c | 121 ++--- freebsd/sys/kern/sys_generic.c | 136 ++++-- freebsd/sys/kern/uipc_socket.c | 24 + freebsd/sys/kern/uipc_syscalls.c | 16 + freebsd/sys/kern/vfs_cache.c | 2 + freebsd/sys/kern/vfs_lookup.c | 4 + freebsd/sys/kern/vfs_mount.c | 2 + freebsd/sys/kern/vfs_subr.c | 4 + freebsd/sys/kern/vfs_syscalls.c | 18 + freebsd/sys/opencrypto/cryptodev.c | 11 +- freebsd/sys/sys/file.h | 98 +++- freebsd/sys/sys/filedesc.h | 89 +++- freebsd/sys/sys/namei.h | 2 + freebsd/sys/sys/proc.h | 2 +- freebsd/sys/sys/socketvar.h | 15 +- freebsd/sys/sys/syscallsubr.h | 5 + libbsd.py | 1 + .../machine/rtems-bsd-kernel-namespace.h | 18 - .../include/machine/rtems-bsd-kernel-space.h | 5 - rtemsbsd/include/machine/rtems-bsd-libio.h | 196 +------- rtemsbsd/rtems/rtems-bsd-libio.c | 61 --- rtemsbsd/rtems/rtems-bsd-syscall-api.c | 462 ++++++++---------- rtemsbsd/rtems/rtems-kernel-fget.c | 79 +++ rtemsbsd/rtems/rtems-kernel-init.c | 7 +- 25 files changed, 713 insertions(+), 723 deletions(-) create mode 100644 rtemsbsd/rtems/rtems-kernel-fget.c diff --git a/freebsd/sys/kern/kern_descrip.c b/freebsd/sys/kern/kern_descrip.c index ddc50633..e32201c9 100644 --- a/freebsd/sys/kern/kern_descrip.c +++ b/freebsd/sys/kern/kern_descrip.c @@ -76,7 +76,7 @@ __FBSDID("$FreeBSD$"); #include <sys/syscallsubr.h> #include <sys/sysctl.h> #include <sys/sysproto.h> -#include <rtems/bsd/sys/unistd.h> +#include <sys/unistd.h> #include <sys/user.h> #include <sys/vnode.h> #ifdef KTRACE @@ -92,6 +92,7 @@ __FBSDID("$FreeBSD$"); #include <ddb/ddb.h> +#ifndef __rtems__ static MALLOC_DEFINE(M_FILEDESC, "filedesc", "Open file descriptor table"); static MALLOC_DEFINE(M_FILEDESC_TO_LEADER, "filedesc_to_leader", "file desc to leader structures"); @@ -362,7 +363,6 @@ sys_getdtablesize(struct thread *td, struct getdtablesize_args *uap) return (0); } -#ifndef __rtems__ /* * Duplicate a file descriptor to a particular value. * @@ -526,7 +526,6 @@ kern_fcntl(struct thread *td, int fd, int cmd, intptr_t arg) tmp = arg; error = kern_dup(td, FDDUP_FIXED, FDDUP_FLAG_CLOEXEC, fd, tmp); break; -#endif /* __rtems__ */ case F_GETFD: error = EBADF; @@ -551,6 +550,7 @@ kern_fcntl(struct thread *td, int fd, int cmd, intptr_t arg) } FILEDESC_XUNLOCK(fdp); break; +#endif /* __rtems__ */ case F_GETFL: error = fget_fcntl(td, fd, &cap_fcntl_rights, F_GETFL, &fp); @@ -813,6 +813,7 @@ kern_fcntl(struct thread *td, int fd, int cmd, intptr_t arg) return (error); } +#ifndef __rtems__ static int getmaxfd(struct thread *td) { @@ -820,7 +821,6 @@ getmaxfd(struct thread *td) return (min((int)lim_cur(td, RLIMIT_NOFILE), maxfilesperproc)); } -#ifndef __rtems__ /* * Common code for dup, dup2, fcntl(F_DUPFD) and fcntl(F_DUP2FD). */ @@ -1182,7 +1182,6 @@ fgetown(struct sigio **sigiop) SIGIO_UNLOCK(); return (pgid); } -#endif /* __rtems__ */ /* * Function drops the filedesc lock on return. @@ -1273,7 +1272,6 @@ kern_close(struct thread *td, int fd) return (closefp(fdp, fd, fp, td, 1)); } -#ifndef __rtems__ /* * Close open file descriptors. */ @@ -1309,7 +1307,6 @@ sys_closefrom(struct thread *td, struct closefrom_args *uap) FILEDESC_SUNLOCK(fdp); return (0); } -#endif /* __rtems__ */ #if defined(COMPAT_43) /* @@ -1436,7 +1433,6 @@ freebsd11_nfstat(struct thread *td, struct freebsd11_nfstat_args *uap) } #endif /* COMPAT_FREEBSD11 */ -#ifndef __rtems__ /* * Return pathconf information about a file descriptor. */ @@ -1493,7 +1489,6 @@ out: fdrop(fp, td); return (error); } -#endif /* __rtems__ */ /* * Initialize filecaps structure. @@ -1628,7 +1623,6 @@ static void filecaps_validate(const struct filecaps *fcaps, const char *func) { -#ifndef __rtems__ KASSERT(cap_rights_is_valid(&fcaps->fc_rights), ("%s: invalid rights", func)); KASSERT((fcaps->fc_fcntls & ~CAP_FCNTL_ALL) == 0, @@ -1642,7 +1636,6 @@ filecaps_validate(const struct filecaps *fcaps, const char *func) KASSERT(fcaps->fc_nioctls == 0 || cap_rights_is_set(&fcaps->fc_rights, CAP_IOCTL), ("%s: ioctls without CAP_IOCTL", func)); -#endif /* __rtems__ */ } static void @@ -1891,12 +1884,10 @@ falloc_noinstall(struct thread *td, struct file **resultfp) priv_check(td, PRIV_MAXFILES) != 0) || openfiles_new >= maxfiles) { atomic_subtract_int(&openfiles, 1); -#ifndef __rtems__ if (ppsratecheck(&lastfail, &curfail, 1)) { printf("kern.maxfiles limit exceeded by uid %i, (%s) " "please see tuning(7).\n", td->td_ucred->cr_ruid, td->td_proc->p_comm); } -#endif /* __rtems__ */ return (ENFILE); } fp = uma_zalloc(file_zone, M_WAITOK); @@ -2050,7 +2041,6 @@ fdshare(struct filedesc *fdp) return (fdp); } -#ifndef __rtems__ /* * Unshare a filedesc structure, if necessary by making a copy */ @@ -2404,7 +2394,6 @@ fdsetugidsafety(struct thread *td) } } } -#endif /* __rtems__ */ /* * If a specific file object occupies a specific file descriptor, close the @@ -2427,7 +2416,6 @@ fdclose(struct thread *td, struct file *fp, int idx) FILEDESC_XUNLOCK(fdp); } -#ifndef __rtems__ /* * Close any files on exec? */ @@ -2453,7 +2441,6 @@ fdcloseexec(struct thread *td) } } } -#endif /* __rtems__ */ /* * It is unsafe for set[ug]id processes to be started with file @@ -2522,7 +2509,6 @@ closef(struct file *fp, struct thread *td) */ if (fp->f_type == DTYPE_VNODE && td != NULL) { vp = fp->f_vnode; -#ifndef __rtems__ if ((td->td_proc->p_leader->p_flag & P_ADVLOCK) != 0) { lf.l_whence = SEEK_SET; lf.l_start = 0; @@ -2531,7 +2517,6 @@ closef(struct file *fp, struct thread *td) (void) VOP_ADVLOCK(vp, (caddr_t)td->td_proc->p_leader, F_UNLCK, &lf, F_POSIX); } -#endif /* __rtems__ */ fdtol = td->td_proc->p_fdtol; if (fdtol != NULL) { /* @@ -2543,10 +2528,8 @@ closef(struct file *fp, struct thread *td) for (fdtol = fdtol->fdl_next; fdtol != td->td_proc->p_fdtol; fdtol = fdtol->fdl_next) { -#ifndef __rtems__ if ((fdtol->fdl_leader->p_flag & P_ADVLOCK) == 0) -#endif /* __rtems__ */ continue; fdtol->fdl_holdcount++; FILEDESC_XUNLOCK(fdp); @@ -2746,18 +2729,6 @@ fget_unlocked(struct filedesc *fdp, int fd, cap_rights_t *needrightsp, *seqp = seq; #endif } -#ifdef __rtems__ - if (fp->f_io != NULL) { - rtems_libio_iop_hold(fp->f_io); - if (RTEMS_BSD_DESCRIP_TRACE) - printf("bsd: fb: fget_unlocked: iop=%p %d (%d) fp=%p (%d) by %p\n", - fp->f_io, fp->f_io->data0, fp->f_io->flags >> 12, - fp, fp->f_count, __builtin_return_address(0)); - } else if (RTEMS_BSD_DESCRIP_TRACE) { - printf("bsd: fb: fget_unlocked: iop=NULL -1 (0) fp=%p (%d) by %p\n", - fp, fp->f_count, __builtin_return_address(0)); - } -#endif /* __rtems__ */ return (0); } @@ -2802,13 +2773,11 @@ _fget(struct thread *td, int fd, struct file **fpp, int flags, if ((fp->f_flag & flags) == 0) error = EBADF; break; -#ifndef __rtems__ case FEXEC: if ((fp->f_flag & (FREAD | FEXEC)) == 0 || ((fp->f_flag & FWRITE) != 0)) error = EBADF; break; -#endif /* __rtems__ */ case 0: break; default: @@ -2831,7 +2800,6 @@ fget(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp) return (_fget(td, fd, fpp, 0, rightsp, NULL)); } -#ifndef __rtems__ int fget_mmap(struct thread *td, int fd, cap_rights_t *rightsp, u_char *maxprotp, struct file **fpp) @@ -2866,7 +2834,6 @@ fget_mmap(struct thread *td, int fd, cap_rights_t *rightsp, u_char *maxprotp, #endif return (error); } -#endif /* __rtems__ */ int fget_read(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp) @@ -2986,14 +2953,12 @@ fgetvp_read(struct thread *td, int fd, cap_rights_t *rightsp, struct vnode **vpp return (_fgetvp(td, fd, FREAD, rightsp, vpp)); } -#ifndef __rtems__ int fgetvp_exec(struct thread *td, int fd, cap_rights_t *rightsp, struct vnode **vpp) { return (_fgetvp(td, fd, FEXEC, rightsp, vpp)); } -#endif /* __rtems__ */ #ifdef notyet int @@ -3021,15 +2986,12 @@ _fdrop(struct file *fp, struct thread *td) error = fo_close(fp, td); atomic_subtract_int(&openfiles, 1); crfree(fp->f_cred); -#ifndef __rtems__ free(fp->f_advice, M_FADVISE); -#endif /* __rtems__ */ uma_zfree(file_zone, fp); return (error); } -#ifndef __rtems__ /* * Apply an advisory lock on a file descriptor. * @@ -3248,7 +3210,6 @@ pwd_chroot(struct thread *td, struct vnode *vp) vrele(oldvp); return (0); } -#endif /* __rtems__ */ void pwd_chdir(struct thread *td, struct vnode *vp) @@ -3273,7 +3234,6 @@ pwd_chdir(struct thread *td, struct vnode *vp) void mountcheckdirs(struct vnode *olddp, struct vnode *newdp) { -#ifndef __rtems__ struct filedesc *fdp; struct prison *pr; struct proc *p; @@ -3334,7 +3294,6 @@ mountcheckdirs(struct vnode *olddp, struct vnode *newdp) sx_sunlock(&allprison_lock); while (nrele--) vrele(olddp); -#endif /* __rtems__ */ } struct filedesc_to_leader * @@ -3362,7 +3321,6 @@ filedesc_to_leader_alloc(struct filedesc_to_leader *old, struct filedesc *fdp, s return (fdtol); } -#ifndef __rtems__ static int sysctl_kern_proc_nfds(SYSCTL_HANDLER_ARGS) { @@ -3861,7 +3819,6 @@ static SYSCTL_NODE(_kern_proc, KERN_PROC_OFILEDESC, ofiledesc, CTLFLAG_RD|CTLFLAG_MPSAFE, sysctl_kern_proc_ofiledesc, "Process ofiledesc entries"); #endif /* COMPAT_FREEBSD7 */ -#endif /* __rtems__ */ int vntype_to_kinfo(int vtype) @@ -3892,7 +3849,6 @@ vntype_to_kinfo(int vtype) return (KF_VTYPE_UNKNOWN); } -#ifndef __rtems__ static SYSCTL_NODE(_kern_proc, KERN_PROC_FILEDESC, filedesc, CTLFLAG_RD|CTLFLAG_MPSAFE, sysctl_kern_proc_filedesc, "Process filedesc entries"); @@ -3964,7 +3920,6 @@ sysctl_kern_proc_cwd(SYSCTL_HANDLER_ARGS) static SYSCTL_NODE(_kern_proc, KERN_PROC_CWD, cwd, CTLFLAG_RD|CTLFLAG_MPSAFE, sysctl_kern_proc_cwd, "Process current working directory"); -#endif /* __rtems__ */ #ifdef DDB /* @@ -4113,13 +4068,10 @@ filelistinit(void *dummy) NULL, NULL, NULL, NULL, UMA_ALIGN_PTR, 0); mtx_init(&sigio_lock, "sigio lock", NULL, MTX_DEF); } -#ifndef __rtems__ SYSINIT(select, SI_SUB_LOCK, SI_ORDER_FIRST, filelistinit, NULL); -#else /* __rtems__ */ -SYSINIT(select_sub_lock, SI_SUB_LOCK, SI_ORDER_FIRST, filelistinit, NULL); -#endif /* __rtems__ */ /*-------------------------------------------------------------------*/ +#endif /* __rtems__ */ static int badfo_readwrite(struct file *fp, struct uio *uio, struct ucred *active_cred, diff --git a/freebsd/sys/kern/kern_event.c b/freebsd/sys/kern/kern_event.c index 1c79ace8..f5682b03 100644 --- a/freebsd/sys/kern/kern_event.c +++ b/freebsd/sys/kern/kern_event.c @@ -396,12 +396,7 @@ filt_fileattach(struct knote *kn) #ifndef __rtems__ return (fo_kqfilter(kn->kn_fp, kn)); #else /* __rtems__ */ - if ((kn->kn_status & KN_FP_IS_IOP) == 0) { - return (fo_kqfilter(kn->kn_fp, kn)); - } else { - rtems_libio_t* iop = (rtems_libio_t*) kn->kn_fp; - return ((*iop->pathinfo.handlers->kqfilter_h)(iop, kn)); - } + return ((*kn->kn_fp->pathinfo.handlers->kqfilter_h)(kn->kn_fp, kn)); #endif /* __rtems__ */ } @@ -412,7 +407,7 @@ kqueue_kqfilter(struct file *fp, struct knote *kn) #ifndef __rtems__ struct kqueue *kq = kn->kn_fp->f_data; #else /* __rtems__ */ - struct kqueue *kq = rtems_bsd_libio_knote_to_kq(kn); + struct kqueue *kq = rtems_bsd_knote_to_file(kn); #endif /* __rtems__ */ if (kn->kn_filter != EVFILT_READ) @@ -431,7 +426,7 @@ filt_kqdetach(struct knote *kn) #ifndef __rtems__ struct kqueue *kq = kn->kn_fp->f_data; #else /* __rtems__ */ - struct kqueue *kq = rtems_bsd_libio_knote_to_kq(kn); + struct kqueue *kq = rtems_bsd_knote_to_file(kn); #endif /* __rtems__ */ knlist_remove(&kq->kq_sel.si_note, kn, 0); @@ -444,7 +439,7 @@ filt_kqueue(struct knote *kn, long hint) #ifndef __rtems__ struct kqueue *kq = kn->kn_fp->f_data; #else /* __rtems__ */ - struct kqueue *kq = rtems_bsd_libio_knote_to_kq(kn); + struct kqueue *kq = rtems_bsd_knote_to_file(kn); #endif /* __rtems__ */ kn->kn_data = kq->kq_count; @@ -1041,11 +1036,17 @@ kern_kqueue(struct thread *td, int flags, struct filecaps *fcaps) kq->kq_cred = crhold(cred); FILEDESC_XLOCK(fdp); +#ifndef __rtems__ TAILQ_INSERT_HEAD(&fdp->fd_kqlist, kq, kq_list); +#else /* __rtems__ */ + TAILQ_INSERT_HEAD(&fd_kqlist, kq, kq_list); +#endif /* __rtems__ */ FILEDESC_XUNLOCK(fdp); finit(fp, FREAD | FWRITE, DTYPE_KQUEUE, kq, &kqueueops); +#ifndef __rtems__ fdrop(fp, td); +#endif /* __rtems__ */ td->td_retval[0] = fd; return (0); @@ -1425,9 +1426,11 @@ kqueue_register(struct kqueue *kq, struct kevent *kev, struct thread *td, int mflag) { struct filterops *fops; +#ifndef __rtems__ struct file *fp; -#ifdef __rtems__ - rtems_libio_t* iop = NULL; +#else /* __rtems__ */ + rtems_libio_t *fp; + struct file *bsd_fp; #endif /* __rtems__ */ struct knote *kn, *tkn; struct knlist *knl; @@ -1463,22 +1466,26 @@ kqueue_register(struct kqueue *kq, struct kevent *kev, struct thread *td, findkn: if (fops->f_isfd) { KASSERT(td != NULL, ("td is NULL")); +#ifndef __rtems__ if (kev->ident > INT_MAX) error = EBADF; else -#ifndef __rtems__ error = fget(td, kev->ident, &cap_event_rights, &fp); #else /* __rtems__ */ - { - int ffd = rtems_bsd_libio_iop_hold(kev->ident, &iop); - if (ffd < 0) + if ((uint32_t)kev->ident < rtems_libio_number_iops) { + unsigned int flags; + + fp = rtems_libio_iop((int)kev->ident); + flags = rtems_libio_iop_hold(fp); + + if ((flags & LIBIO_FLAGS_OPEN) != 0) { + error = 0; + } else { + rtems_libio_iop_drop(fp); error = EBADF; - else { - if (iop == NULL) - error = fget(td, ffd, &cap_event_rights, &fp); - else - fp = NULL; } + } else { + error = EBADF; } #endif /* __rtems__ */ if (error) @@ -1486,19 +1493,13 @@ findkn: if ((kev->flags & EV_ADD) == EV_ADD && kqueue_expand(kq, fops, kev->ident, M_NOWAIT) != 0) { -#ifndef __rtems__ /* try again */ +#ifndef __rtems__ fdrop(fp, td); - fp = NULL; #else /* __rtems__ */ - if (fp != NULL) { - fdrop(fp, td); - fp = NULL; - } else if (iop != NULL) { - rtems_libio_iop_drop(iop); - iop = NULL; - } + rtems_libio_iop_drop(fp); #endif /* __rtems__ */ + fp = NULL; error = kqueue_expand(kq, fops, kev->ident, mflag); if (error) goto done; @@ -1508,7 +1509,8 @@ findkn: #ifndef __rtems__ if (fp->f_type == DTYPE_KQUEUE) { #else /* __rtems__ */ - if (fp != NULL && fp->f_type == DTYPE_KQUEUE) { + bsd_fp = rtems_bsd_iop_to_file(fp); + if (bsd_fp != NULL && bsd_fp->f_type == DTYPE_KQUEUE) { #endif /* __rtems__ */ /* * If we add some intelligence about what we are doing, @@ -1517,7 +1519,11 @@ findkn: * getting both the knlist lock and the kq lock since * they are the same thing. */ +#ifndef __rtems__ if (fp->f_data == kq) { +#else /* __rtems__ */ + if (bsd_fp->f_data == kq) { +#endif /* __rtems__ */ error = EINVAL; goto done; } @@ -1579,15 +1585,13 @@ findkn: kq->kq_state |= KQ_FLUXWAIT; msleep(kq, &kq->kq_lock, PSOCK | PDROP, "kqflxwt", 0); if (fp != NULL) { +#ifndef __rtems__ fdrop(fp, td); +#else /* __rtems__ */ + rtems_libio_iop_drop(fp); +#endif /* __rtems__ */ fp = NULL; } -#ifdef __rtems__ - if (iop != NULL) { - rtems_libio_iop_drop(iop); - iop = NULL; - } -#endif /* __rtems__ */ goto findkn; } @@ -1603,17 +1607,7 @@ findkn: error = ENOMEM; goto done; } -#ifndef __rtems__ kn->kn_fp = fp; -#else /* __rtems__ */ - if (fp != NULL) { - kn->kn_fp = fp; - kn->kn_status = 0; - } else if (iop != NULL) { - rtems_bsd_libio_iop_to_knote(kn, iop); - kn->kn_status = KN_FP_IS_IOP; - } -#endif /* __rtems__ */ kn->kn_kq = kq; kn->kn_fop = fops; /* @@ -1622,9 +1616,6 @@ findkn: */ fops = NULL; fp = NULL; -#ifdef __rtems__ - iop = NULL; -#endif /* __rtems__ */ kn->kn_sfflags = kev->fflags; kn->kn_sdata = kev->data; @@ -1633,11 +1624,7 @@ findkn: kn->kn_kevent = *kev; kn->kn_kevent.flags &= ~(EV_ADD | EV_DELETE | EV_ENABLE | EV_DISABLE | EV_FORCEONESHOT); -#ifndef __rtems__ kn->kn_status = KN_DETACHED; -#else /* __rtems__ */ - kn->kn_status |= KN_DETACHED; -#endif /* __rtems__ */ if ((kev->flags & EV_DISABLE) != 0) kn->kn_status |= KN_DISABLED; kn_enter_flux(kn); @@ -1729,10 +1716,10 @@ done: if (filedesc_unlock) FILEDESC_XUNLOCK(td->td_proc->p_fd); if (fp != NULL) +#ifndef __rtems__ fdrop(fp, td); -#ifdef __rtems__ - if (iop != NULL) - rtems_libio_iop_drop(iop); +#else /* __rtems__ */ + rtems_libio_iop_drop(fp); #endif /* __rtems__ */ knote_free(tkn); if (fops != NULL) @@ -2269,7 +2256,9 @@ static int kqueue_close(struct file *fp, struct thread *td) { struct kqueue *kq = fp->f_data; +#ifndef __rtems__ struct filedesc *fdp; +#endif /* __rtems__ */ int error; int filedesc_unlock; @@ -2277,6 +2266,7 @@ kqueue_close(struct file *fp, struct thread *td) return error; kqueue_drain(kq, td); +#ifndef __rtems__ /* * We could be called due to the knote_drop() doing fdrop(), * called from kqueue_register(). In this case the global @@ -2293,6 +2283,12 @@ kqueue_close(struct file *fp, struct thread *td) TAILQ_REMOVE(&fdp->fd_kqlist, kq, kq_list); if (filedesc_unlock) FILEDESC_XUNLOCK(fdp); +#else /* __rtems__ */ + (void)filedesc_unlock; + rtems_libio_lock(); + TAILQ_REMOVE(&fd_kqlist, kq, kq_list); + rtems_libio_unlock(); +#endif /* __rtems__ */ kqueue_destroy(kq); chgkqcnt(kq->kq_cred->cr_ruidinfo, -1, 0); @@ -2674,18 +2670,26 @@ again: /* need to reacquire lock since we have dropped it */ void knote_fdclose(struct thread *td, int fd) { +#ifndef __rtems__ struct filedesc *fdp = td->td_proc->p_fd; +#endif /* __rtems__ */ struct kqueue *kq; struct knote *kn; int influx; +#ifndef __rtems__ FILEDESC_XLOCK_ASSERT(fdp); +#endif /* __rtems__ */ /* * We shouldn't have to worry about new kevents appearing on fd * since filedesc is locked. */ +#ifndef __rtems__ TAILQ_FOREACH(kq, &fdp->fd_kqlist, kq_list) { +#else /* __rtems__ */ + TAILQ_FOREACH(kq, &fd_kqlist, kq_list) { +#endif /* __rtems__ */ KQ_LOCK(kq); again: @@ -2773,10 +2777,7 @@ knote_drop_detached(struct knote *kn, struct thread *td) #ifndef __rtems__ fdrop(kn->kn_fp, td); #else /* __rtems__ */ - if ((kn->kn_status & KN_FP_IS_IOP) == 0) - fdrop(kn->kn_fp, td); - else - rtems_libio_iop_drop((rtems_libio_t*) kn->kn_fp); + rtems_libio_iop_drop(kn->kn_fp); #endif /* __rtems__ */ kn->kn_fp = NULL; } diff --git a/freebsd/sys/kern/sys_generic.c b/freebsd/sys/kern/sys_generic.c index 827380ce..1e5351a7 100644 --- a/freebsd/sys/kern/sys_generic.c +++ b/freebsd/sys/kern/sys_generic.c @@ -805,12 +805,14 @@ kern_ioctl(struct thread *td, int fd, u_long com, caddr_t data) } switch (com) { +#ifndef __rtems__ case FIONCLEX: fdp->fd_ofiles[fd].fde_flags &= ~UF_EXCLOSE; goto out; case FIOCLEX: fdp->fd_ofiles[fd].fde_flags |= UF_EXCLOSE; goto out; +#endif /* __rtems__ */ case FIONBIO: if ((tmp = *(int *)data)) atomic_set_int(&fp->f_flag, FNONBLOCK); @@ -1236,23 +1238,73 @@ selsetbits(fd_mask **ibits, fd_mask **obits, int idx, fd_mask bit, int events) return (n); } +#ifndef __rtems__ static __inline int getselfd_cap(struct filedesc *fdp, int fd, struct file **fpp) { -#ifdef __rtems__ + + return (fget_unlocked(fdp, fd, &cap_event_rights, fpp, NULL)); +} +#else /* __rtems__ */ +static int +getselfd_cap(struct filedesc *fdp, int fd, rtems_libio_t **fpp) +{ rtems_libio_t *iop; - int ffd = rtems_bsd_libio_iop_hold(fd, &iop); - if (ffd < 0) - return EBADF; - if (iop != NULL) { - *fpp = NULL; - return 0; + unsigned int actual_flags; + + (void)fdp; + + if ((uint32_t)fd >= rtems_libio_number_iops) { + return (EBADF); } - fd = ffd; -#endif /* __rtems__ */ - return (fget_unlocked(fdp, fd, &cap_event_rights, fpp, NULL)); + iop = rtems_libio_iop(fd); + actual_flags = rtems_libio_iop_hold(iop); + + if ((actual_flags & LIBIO_FLAGS_OPEN) != LIBIO_FLAGS_OPEN) { + rtems_libio_iop_drop(iop); + return (EBADF); + } + + *fpp = iop; + return (0); +} + +static inline rtems_libio_t * +rtems_bsd_get_file_for_poll(int fd) +{ + rtems_libio_t *iop; + unsigned int actual_flags; + + if ((uint32_t)fd >= rtems_libio_number_iops) { + return (NULL); + } + + iop = rtems_libio_iop(fd); + actual_flags = rtems_libio_iop_hold(iop); + + if ((actual_flags & LIBIO_FLAGS_OPEN) != LIBIO_FLAGS_OPEN) { + rtems_libio_iop_drop(iop); + return (NULL); + } + + return (iop); +} + +static inline int +rtems_bsd_fo_poll(rtems_libio_t *iop, int events, struct ucred *active_cred, + struct thread *td) +{ + int error; + + (void)active_cred; + (void)td; + + error = ((*iop->pathinfo.handlers->poll_h)(iop, events)); + rtems_libio_iop_drop(iop); + return (error); } +#endif /* __rtems__ */ /* * Traverse the list of fds attached to this thread's seltd and check for @@ -1266,7 +1318,11 @@ selrescan(struct thread *td, fd_mask **ibits, fd_mask **obits) struct seltd *stp; struct selfd *sfp; struct selfd *sfn; +#ifndef __rtems__ struct file *fp; +#else /* __rtems__ */ + rtems_libio_t *fp; +#endif /* __rtems__ */ fd_mask bit; int fd, ev, n, idx; int error; @@ -1290,10 +1346,8 @@ selrescan(struct thread *td, fd_mask **ibits, fd_mask **obits) ev = fo_poll(fp, selflags(ibits, idx, bit), td->td_ucred, td); fdrop(fp, td); #else /* __rtems__ */ - ev = rtems_bsd_libio_fo_poll(fd, fp, selflags(ibits, idx, bit), - td->td_ucred, td); - if (fp != NULL) - fdrop(fp, td); + ev = rtems_bsd_fo_poll(fp, selflags(ibits, idx, bit), + td->td_ucred, td); #endif /* __rtems__ */ if (ev != 0) n += selsetbits(ibits, obits, idx, bit, ev); @@ -1311,7 +1365,11 @@ static int selscan(struct thread *td, fd_mask **ibits, fd_mask **obits, int nfd) { struct filedesc *fdp; +#ifndef __rtems__ struct file *fp; +#else /* __rtems__ */ + rtems_libio_t *fp; +#endif /* __rtems__ */ fd_mask bit; int ev, flags, end, fd; int n, idx; @@ -1334,11 +1392,8 @@ selscan(struct thread *td, fd_mask **ibits, fd_mask **obits, int nfd) ev = fo_poll(fp, flags, td->td_ucred, td); fdrop(fp, td); #else /* __rtems__ */ - ev = rtems_bsd_libio_fo_poll(fd, fp, - selflags(ibits, idx, bit), - td->td_ucred, td); - if (fp != NULL) - fdrop(fp, td); + ev = rtems_bsd_fo_poll(fp, flags, td->td_ucred, + td); #endif /* __rtems__ */ if (ev != 0) n += selsetbits(ibits, obits, idx, bit, ev); @@ -1507,7 +1562,11 @@ pollrescan(struct thread *td) struct selfd *sfn; struct selinfo *si; struct filedesc *fdp; +#ifndef __rtems__ struct file *fp; +#else /* __rtems__ */ + rtems_libio_t *fp; +#endif /* __rtems__ */ struct pollfd *fd; int n; @@ -1524,24 +1583,15 @@ pollrescan(struct thread *td) continue; #ifndef __rtems__ fp = fdp->fd_ofiles[fd->fd].fde_file; +#else /* __rtems__ */ + fp = rtems_bsd_get_file_for_poll(fd->fd); +#endif /* __rtems__ */ #ifdef CAPABILITIES if (fp == NULL || cap_check(cap_rights(fdp, fd->fd), &cap_event_rights) != 0) #else if (fp == NULL) #endif -#else /* __rtems__ */ - rtems_libio_t* iop; - int ffd = rtems_bsd_libio_iop_hold(fd->fd, &iop); - if (ffd >= 0) { - if (iop == NULL) { - fp = fdp->fd_ofiles[ffd].fde_file; - } else { - fp = NULL; - } - } - else -#endif /* __rtems__ */ { fd->revents = POLLNVAL; n++; @@ -1555,7 +1605,8 @@ pollrescan(struct thread *td) #ifndef __rtems__ fd->revents = fo_poll(fp, fd->events, td->td_ucred, td); #else /* __rtems__ */ - fd->revents = rtems_bsd_libio_fo_poll(ffd, fp, fd->events, td->td_ucred, td); + fd->revents = rtems_bsd_fo_poll(fp, fd->events, td->td_ucred, + td); #endif /* __rtems__ */ if (fd->revents != 0) n++; @@ -1592,7 +1643,11 @@ static int pollscan(struct thread *td, struct pollfd *fds, u_int nfd) { struct filedesc *fdp = td->td_proc->p_fd; +#ifndef __rtems__ struct file *fp; +#else /* __rtems__ */ + rtems_libio_t *fp; +#endif /* __rtems__ */ int i, n = 0; FILEDESC_SLOCK(fdp); @@ -1609,24 +1664,15 @@ pollscan(struct thread *td, struct pollfd *fds, u_int nfd) } else { #ifndef __rtems__ fp = fdp->fd_ofiles[fds->fd].fde_file; +#else /* __rtems__ */ + fp = rtems_bsd_get_file_for_poll(fds->fd); +#endif /* __rtems__ */ #ifdef CAPABILITIES if (fp == NULL || cap_check(cap_rights(fdp, fds->fd), &cap_event_rights) != 0) #else if (fp == NULL) #endif -#else /* __rtems__ */ - rtems_libio_t* iop; - int ffd = rtems_bsd_libio_iop_hold(fds->fd, &iop); - if (ffd >= 0) { - if (iop == NULL) { - fp = fdp->fd_ofiles[ffd].fde_file; - } else { - fp = NULL; - } - } - if (ffd < 0) -#endif /* __rtems__ */ { fds->revents = POLLNVAL; n++; @@ -1640,7 +1686,7 @@ pollscan(struct thread *td, struct pollfd *fds, u_int nfd) fds->revents = fo_poll(fp, fds->events, td->td_ucred, td); #else /* __rtems__ */ - fds->revents = rtems_bsd_libio_fo_poll(ffd, fp, fds->events, + fds->revents = rtems_bsd_fo_poll(fp, fds->events, td->td_ucred, td); #endif /* __rtems__ */ /* diff --git a/freebsd/sys/kern/uipc_socket.c b/freebsd/sys/kern/uipc_socket.c index 60f9a69d..9c05a228 100644 --- a/freebsd/sys/kern/uipc_socket.c +++ b/freebsd/sys/kern/uipc_socket.c @@ -3384,7 +3384,11 @@ sopoll_generic(struct socket *so, int events, struct ucred *active_cred, int soo_kqfilter(struct file *fp, struct knote *kn) { +#ifndef __rtems__ struct socket *so = kn->kn_fp->f_data; +#else /* __rtems__ */ + struct socket *so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ struct sockbuf *sb; struct knlist *knl; @@ -3594,7 +3598,11 @@ pru_sopoll_notsupp(struct socket *so, int events, struct ucred *cred, static void filt_sordetach(struct knote *kn) { +#ifndef __rtems__ struct socket *so = kn->kn_fp->f_data; +#else /* __rtems__ */ + struct socket *so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ so_rdknl_lock(so); knlist_remove(&so->so_rdsel.si_note, kn, 1); @@ -3609,7 +3617,11 @@ filt_soread(struct knote *kn, long hint) { struct socket *so; +#ifndef __rtems__ so = kn->kn_fp->f_data; +#else /* __rtems__ */ + so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ if (SOLISTENING(so)) { SOCK_LOCK_ASSERT(so); @@ -3645,7 +3657,11 @@ filt_soread(struct knote *kn, long hint) static void filt_sowdetach(struct knote *kn) { +#ifndef __rtems__ struct socket *so = kn->kn_fp->f_data; +#else /* __rtems__ */ + struct socket *so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ so_wrknl_lock(so); knlist_remove(&so->so_wrsel.si_note, kn, 1); @@ -3660,7 +3676,11 @@ filt_sowrite(struct knote *kn, long hint) { struct socket *so; +#ifndef __rtems__ so = kn->kn_fp->f_data; +#else /* __rtems__ */ + so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ if (SOLISTENING(so)) return (0); @@ -3690,7 +3710,11 @@ filt_soempty(struct knote *kn, long hint) { struct socket *so; +#ifndef __rtems__ so = kn->kn_fp->f_data; +#else /* __rtems__ */ + so = rtems_bsd_knote_to_file(kn)->f_data; +#endif /* __rtems__ */ if (SOLISTENING(so)) return (1); diff --git a/freebsd/sys/kern/uipc_syscalls.c b/freebsd/sys/kern/uipc_syscalls.c index a2f7d6f8..50413091 100644 --- a/freebsd/sys/kern/uipc_syscalls.c +++ b/freebsd/sys/kern/uipc_syscalls.c @@ -113,6 +113,7 @@ getsockaddr_noalloc(struct sockaddr **namp, const struct sockaddr *uaddr, size_t #endif /* __rtems__ */ static int sockargs(struct mbuf **, char *, socklen_t, int); +#ifndef __rtems__ /* * Convert a user file descriptor to a kernel file entry and check if required * capability rights are present. @@ -140,6 +141,7 @@ getsock_cap(struct thread *td, int fd, cap_rights_t *rightsp, *fpp = fp; return (0); } +#endif /* __rtems__ */ /* * System call interface to the socket abstraction. @@ -193,7 +195,9 @@ kern_socket(struct thread *td, int domain, int type, int protocol) (void) fo_ioctl(fp, FIONBIO, &fflag, td->td_ucred, td); td->td_retval[0] = fd; } +#ifndef __rtems__ fdrop(fp, td); +#endif /* __rtems__ */ return (error); } @@ -349,7 +353,9 @@ accept1(td, s, uname, anamelen, flags) sizeof(namelen)); if (error != 0) fdclose(td, fp, td->td_retval[0]); +#ifndef __rtems__ fdrop(fp, td); +#endif /* __rtems__ */ free(name, M_SONAME); return (error); } @@ -472,8 +478,10 @@ done: } else *fp = NULL; } +#ifndef __rtems__ if (nfp != NULL) fdrop(nfp, td); +#endif /* __rtems__ */ fdrop(headfp, td); return (error); } @@ -692,15 +700,21 @@ kern_socketpair(struct thread *td, int domain, int type, int protocol, (void) fo_ioctl(fp1, FIONBIO, &fflag, td->td_ucred, td); (void) fo_ioctl(fp2, FIONBIO, &fflag, td->td_ucred, td); } +#ifndef __rtems__ fdrop(fp1, td); fdrop(fp2, td); +#endif /* __rtems__ */ return (0); free4: fdclose(td, fp2, rsv[1]); +#ifndef __rtems__ fdrop(fp2, td); +#endif /* __rtems__ */ free3: fdclose(td, fp1, rsv[0]); +#ifndef __rtems__ fdrop(fp1, td); +#endif /* __rtems__ */ free2: if (so2 != NULL) (void)soclose(so2); @@ -1712,6 +1726,7 @@ getsockaddr(struct sockaddr **namp, caddr_t uaddr, size_t len) void m_dispose_extcontrolm(struct mbuf *m) { +#ifndef __rtems__ struct cmsghdr *cm; struct file *fp; struct thread *td; @@ -1752,4 +1767,5 @@ m_dispose_extcontrolm(struct mbuf *m) } m_chtype(m, MT_CONTROL); } +#endif /* __rtems__ */ } diff --git a/freebsd/sys/kern/vfs_cache.c b/freebsd/sys/kern/vfs_cache.c index 7ae1de1d..3faf6188 100644 --- a/freebsd/sys/kern/vfs_cache.c +++ b/freebsd/sys/kern/vfs_cache.c @@ -2146,6 +2146,7 @@ static int __read_mostly disablecwd; SYSCTL_INT(_debug, OID_AUTO, disablecwd, CTLFLAG_RW, &disablecwd, 0, "Disable the getcwd syscall"); +#ifndef __rtems__ /* Implementation of the getcwd syscall. */ int sys___getcwd(struct thread *td, struct __getcwd_args *uap) @@ -2196,6 +2197,7 @@ kern___getcwd(struct thread *td, char *buf, enum uio_seg bufseg, size_t buflen, free(tmpbuf, M_TEMP); return (error); } +#endif /* __rtems__ */ /* * Thus begins the fullpath magic. diff --git a/freebsd/sys/kern/vfs_lookup.c b/freebsd/sys/kern/vfs_lookup.c index 656ec51d..83b9f713 100644 --- a/freebsd/sys/kern/vfs_lookup.c +++ b/freebsd/sys/kern/vfs_lookup.c @@ -381,7 +381,9 @@ namei(struct nameidata *ndp) FILEDESC_SLOCK(fdp); ndp->ni_rootdir = fdp->fd_rdir; vrefact(ndp->ni_rootdir); +#ifndef __rtems__ ndp->ni_topdir = fdp->fd_jdir; +#endif /* __rtems__ */ /* * If we are auditing the kernel pathname, save the user pathname. @@ -837,7 +839,9 @@ dirloop: pr = NULL; #endif /* __rtems__ */ if (dp == ndp->ni_rootdir || +#ifndef __rtems__ dp == ndp->ni_topdir || +#endif /* __rtems__ */ dp == rootvnode || pr != NULL || ((dp->v_vflag & VV_ROOT) != 0 && diff --git a/freebsd/sys/kern/vfs_mount.c b/freebsd/sys/kern/vfs_mount.c index 4635857e..2e122a98 100644 --- a/freebsd/sys/kern/vfs_mount.c +++ b/freebsd/sys/kern/vfs_mount.c @@ -950,7 +950,9 @@ vfs_domount_first( VOP_UNLOCK(vp, 0); EVENTHANDLER_DIRECT_INVOKE(vfs_mounted, mp, newdp, td); VOP_UNLOCK(newdp, 0); +#ifndef __rtems__ mountcheckdirs(vp, newdp); +#endif /* __rtems__ */ vrele(newdp); if ((mp->mnt_flag & MNT_RDONLY) == 0) vfs_allocate_syncvnode(mp); diff --git a/freebsd/sys/kern/vfs_subr.c b/freebsd/sys/kern/vfs_subr.c index bc38e770..5f4d09da 100644 --- a/freebsd/sys/kern/vfs_subr.c +++ b/freebsd/sys/kern/vfs_subr.c @@ -5365,7 +5365,11 @@ filt_vfsread(struct knote *kn, long hint) return (0); VI_LOCK(vp); +#ifndef __rtems__ kn->kn_data = va.va_size - kn->kn_fp->f_offset; +#else /* __rtems__ */ + kn->kn_data = va.va_size - rtems_bsd_knote_to_file(kn)->f_offset; +#endif /* __rtems__ */ res = (kn->kn_sfflags & NOTE_FILE_POLL) != 0 || kn->kn_data != 0; VI_UNLOCK(vp); return (res); diff --git a/freebsd/sys/kern/vfs_syscalls.c b/freebsd/sys/kern/vfs_syscalls.c index 0b7e054a..7e8e29e4 100644 --- a/freebsd/sys/kern/vfs_syscalls.c +++ b/freebsd/sys/kern/vfs_syscalls.c @@ -1050,12 +1050,19 @@ sys_openat(struct thread *td, struct openat_args *uap) } int +#ifndef __rtems__ kern_openat(struct thread *td, int fd, char *path, enum uio_seg pathseg, int flags, int mode) +#else /* __rtems__ */ +kern_openat(struct thread *td, int fd, char *path, enum uio_seg pathseg, + int flags, int mode, struct file *fp) +#endif /* __rtems__ */ { struct proc *p = td->td_proc; struct filedesc *fdp = p->p_fd; +#ifndef __rtems__ struct file *fp; +#endif /* __rtems__ */ struct vnode *vp; struct nameidata nd; cap_rights_t rights; @@ -1088,9 +1095,14 @@ kern_openat(struct thread *td, int fd, char *path, enum uio_seg pathseg, * Allocate a file structure. The descriptor to reference it * is allocated and set by finstall() below. */ +#ifndef __rtems__ error = falloc_noinstall(td, &fp); if (error != 0) return (error); +#else /* __rtems__ */ + rtems_libio_iop_hold(fp->f_io); + error = 0; +#endif /* __rtems__ */ /* * An extra reference on `fp' has been held for us by * falloc_noinstall(). @@ -1164,12 +1176,15 @@ kern_openat(struct thread *td, int fd, char *path, enum uio_seg pathseg, } VOP_UNLOCK(vp, 0); +#ifndef __rtems__ if (flags & O_TRUNC) { error = fo_truncate(fp, 0, td->td_ucred, td); if (error != 0) goto bad; } +#endif /* __rtems__ */ success: +#ifndef __rtems__ /* * If we haven't already installed the FD (for dupfdopen), do so now. */ @@ -1191,6 +1206,7 @@ success: } else { filecaps_free(&nd.ni_filecaps); } +#endif /* __rtems__ */ /* * Release our private reference, leaving the one associated with @@ -4372,6 +4388,7 @@ sys_fhreadlink(struct thread *td, struct fhreadlink_args *uap) return (error); } +#ifndef __rtems__ /* * syscall for the rpc.lockd to use to translate a NFS file handle into an * open descriptor. @@ -4459,6 +4476,7 @@ bad: td->td_retval[0] = indx; return (error); } +#endif /* __rtems__ */ /* * Stat an (NFS) file handle. diff --git a/freebsd/sys/opencrypto/cryptodev.c b/freebsd/sys/opencrypto/cryptodev.c index 71872532..97459559 100644 --- a/freebsd/sys/opencrypto/cryptodev.c +++ b/freebsd/sys/opencrypto/cryptodev.c @@ -1513,17 +1513,10 @@ cryptoioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag, struct thread } /* falloc automatically provides an extra reference to 'f'. */ finit(f, FREAD | FWRITE, DTYPE_CRYPTO, fcr, &cryptofops); -#ifdef __rtems__ - fd = rtems_bsd_libio_iop_allocate_with_file(td, fd, &rtems_bsd_sysgen_nodeops); - if (fd < 0) { - fdclose(td, f, fd); - mtx_destroy(&fcr->lock); - free(fcr, M_XDATA); - return (error); - } -#endif /* __rtems__ */ *(u_int32_t *)data = fd; +#ifndef __rtems__ fdrop(f, td); +#endif /* __rtems__ */ break; case CRIOFINDDEV: error = cryptodev_find((struct crypt_find_op *)data); diff --git a/freebsd/sys/sys/file.h b/freebsd/sys/sys/file.h index d48ca0e9..68c33299 100644 --- a/freebsd/sys/sys/file.h +++ b/freebsd/sys/sys/file.h @@ -247,6 +247,7 @@ extern int maxfiles; /* kernel limit on number of open files */ extern int maxfilesperproc; /* per process limit on number of open files */ extern volatile int openfiles; /* actual number of open files */ +#ifndef __rtems__ int fget(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp); int fget_mmap(struct thread *td, int fd, cap_rights_t *rightsp, u_char *maxprotp, struct file **fpp); @@ -257,6 +258,51 @@ int fget_write(struct thread *td, int fd, cap_rights_t *rightsp, int fget_fcntl(struct thread *td, int fd, cap_rights_t *rightsp, int needfcntl, struct file **fpp); int _fdrop(struct file *fp, struct thread *td); +#else /* __rtems__ */ +int rtems_bsd_fget(int fd, struct file **fpp, int flags); + +static inline int +fget(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp) +{ + struct file *fp; + + (void)td; + (void)rightsp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN)); +} + +static inline int +fget_read(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp) +{ + struct file *fp; + + (void)td; + (void)rightsp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN | LIBIO_FLAGS_READ)); +} + +static inline int +fget_write(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp) +{ + struct file *fp; + + (void)td; + (void)rightsp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN | LIBIO_FLAGS_WRITE)); +} + +static inline int +fget_fcntl(struct thread *td, int fd, cap_rights_t *rightsp, int needfcntl, + struct file **fpp) +{ + struct file *fp; + + (void)td; + (void)needfcntl; + (void)rightsp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN)); +} +#endif /* __rtems__ */ fo_rdwr_t invfo_rdwr; fo_truncate_t invfo_truncate; @@ -274,7 +320,36 @@ fo_fill_kinfo_t vn_fill_kinfo; int vn_fill_kinfo_vnode(struct vnode *vp, struct kinfo_file *kif); #endif /* __rtems__ */ +#ifndef __rtems__ void finit(struct file *, u_int, short, void *, struct fileops *); +#else /* __rtems__ */ +static inline void +finit(struct file *fp, u_int flag, short type, void *data, struct fileops *ops) +{ + uint32_t libio_flags; + + fp->f_data = data; + fp->f_flag = flag; + fp->f_type = type; + fp->f_ops = ops; + + libio_flags = LIBIO_FLAGS_OPEN; + + if ((flag & FREAD) == FREAD) { + libio_flags |= LIBIO_FLAGS_READ; + } + + if ((flag & FWRITE) == FWRITE) { + libio_flags |= LIBIO_FLAGS_WRITE; + } + + if ((flag & FNONBLOCK) == FNONBLOCK) { + libio_flags |= LIBIO_FLAGS_NO_DELAY; + } + + rtems_libio_iop_flags_set(fp->f_io, libio_flags); +} +#endif /* __rtems__ */ int fgetvp(struct thread *td, int fd, cap_rights_t *rightsp, struct vnode **vpp); int fgetvp_exec(struct thread *td, int fd, cap_rights_t *rightsp, @@ -286,6 +361,7 @@ int fgetvp_read(struct thread *td, int fd, cap_rights_t *rightsp, int fgetvp_write(struct thread *td, int fd, cap_rights_t *rightsp, struct vnode **vpp); +#ifndef __rtems__ static __inline int _fnoop(void) { @@ -299,23 +375,19 @@ fhold(struct file *fp) return (refcount_acquire_checked(&fp->f_count)); } -#ifndef __rtems__ #define fdrop(fp, td) \ (refcount_release(&(fp)->f_count) ? _fdrop((fp), (td)) : _fnoop()) #else /* __rtems__ */ -static inline int fdrop(struct file *fp, struct thread *td) +/* + * Must not be called after falloc_caps(). The file reference counting in + * RTEMS and FreeBSD work slightly different. + */ +static inline void +fdrop(struct file *fp, struct thread *td) { - if (fp->f_io != NULL) { - if (RTEMS_BSD_DESCRIP_TRACE) - printf("bsd: fb: fdrop: iop=%p %d (%d) fp=%p (%d) by %p\n", - fp->f_io, fp->f_io->data0, fp->f_io->flags >> 12, - fp, fp->f_count, __builtin_return_address(0)); - rtems_libio_iop_drop(fp->f_io); - } else if (RTEMS_BSD_DESCRIP_TRACE) { - printf("bsd: fb: fdrop: %d %p %d by %p\n", - -1, fp, fp->f_count, __builtin_return_address(0)); - } - return (refcount_release(&(fp)->f_count) ? _fdrop((fp), (td)) : _fnoop()); + + (void)td; + rtems_libio_iop_drop(fp->f_io); } #endif /* __rtems__ */ diff --git a/freebsd/sys/sys/filedesc.h b/freebsd/sys/sys/filedesc.h index dc132677..634470fb 100644 --- a/freebsd/sys/sys/filedesc.h +++ b/freebsd/sys/sys/filedesc.h @@ -77,20 +77,26 @@ struct fdescenttbl { #define NDSLOTTYPE u_long struct filedesc { +#ifndef __rtems__ struct fdescenttbl *fd_files; /* open files table */ +#endif /* __rtems__ */ struct vnode *fd_cdir; /* current directory */ struct vnode *fd_rdir; /* root directory */ +#ifndef __rtems__ struct vnode *fd_jdir; /* jail root directory */ NDSLOTTYPE *fd_map; /* bitmap of free fds */ int fd_lastfile; /* high-water mark of fd_ofiles */ int fd_freefile; /* approx. next free file */ +#endif /* __rtems__ */ u_short fd_cmask; /* mask for file creation */ +#ifndef __rtems__ int fd_refcnt; /* thread reference count */ int fd_holdcnt; /* hold count on structure + mutex */ struct sx fd_sx; /* protects members of this struct */ struct kqlist fd_kqlist; /* list of kqueues on this filedesc */ int fd_holdleaderscount; /* block fdfree() for shared close() */ int fd_holdleaderswakeup; /* fdfree() needs wakeup */ +#endif /* __rtems__ */ }; /* @@ -102,6 +108,7 @@ struct filedesc { * * fdl_refcount and fdl_holdcount are protected by struct filedesc mtx. */ +#ifndef __rtems__ struct filedesc_to_leader { int fdl_refcount; /* references from struct proc */ int fdl_holdcount; /* temporary hold during closef */ @@ -113,6 +120,9 @@ struct filedesc_to_leader { }; #define fd_nfiles fd_files->fdt_nfiles #define fd_ofiles fd_files->fdt_ofiles +#else /* __rtems__ */ +struct filedesc_to_leader; +#endif /* __rtems__ */ /* * Per-process open flags. @@ -120,15 +130,26 @@ struct filedesc_to_leader { #define UF_EXCLOSE 0x01 /* auto-close on exec */ #ifdef _KERNEL +#ifdef __rtems__ +#include <sys/file.h> +#include <rtems/libio_.h> +#endif /* __rtems__ */ /* Lock a file descriptor table. */ #define FILEDESC_LOCK_INIT(fdp) sx_init(&(fdp)->fd_sx, "filedesc structure") #define FILEDESC_LOCK_DESTROY(fdp) sx_destroy(&(fdp)->fd_sx) #define FILEDESC_LOCK(fdp) (&(fdp)->fd_sx) +#ifndef __rtems__ #define FILEDESC_XLOCK(fdp) sx_xlock(&(fdp)->fd_sx) #define FILEDESC_XUNLOCK(fdp) sx_xunlock(&(fdp)->fd_sx) #define FILEDESC_SLOCK(fdp) sx_slock(&(fdp)->fd_sx) #define FILEDESC_SUNLOCK(fdp) sx_sunlock(&(fdp)->fd_sx) +#else /* __rtems__ */ +#define FILEDESC_XLOCK(fdp) rtems_libio_lock() +#define FILEDESC_XUNLOCK(fdp) rtems_libio_unlock() +#define FILEDESC_SLOCK(fdp) rtems_libio_lock() +#define FILEDESC_SUNLOCK(fdp) rtems_libio_unlock() +#endif /* __rtems__ */ #define FILEDESC_LOCK_ASSERT(fdp) sx_assert(&(fdp)->fd_sx, SX_LOCKED | \ SX_NOTRECURSED) @@ -154,17 +175,42 @@ enum { struct thread; -void filecaps_init(struct filecaps *fcaps); +static __inline void +filecaps_init(struct filecaps *fcaps) +{ + + bzero(fcaps, sizeof(*fcaps)); + fcaps->fc_nioctls = -1; +} bool filecaps_copy(const struct filecaps *src, struct filecaps *dst, bool locked); void filecaps_move(struct filecaps *src, struct filecaps *dst); +#ifndef __rtems__ void filecaps_free(struct filecaps *fcaps); +#else /* __rtems__ */ +#define filecaps_free(fcaps) do { } while (0) +#endif /* __rtems__ */ int closef(struct file *fp, struct thread *td); int dupfdopen(struct thread *td, struct filedesc *fdp, int dfd, int mode, int openerror, int *indxp); +#ifndef __rtems__ int falloc_caps(struct thread *td, struct file **resultfp, int *resultfd, int flags, struct filecaps *fcaps); +#else /* __rtems__ */ +int rtems_bsd_falloc(struct file **resultfp, int *resultfd); + +static inline int +falloc_caps(struct thread *td, struct file **resultfp, int *resultfd, + int flags, struct filecaps *fcaps) +{ + + (void)td; + (void)flags; + (void)fcaps; + return (rtems_bsd_falloc(resultfp, resultfd)); +} +#endif /* __rtems__ */ int falloc_noinstall(struct thread *td, struct file **resultfp); void _finstall(struct filedesc *fdp, struct file *fp, int fd, int flags, struct filecaps *fcaps); @@ -173,7 +219,20 @@ int finstall(struct thread *td, struct file *fp, int *resultfd, int flags, int fdalloc(struct thread *td, int minfd, int *result); int fdallocn(struct thread *td, int minfd, int *fds, int n); int fdcheckstd(struct thread *td); +#ifndef __rtems__ void fdclose(struct thread *td, struct file *fp, int idx); +#else /* __rtems__ */ +void rtems_bsd_fdclose(struct file *fp); + +static inline void +fdclose(struct thread *td, struct file *fp, int idx) +{ + + (void)td; + (void)idx; + rtems_bsd_fdclose(fp); +} +#endif /* __rtems__ */ void fdcloseexec(struct thread *td); void fdsetugidsafety(struct thread *td); struct filedesc *fdcopy(struct filedesc *fdp); @@ -192,6 +251,7 @@ int getvnode(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp); void mountcheckdirs(struct vnode *olddp, struct vnode *newdp); +#ifndef __rtems__ int fget_cap_locked(struct filedesc *fdp, int fd, cap_rights_t *needrightsp, struct file **fpp, struct filecaps *havecapsp); int fget_cap(struct thread *td, int fd, cap_rights_t *needrightsp, @@ -245,7 +305,32 @@ void pwd_chdir(struct thread *td, struct vnode *vp); int pwd_chroot(struct thread *td, struct vnode *vp); void pwd_ensure_dirs(void); -#ifdef __rtems__ +#else /* __rtems__ */ +static inline int +fget_cap(struct thread *td, int fd, cap_rights_t *needrightsp, + struct file **fpp, struct filecaps *havecapsp) +{ + + (void)td; + (void)needrightsp; + (void)havecapsp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN)); +} + +#define fget_cap_locked(fdp, fd, needrightsp, fpp, havecapsp) \ + fget_cap(NULL, fd, needrightsp, fpp, havecapsp) + +static inline int +rtems_bsd_fget_unlocked(int fd, struct file **fpp, seq_t *seqp) +{ + + (void)seqp; + return (rtems_bsd_fget(fd, fpp, LIBIO_FLAGS_OPEN)); +} + +#define fget_unlocked(fdp, fd, needrightsp, fpp, seqp) \ + rtems_bsd_fget_unlocked(fd, fpp, seqp) + #include <machine/rtems-bsd-libio.h> #endif /* __rtems__ */ #endif /* _KERNEL */ diff --git a/freebsd/sys/sys/namei.h b/freebsd/sys/sys/namei.h index 53814117..500024de 100644 --- a/freebsd/sys/sys/namei.h +++ b/freebsd/sys/sys/namei.h @@ -75,7 +75,9 @@ struct nameidata { */ struct vnode *ni_startdir; /* starting directory */ struct vnode *ni_rootdir; /* logical root directory */ +#ifndef __rtems__ struct vnode *ni_topdir; /* logical top directory */ +#endif /* __rtems__ */ int ni_dirfd; /* starting directory for *at functions */ int ni_lcf; /* local call flags */ /* diff --git a/freebsd/sys/sys/proc.h b/freebsd/sys/sys/proc.h index 6ac1025d..4e061de8 100644 --- a/freebsd/sys/sys/proc.h +++ b/freebsd/sys/sys/proc.h @@ -633,8 +633,8 @@ struct proc { #endif /* __rtems__ */ struct ucred *p_ucred; /* (c) Process owner's identity. */ struct filedesc *p_fd; /* (b) Open files. */ - struct filedesc_to_leader *p_fdtol; /* (b) Tracking node */ #ifndef __rtems__ + struct filedesc_to_leader *p_fdtol; /* (b) Tracking node */ struct pstats *p_stats; /* (b) Accounting/statistics (CPU). */ struct plimit *p_limit; /* (c) Resource limits. */ struct callout p_limco; /* (c) Limit callout handle */ diff --git a/freebsd/sys/sys/socketvar.h b/freebsd/sys/sys/socketvar.h index 96ba4a01..ad57730a 100644 --- a/freebsd/sys/sys/socketvar.h +++ b/freebsd/sys/sys/socketvar.h @@ -381,9 +381,22 @@ struct uio; */ #ifndef __rtems__ int getsockaddr(struct sockaddr **namp, caddr_t uaddr, size_t len); -#endif /* __rtems__ */ int getsock_cap(struct thread *td, int fd, cap_rights_t *rightsp, struct file **fpp, u_int *fflagp, struct filecaps *havecaps); +#else /* __rtems__ */ +int rtems_bsd_getsock(int fd, struct file **fpp, u_int *fflagp); + +static inline int +getsock_cap(struct thread *td, int fd, cap_rights_t *rightsp, + struct file **fpp, u_int *fflagp, struct filecaps *havecaps) +{ + + (void)td; + (void)rightsp; + (void)havecaps; + return (rtems_bsd_getsock(fd, fpp, fflagp)); +} +#endif /* __rtems__ */ void soabort(struct socket *so); int soaccept(struct socket *so, struct sockaddr **nam); void soaio_enqueue(struct task *task); diff --git a/freebsd/sys/sys/syscallsubr.h b/freebsd/sys/sys/syscallsubr.h index 677afdd6..f150d7f9 100644 --- a/freebsd/sys/sys/syscallsubr.h +++ b/freebsd/sys/sys/syscallsubr.h @@ -191,8 +191,13 @@ int kern_nanosleep(struct thread *td, struct timespec *rqt, struct timespec *rmt); int kern_ogetdirentries(struct thread *td, struct ogetdirentries_args *uap, long *ploff); +#ifndef __rtems__ int kern_openat(struct thread *td, int fd, char *path, enum uio_seg pathseg, int flags, int mode); +#else /* __rtems__ */ +int kern_openat(struct thread *td, int fd, char *path, + enum uio_seg pathseg, int flags, int mode, struct file *fp); +#endif /* __rtems__ */ int kern_pathconf(struct thread *td, char *path, enum uio_seg pathseg, int name, u_long flags, long *valuep); int kern_pipe(struct thread *td, int fildes[2], int flags, diff --git a/libbsd.py b/libbsd.py index 983f41a1..ec72b3e2 100644 --- a/libbsd.py +++ b/libbsd.py @@ -203,6 +203,7 @@ class rtems(builder.Module): 'rtems/rtems-kernel-dev.c', 'rtems/rtems-kernel-dirent.c', 'rtems/rtems-kernel-epoch.c', + 'rtems/rtems-kernel-fget.c', 'rtems/rtems-kernel-get-file.c', 'rtems/rtems-kernel-init.c', 'rtems/rtems-kernel-irqs.c', diff --git a/rtemsbsd/include/machine/rtems-bsd-kernel-namespace.h b/rtemsbsd/include/machine/rtems-bsd-kernel-namespace.h index a83334b5..dc19c7c2 100644 --- a/rtemsbsd/include/machine/rtems-bsd-kernel-namespace.h +++ b/rtemsbsd/include/machine/rtems-bsd-kernel-namespace.h @@ -1765,8 +1765,6 @@ #define eventhandler_prune_list _bsd_eventhandler_prune_list #define eventhandler_register _bsd_eventhandler_register #define extattr_check_cred _bsd_extattr_check_cred -#define falloc_caps _bsd_falloc_caps -#define falloc_noinstall _bsd_falloc_noinstall #define fb_commonioctl _bsd_fb_commonioctl #define fb_dump_adp_info _bsd_fb_dump_adp_info #define fb_dump_mode_info _bsd_fb_dump_mode_info @@ -1806,16 +1804,6 @@ #define fdt_pinctrl_configure_tree _bsd_fdt_pinctrl_configure_tree #define fdt_pinctrl_register _bsd_fdt_pinctrl_register #define fdt_regsize _bsd_fdt_regsize -#define fget _bsd_fget -#define fget_cap _bsd_fget_cap -#define fget_cap_locked _bsd_fget_cap_locked -#define fget_fcntl _bsd_fget_fcntl -#define fget_read _bsd_fget_read -#define fget_unlocked _bsd_fget_unlocked -#define fget_write _bsd_fget_write -#define fgetvp _bsd_fgetvp -#define fgetvp_read _bsd_fgetvp_read -#define fgetvp_rights _bsd_fgetvp_rights #define fha_assign _bsd_fha_assign #define fha_init _bsd_fha_init #define fha_nd_complete _bsd_fha_nd_complete @@ -1827,15 +1815,9 @@ #define fib6_free_nh_ext _bsd_fib6_free_nh_ext #define fib6_lookup_nh_basic _bsd_fib6_lookup_nh_basic #define fib6_lookup_nh_ext _bsd_fib6_lookup_nh_ext -#define filecaps_copy _bsd_filecaps_copy -#define filecaps_free _bsd_filecaps_free -#define filecaps_init _bsd_filecaps_init -#define filecaps_move _bsd_filecaps_move -#define filedesc_to_leader_alloc _bsd_filedesc_to_leader_alloc #define find_and_ref_tcp_fb _bsd_find_and_ref_tcp_fb #define find_and_ref_tcp_functions _bsd_find_and_ref_tcp_functions #define find_handler _bsd_find_handler -#define finit _bsd_finit #define finstall _bsd_finstall #define firewire_broadcastaddr _bsd_firewire_broadcastaddr #define firewire_busreset _bsd_firewire_busreset diff --git a/rtemsbsd/include/machine/rtems-bsd-kernel-space.h b/rtemsbsd/include/machine/rtems-bsd-kernel-space.h index 37bd701d..7b766538 100644 --- a/rtemsbsd/include/machine/rtems-bsd-kernel-space.h +++ b/rtemsbsd/include/machine/rtems-bsd-kernel-space.h @@ -233,11 +233,6 @@ dev_t rtems_bsd__makedev(int _M, int _m); */ #define SIGISMEMBER(set, signo) (0) -/* - * Special knote status bit to indicate the kn_fp is an iop. - */ -#define KN_FP_IS_IOP 0x10000000 - /* * Ensure that padding bytes are zeroed and that the name is NUL-terminated. */ diff --git a/rtemsbsd/include/machine/rtems-bsd-libio.h b/rtemsbsd/include/machine/rtems-bsd-libio.h index e662a9ec..3c3a8bbb 100644 --- a/rtemsbsd/include/machine/rtems-bsd-libio.h +++ b/rtemsbsd/include/machine/rtems-bsd-libio.h @@ -54,6 +54,8 @@ extern const rtems_filesystem_file_handlers_r rtems_bsd_sysgen_imfsnodeops; extern const rtems_filesystem_file_handlers_r rtems_bsd_sysgen_dirops; extern const rtems_filesystem_file_handlers_r rtems_bsd_sysgen_fileops; +int rtems_bsd_sysgen_close(rtems_libio_t *iop); + static int inline rtems_bsd_error_to_status_and_errno(int error) { if (error == 0) { @@ -63,26 +65,6 @@ static int inline rtems_bsd_error_to_status_and_errno(int error) } } -static inline uint32_t -rtems_bsd_libio_fflag_to_flags(u_int fflag) -{ - uint32_t libio_flags = 0; - - if ((fflag & FREAD) == FREAD) { - libio_flags |= LIBIO_FLAGS_READ; - } - - if ((fflag & FWRITE) == FWRITE) { - libio_flags |= LIBIO_FLAGS_WRITE; - } - - if ((fflag & FNONBLOCK) == FNONBLOCK) { - libio_flags |= LIBIO_FLAGS_NO_DELAY; - } - - return (libio_flags); -} - static inline u_int rtems_bsd_libio_flags_to_fflag(uint32_t libio_flags) { @@ -103,20 +85,6 @@ rtems_bsd_libio_flags_to_fflag(uint32_t libio_flags) return (fflag); } -static inline bool -rtems_bsd_is_libbsd_nvops(rtems_libio_t *iop) -{ - return (iop->pathinfo.handlers == &rtems_bsd_sysgen_dirops || - iop->pathinfo.handlers == &rtems_bsd_sysgen_fileops); -} - -static inline bool -rtems_bsd_is_libbsd_descriptor(rtems_libio_t *iop) -{ - return (iop->pathinfo.handlers == &rtems_bsd_sysgen_nodeops || - rtems_bsd_is_libbsd_nvops(iop)); -} - static inline rtems_libio_t * rtems_bsd_libio_loc_to_iop(const rtems_filesystem_location_info_t *loc) { @@ -151,173 +119,19 @@ rtems_bsd_libio_loc_to_vnode_dir(const rtems_filesystem_location_info_t *loc) ->node_access_2; } -static inline void -rtems_bsd_libio_iop_free(rtems_libio_t *iop) -{ - rtems_libio_free(iop); -} - -static int -rtems_bsd_libio_iop_to_descriptor(rtems_libio_t *iop) -{ - return (int)iop->data0; -} - static struct vnode * rtems_bsd_libio_iop_to_vnode(rtems_libio_t *iop) { return rtems_bsd_libio_loc_to_vnode(&iop->pathinfo); } -static int -rtems_bsd_libio_fd_to_descriptor(int fd) -{ - return rtems_bsd_libio_iop_to_descriptor(rtems_libio_iop(fd)); -} - static inline struct file * -rtems_bsd_libio_iop_to_file_hold(rtems_libio_t *iop, struct thread *td) -{ - struct file *fp; - int error = fget_unlocked(td->td_proc->p_fd, - rtems_bsd_libio_iop_to_descriptor(iop), NULL, &fp, NULL); - if (error != 0) { - fp = NULL; - } - return fp; -} - -static inline int -rtems_bsd_file_to_libio_fd(struct file *fp) -{ - return fp->f_io - rtems_libio_iops; -} - -static inline void -rtems_bsd_libio_iop_set_bsd_descriptor(rtems_libio_t *iop, int fd) -{ - iop->data0 = fd; - /* if not vnops the fstat passes a loc, need to get the iop to get the - * fp */ - if (!rtems_bsd_is_libbsd_nvops(iop)) { - iop->pathinfo.node_access = iop; - } -} - -static inline void -rtems_bsd_libio_iop_set_bsd_file(rtems_libio_t *iop, struct file *fp) -{ - fp->f_io = iop; -} - -/* - * The fd is a libio file descriptor. - * - * Return -1 if the descriptor is closed or not valid. The descriptor is not - * held. - * - * If open hold the descriptor. If the descriptor referneces a BSD - * descriptor return the BSD descriptor else return the libio descriptor. - * - * Optionally return the iop in *iopp if the descriptor if a libio descriptor - * else return NULL. - */ -static inline int -rtems_bsd_libio_iop_hold(int fd, rtems_libio_t **iopp) +rtems_bsd_knote_to_file(const struct knote *kn) { - rtems_libio_t *iop = NULL; - unsigned int flags = 0; - int ffd = -1; - if (fd < rtems_libio_number_iops) { - iop = rtems_libio_iop(fd); - flags = rtems_libio_iop_hold(iop); - if ((flags & LIBIO_FLAGS_OPEN) != 0) { - if (rtems_bsd_is_libbsd_descriptor(iop)) { - ffd = rtems_bsd_libio_iop_to_descriptor(iop); - if (iopp != NULL) { - *iopp = NULL; - } - } else { - ffd = fd; - if (iopp != NULL) { - *iopp = iop; - } - } - } else { - rtems_libio_iop_drop(iop); - } - if (RTEMS_BSD_DESCRIP_TRACE) - flags = iop->flags; - } else { - *iopp = NULL; - } - if (RTEMS_BSD_DESCRIP_TRACE) - printf("bsd: iop: hold: fd=%d ffd=%d refs=%d iop=%p by %p\n", - fd, ffd, flags >> 12, iop, __builtin_return_address(0)); - return ffd; + return (kn->kn_fp->data1); } -static inline int -rtems_bsd_libio_iop_drop(int fd) -{ - if (RTEMS_BSD_DESCRIP_TRACE) - printf("bsd: iop: drop: fd=%d refs=%d by %p\n", fd, - rtems_libio_iop(fd)->flags >> 12, - __builtin_return_address(0)); - rtems_libio_iop_drop(rtems_libio_iop(fd)); - return 0; -} - -static inline int -rtems_bsd_libio_fo_poll(int fd, struct file *fp, int events, - struct ucred *active_cred, struct thread *td) -{ - int error; - if (fp == NULL) { - rtems_libio_t *iop = rtems_libio_iop(fd); - error = (*iop->pathinfo.handlers->poll_h)(iop, events); - } else { - error = (*fp->f_ops->fo_poll)(fp, events, active_cred, td); - fd = rtems_bsd_file_to_libio_fd(fp); - } - rtems_bsd_libio_iop_drop(fd); - return error; -} - -static inline void -rtems_bsd_libio_iop_to_knote(struct knote *kn, rtems_libio_t *iop) -{ - kn->kn_fp = (struct file *)iop; -} - -static inline struct kqueue * -rtems_bsd_libio_knote_to_kq(struct knote *kn) -{ - struct kqueue *kq = kn->kn_kq; - if ((kn->kn_status & KN_FP_IS_IOP) == 0) { - if (kq != kn->kn_fp->f_data) - panic("libio kq wrong\n"); - } - return kq; -} - -/* - * Returns an iop with null file system mount or NULL is ENFILE. - */ -rtems_libio_t *rtems_bsd_libio_iop_allocate(void); - -/* - * Returns the libio descriptor or -1 if ENFILE. - */ -int rtems_bsd_libio_iop_allocate_with_file( - struct thread *td, int fd, const rtems_filesystem_file_handlers_r *ops); - -/* - * Set the BSD file descriptor in the iop. Returns 0 if successful or an error - * number, - */ -int rtems_bsd_libio_iop_set_bsd_fd(struct thread *td, int fd, - rtems_libio_t *iop, const rtems_filesystem_file_handlers_r *ops); +struct file *rtems_bsd_iop_to_file(const rtems_libio_t *iop); /* * Set the vnode in the libio location. diff --git a/rtemsbsd/rtems/rtems-bsd-libio.c b/rtemsbsd/rtems/rtems-bsd-libio.c index fba82831..59f22feb 100644 --- a/rtemsbsd/rtems/rtems-bsd-libio.c +++ b/rtemsbsd/rtems/rtems-bsd-libio.c @@ -45,67 +45,6 @@ #include <rtems/libio.h> -rtems_libio_t * -rtems_bsd_libio_iop_allocate(void) -{ - rtems_libio_t *iop = rtems_libio_allocate(); - if (iop != NULL) { - iop->pathinfo.mt_entry = &rtems_filesystem_null_mt_entry; - rtems_filesystem_location_add_to_mt_entry(&iop->pathinfo); - } - return iop; -} - -int -rtems_bsd_libio_iop_allocate_with_file( - struct thread *td, int fd, const rtems_filesystem_file_handlers_r *ops) -{ - rtems_libio_t *iop = rtems_bsd_libio_iop_allocate(); - int iofd = -1; - if (iop != NULL) { - int error = rtems_bsd_libio_iop_set_bsd_fd(td, fd, iop, ops); - /* - * The fp is held and needs to be dropped and that drops the - * iop. - */ - if (error == 0) { - rtems_libio_iop_hold(iop); - iofd = rtems_libio_iop_to_descriptor(iop); - } else { - rtems_libio_free(iop); - } - } - return iofd; -} - -int -rtems_bsd_libio_iop_set_bsd_fd(struct thread *td, int fd, rtems_libio_t *iop, - const rtems_filesystem_file_handlers_r *ops) -{ - struct filedesc *fdp = td->td_proc->p_fd; - int error; - FILEDESC_XLOCK(fdp); - if (fd < fdp->fd_nfiles) { - struct file *fp = fget_locked(fdp, fd); - if (fp != NULL) { - rtems_bsd_libio_iop_set_bsd_file(iop, fp); - rtems_libio_iop_flags_set(iop, - LIBIO_FLAGS_OPEN | - rtems_bsd_libio_fflag_to_flags(fp->f_flag)); - if (ops != NULL) - iop->pathinfo.handlers = ops; - rtems_bsd_libio_iop_set_bsd_descriptor(iop, fd); - error = 0; - } else { - error = EBADF; - } - } else { - error = EBADF; - } - FILEDESC_XUNLOCK(fdp); - return error; -} - void rtems_bsd_libio_loc_set_vnode( rtems_filesystem_location_info_t *loc, struct vnode *vp) diff --git a/rtemsbsd/rtems/rtems-bsd-syscall-api.c b/rtemsbsd/rtems/rtems-bsd-syscall-api.c index 5c45d88a..ba8a6b60 100644 --- a/rtemsbsd/rtems/rtems-bsd-syscall-api.c +++ b/rtemsbsd/rtems/rtems-bsd-syscall-api.c @@ -43,6 +43,7 @@ #include <sys/file.h> #include <sys/filedesc.h> #include <sys/proc.h> +#include <sys/socketvar.h> #include <sys/syscallsubr.h> #include <sys/sysproto.h> #include <sys/vnode.h> @@ -63,7 +64,6 @@ static int rtems_bsd_sysgen_opendir( rtems_libio_t *iop, const char *path, int oflag, mode_t mode); static int rtems_bsd_sysgen_open( rtems_libio_t *iop, const char *path, int oflag, mode_t mode); -static int rtems_bsd_sysgen_close(rtems_libio_t *iop); static ssize_t rtems_bsd_sysgen_read( rtems_libio_t *iop, void *buffer, size_t count); static ssize_t rtems_bsd_sysgen_readv( @@ -165,6 +165,98 @@ const rtems_filesystem_file_handlers_r rtems_bsd_sysgen_imfsnodeops = { .mmap_h = rtems_filesystem_default_mmap }; +int +rtems_bsd_getsock(int fd, struct file **fpp, u_int *fflagp) +{ + int error; + rtems_libio_t *iop; + unsigned int actual_flags; + struct file *fp; + + if ((uint32_t)fd >= rtems_libio_number_iops) { + error = EBADF; + goto bad; + } + + iop = rtems_libio_iop(fd); + actual_flags = rtems_libio_iop_hold(iop); + + if ((actual_flags & LIBIO_FLAGS_OPEN) != LIBIO_FLAGS_OPEN) { + error = EBADF; + goto drop; + } + + if (iop->pathinfo.handlers->close_h != rtems_bsd_sysgen_close) { + error = ENOTSOCK; + goto drop; + } + + fp = iop->data1; + + if (fp->f_type != DTYPE_SOCKET) { + error = ENOTSOCK; + goto drop; + } + + if (fflagp != NULL) + *fflagp = fp->f_flag; + *fpp = fp; + return (0); + +drop: + rtems_libio_iop_drop(iop); + +bad: + *fpp = NULL; + return (error); +} + +struct file * +rtems_bsd_iop_to_file(const rtems_libio_t *iop) +{ + + if (iop->pathinfo.handlers->close_h != rtems_bsd_sysgen_close) { + return (NULL); + } + + return (iop->data1); +} + +int +rtems_bsd_falloc(struct file **resultfp, int *resultfd) +{ + struct file *fp; + rtems_libio_t *iop; + + fp = malloc(sizeof(*fp), M_TEMP, M_ZERO | M_NOWAIT); + *resultfp = fp; + if (fp == NULL) { + return (ENOMEM); + } + + iop = rtems_libio_allocate(); + if (iop == NULL) { + return (ENFILE); + } + + fp->f_io = iop; + iop->data1 = fp; + iop->pathinfo.node_access = iop; + iop->pathinfo.handlers = &rtems_bsd_sysgen_nodeops; + iop->pathinfo.mt_entry = &rtems_filesystem_null_mt_entry; + rtems_filesystem_location_add_to_mt_entry(&iop->pathinfo); + *resultfd = rtems_libio_iop_to_descriptor(iop); + return (0); +} + +void +rtems_bsd_fdclose(struct file *fp) +{ + + rtems_libio_free(fp->f_io); + free(fp, M_TEMP); +} + int accept(int socket, struct sockaddr *__restrict address, socklen_t *__restrict address_len) @@ -181,37 +273,14 @@ accept(int socket, struct sockaddr *__restrict address, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - int ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.name = address; ua.anamelen = address_len; error = sys_accept(td, &ua); - rtems_bsd_libio_iop_drop(socket); - if (error != 0) { - return rtems_bsd_error_to_status_and_errno(error); - } - iop = rtems_bsd_libio_iop_allocate(); - afd = td->td_retval[0]; - if (iop == NULL) { - kern_close(td, afd); - return rtems_bsd_error_to_status_and_errno(ENFILE); - } - error = rtems_bsd_libio_iop_set_bsd_fd( - td, afd, iop, &rtems_bsd_sysgen_nodeops); if (error != 0) { - rtems_bsd_libio_iop_free(iop); - kern_close(td, afd); return rtems_bsd_error_to_status_and_errno(error); } - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: accept: %d (%d) => %d -> %d\n", socket, ffd, - rtems_libio_iop_to_descriptor(iop), - rtems_bsd_libio_iop_to_descriptor(iop)); - } - return rtems_libio_iop_to_descriptor(iop); + return (td->td_retval[0]); } int @@ -219,7 +288,6 @@ bind(int socket, const struct sockaddr *address, socklen_t address_len) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct bind_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: bind: %d\n", socket); @@ -227,15 +295,10 @@ bind(int socket, const struct sockaddr *address, socklen_t address_len) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd == -1) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.name = address; ua.namelen = address_len; error = sys_bind(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -244,7 +307,6 @@ connect(int socket, const struct sockaddr *address, socklen_t address_len) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct connect_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: connect: %d\n", socket); @@ -252,15 +314,10 @@ connect(int socket, const struct sockaddr *address, socklen_t address_len) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.name = address; ua.namelen = address_len; error = sys_connect(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -270,7 +327,6 @@ getpeername(int socket, struct sockaddr *__restrict address, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct getpeername_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: getpeername: %d\n", socket); @@ -278,15 +334,10 @@ getpeername(int socket, struct sockaddr *__restrict address, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.fdes = ffd; + ua.fdes = socket; ua.asa = address; ua.alen = address_len; error = sys_getpeername(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -296,7 +347,6 @@ getsockname(int socket, struct sockaddr *__restrict address, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct getsockname_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: getsockname: %d\n", socket); @@ -304,15 +354,10 @@ getsockname(int socket, struct sockaddr *__restrict address, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.fdes = ffd; + ua.fdes = socket; ua.asa = address; ua.alen = address_len; error = sys_getsockname(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -322,7 +367,6 @@ getsockopt(int socket, int level, int option_name, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct getsockopt_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: getsockopt: %d\n", socket); @@ -330,17 +374,12 @@ getsockopt(int socket, int level, int option_name, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.level = level; ua.name = option_name; ua.val = (caddr_t)option_value; ua.avalsize = option_len; error = sys_getsockopt(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -349,7 +388,6 @@ kqueue(void) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct kqueue_args ua = {}; - rtems_libio_t *iop; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: kqueue:\n"); @@ -357,28 +395,11 @@ kqueue(void) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - iop = rtems_bsd_libio_iop_allocate(); - if (iop == NULL) { - return rtems_bsd_error_to_status_and_errno(ENFILE); - } error = sys_kqueue(td, &ua); if (error != 0) { - goto out; - } - error = rtems_bsd_libio_iop_set_bsd_fd( - td, td->td_retval[0], iop, &rtems_bsd_sysgen_nodeops); - if (error == 0) { - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: kqueue: %d -> %d\n", - rtems_libio_iop_to_descriptor(iop), - rtems_bsd_libio_iop_to_descriptor(iop)); - } - return rtems_libio_iop_to_descriptor(iop); + return rtems_bsd_error_to_status_and_errno(error); } - kern_close(td, rtems_libio_iop_to_descriptor(iop)); -out: - rtems_bsd_libio_iop_free(iop); - return rtems_bsd_error_to_status_and_errno(error); + return (td->td_retval[0]); } __weak_reference(kevent, _kevent); @@ -397,18 +418,13 @@ kevent(int kq, const struct kevent *changelist, int nchanges, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(kq, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.fd = ffd; + ua.fd = kq; ua.changelist = changelist; ua.nchanges = nchanges; ua.eventlist = eventlist; ua.nevents = nevents; ua.timeout = timeout; error = sys_kevent(td, &ua); - rtems_bsd_libio_iop_drop(kq); if (error != 0) { return rtems_bsd_error_to_status_and_errno(error); } @@ -420,7 +436,6 @@ listen(int socket, int backlog) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct listen_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: listen: %d\n", socket); @@ -428,14 +443,9 @@ listen(int socket, int backlog) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.backlog = backlog; error = sys_listen(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -507,7 +517,6 @@ recvfrom(int socket, void *__restrict buffer, size_t length, int flags, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct recvfrom_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: recvfrom: %d\n", socket); @@ -515,18 +524,13 @@ recvfrom(int socket, void *__restrict buffer, size_t length, int flags, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.buf = buffer; ua.len = length; ua.flags = flags; ua.from = address; ua.fromlenaddr = address_len; error = sys_recvfrom(td, &ua); - rtems_bsd_libio_iop_drop(socket); if (error != 0) { return rtems_bsd_error_to_status_and_errno(error); } @@ -538,7 +542,6 @@ recvmsg(int socket, struct msghdr *message, int flags) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct recvmsg_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: recvmsg: %d\n", socket); @@ -546,15 +549,10 @@ recvmsg(int socket, struct msghdr *message, int flags) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.msg = message; ua.flags = flags; error = sys_recvmsg(td, &ua); - rtems_bsd_libio_iop_drop(socket); if (error != 0) { return rtems_bsd_error_to_status_and_errno(error); } @@ -591,7 +589,6 @@ sendto(int socket, const void *message, size_t length, int flags, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct sendto_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: sendto: %d\n", socket); @@ -599,18 +596,13 @@ sendto(int socket, const void *message, size_t length, int flags, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.buf = (caddr_t)message; ua.len = length; ua.flags = flags; ua.to = dest_addr; ua.tolen = dest_len; error = sys_sendto(td, &ua); - rtems_bsd_libio_iop_drop(socket); if (error != 0) { return rtems_bsd_error_to_status_and_errno(error); } @@ -622,7 +614,6 @@ sendmsg(int socket, const struct msghdr *message, int flags) { struct thread *td = rtems_bsd_get_curthread_or_null(); struct sendmsg_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: sendmsg: %d\n", socket); @@ -630,15 +621,10 @@ sendmsg(int socket, const struct msghdr *message, int flags) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.msg = message; ua.flags = flags; error = sys_sendmsg(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -648,7 +634,6 @@ setsockopt(int socket, int level, int option_name, const void *option_value, { struct thread *td = rtems_bsd_get_curthread_or_null(); struct setsockopt_args ua; - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: setsockopt: %d\n", socket); @@ -656,17 +641,12 @@ setsockopt(int socket, int level, int option_name, const void *option_value, if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - ua.s = ffd; + ua.s = socket; ua.level = level; ua.name = option_name; ua.val = __DECONST(void *, option_value); ua.valsize = option_len; error = sys_setsockopt(td, &ua); - rtems_bsd_libio_iop_drop(socket); return rtems_bsd_error_to_status_and_errno(error); } @@ -674,7 +654,6 @@ int shutdown(int socket, int how) { struct thread *td = rtems_bsd_get_curthread_or_null(); - int ffd; int error; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: shutdown: %d\n", socket); @@ -682,17 +661,8 @@ shutdown(int socket, int how) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - ffd = rtems_bsd_libio_iop_hold(socket, NULL); - if (ffd < 0) { - return rtems_bsd_error_to_status_and_errno(EBADF); - } - if (rtems_bsd_is_libbsd_descriptor(rtems_libio_iop(socket))) { - struct shutdown_args ua = { .s = ffd, .how = how }; - error = sys_shutdown(td, &ua); - } else { - error = ENOTSOCK; - } - rtems_bsd_libio_iop_drop(socket); + struct shutdown_args ua = { .s = socket, .how = how }; + error = sys_shutdown(td, &ua); return rtems_bsd_error_to_status_and_errno(error); } @@ -700,45 +670,26 @@ int socket(int domain, int type, int protocol) { struct thread *td; - rtems_libio_t *iop; struct socket_args ua; int error; td = rtems_bsd_get_curthread_or_null(); if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - iop = rtems_bsd_libio_iop_allocate(); - if (iop == NULL) { - return rtems_bsd_error_to_status_and_errno(ENFILE); - } ua.domain = domain; ua.type = type; ua.protocol = protocol; error = sys_socket(td, &ua); if (error != 0) { - rtems_bsd_libio_iop_free(iop); - return rtems_bsd_error_to_status_and_errno(error); - } - error = rtems_bsd_libio_iop_set_bsd_fd( - td, td->td_retval[0], iop, &rtems_bsd_sysgen_nodeops); - if (error != 0) { - kern_close(td, td->td_retval[0]); - rtems_bsd_libio_iop_free(iop); return rtems_bsd_error_to_status_and_errno(error); } - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: socket: %d -> %d\n", - rtems_libio_iop_to_descriptor(iop), - rtems_bsd_libio_iop_to_descriptor(iop)); - } - return rtems_libio_iop_to_descriptor(iop); + return (td->td_retval[0]); } int socketpair(int domain, int type, int protocol, int *socket_vector) { struct thread *td; - rtems_libio_t *iop[2]; struct socketpair_args ua; int error; if (RTEMS_BSD_SYSCALL_TRACE) { @@ -748,48 +699,15 @@ socketpair(int domain, int type, int protocol, int *socket_vector) if (td == NULL) { return rtems_bsd_error_to_status_and_errno(ENOMEM); } - iop[0] = rtems_bsd_libio_iop_allocate(); - if (iop[0] == NULL) { - return rtems_bsd_error_to_status_and_errno(ENFILE); - } - iop[1] = rtems_bsd_libio_iop_allocate(); - if (iop[1] == NULL) { - rtems_bsd_libio_iop_free(iop[0]); - return rtems_bsd_error_to_status_and_errno(ENFILE); - } ua.domain = domain; ua.type = type; ua.protocol = protocol; ua.rsv = socket_vector; error = sys_socketpair(td, &ua); if (error != 0) { - goto out; - } - error = rtems_bsd_libio_iop_set_bsd_fd( - td, socket_vector[0], iop[0], &rtems_bsd_sysgen_nodeops); - if (error != 0) { - goto out; - } - error = rtems_bsd_libio_iop_set_bsd_fd( - td, socket_vector[1], iop[1], &rtems_bsd_sysgen_nodeops); - if (error == 0) { - socket_vector[0] = rtems_libio_iop_to_descriptor(iop[0]); - socket_vector[1] = rtems_libio_iop_to_descriptor(iop[1]); - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: socketpair: %d -> %d, %d -> %d\n", - socket_vector[0], - rtems_bsd_libio_iop_to_descriptor(iop[0]), - socket_vector[1], - rtems_bsd_libio_iop_to_descriptor(iop[1])); - } - return 0; + return rtems_bsd_error_to_status_and_errno(error); } -out: - kern_close(td, rtems_bsd_libio_iop_to_descriptor(iop[0])); - kern_close(td, rtems_bsd_libio_iop_to_descriptor(iop[1])); - rtems_bsd_libio_iop_free(iop[0]); - rtems_bsd_libio_iop_free(iop[1]); - return rtems_bsd_error_to_status_and_errno(error); + return (0); } @@ -814,6 +732,7 @@ rtems_bsd_sysgen_open_node( int opathlen; int fd; int error; + struct vnode *vn; if (td == NULL) { if (RTEMS_BSD_SYSCALL_TRACE) { @@ -822,6 +741,18 @@ rtems_bsd_sysgen_open_node( return rtems_bsd_error_to_status_and_errno(ENOMEM); } + + fp = malloc(sizeof(*fp), M_TEMP, M_ZERO | M_NOWAIT); + if (fp == NULL) { + return rtems_bsd_error_to_status_and_errno(ENOMEM); + } + + refcount_init(&fp->f_count, 1); + fp->f_cred = crhold(td->td_ucred); + fp->f_ops = &badfileops; + fp->f_io = iop; + iop->data1 = fp; + fdp = td->td_proc->p_fd; /* @@ -890,7 +821,7 @@ rtems_bsd_sysgen_open_node( VREF(fdp->fd_cdir); error = kern_openat(td, AT_FDCWD, RTEMS_DECONST(char *, opath), - UIO_USERSPACE, oflag, mode); + UIO_USERSPACE, oflag, mode, fp); vrele(fdp->fd_cdir); @@ -907,19 +838,10 @@ rtems_bsd_sysgen_open_node( FILEDESC_XLOCK(fdp); fdp->fd_cdir = cdir; fdp->fd_rdir = rdir; - if (fd < fdp->fd_nfiles) { - struct vnode *vn; - fp = fget_locked(fdp, fd); - if (fp != NULL) { - vn = fp->f_vnode; - } else { - vn = NULL; - } - rtems_bsd_libio_loc_set_vnode(&iop->pathinfo, vn); - } + rtems_bsd_libio_loc_set_vnode(&iop->pathinfo, fp->f_vnode); FILEDESC_XUNLOCK(fdp); - rtems_bsd_libio_iop_set_bsd_fd(td, fd, iop, &rtems_bsd_sysgen_fileops); + iop->pathinfo.handlers = &rtems_bsd_sysgen_fileops; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: open: fd = %d vn=%p\n", fd, @@ -946,28 +868,42 @@ rtems_bsd_sysgen_open( int rtems_bsd_sysgen_close(rtems_libio_t *iop) { - struct thread *td = curthread; + struct thread *td; + struct file *fp; int error; - int ffd = rtems_bsd_libio_iop_to_descriptor(iop); + if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: close: %d -> %d\n", - rtems_libio_iop_to_descriptor(iop), ffd); - } - if (td != NULL) { - if (ffd >= 0) { - rtems_libio_iop_hold(iop); - error = kern_close(td, ffd); - } else { - error = EBADF; + printf("bsd: sys: close: %d\n", + rtems_libio_iop_to_descriptor(iop)); + } + + td = rtems_bsd_get_curthread_or_null(); + if (td == NULL) { + if (RTEMS_BSD_SYSCALL_TRACE) { + printf("bsd: sys: close: no curthread\n"); } - } else { - error = ENOMEM; + return (rtems_bsd_error_to_status_and_errno(ENOMEM)); } - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: close: %d: %d: %s\n", - rtems_libio_iop_to_descriptor(iop), error, strerror(error)); + + fp = iop->data1; + BSD_ASSERT(fp->f_count == 1); + error = (fo_close(fp, td)); + if (error != 0) { + if (RTEMS_BSD_SYSCALL_TRACE) { + printf("bsd: sys: close: error = %d\n", error); + } + return (rtems_bsd_error_to_status_and_errno(error)); } - return rtems_bsd_error_to_status_and_errno(error); + + if (RTEMS_BSD_SYSCALL_TRACE) { + printf("bsd: sys: close: success\n"); + } + FILEDESC_XLOCK(NULL); + knote_fdclose(td, rtems_libio_iop_to_descriptor(iop)); + FILEDESC_XUNLOCK(NULL); + crfree(fp->f_cred); + free(fp, M_TEMP); + return (0); } ssize_t @@ -975,7 +911,7 @@ rtems_bsd_sysgen_read(rtems_libio_t *iop, void *buffer, size_t count) { struct thread *td = curthread; struct vnode *vp = rtems_bsd_libio_iop_to_vnode(iop); - int fd = rtems_bsd_libio_iop_to_descriptor(iop); + int fd = rtems_libio_iop_to_descriptor(iop); int error; ssize_t size = 0; @@ -1046,7 +982,7 @@ rtems_bsd_sysgen_read(rtems_libio_t *iop, void *buffer, size_t count) .uio_rw = UIO_READ, .uio_td = td }; error = kern_readv( - td, rtems_bsd_libio_iop_to_descriptor(iop), &auio); + td, rtems_libio_iop_to_descriptor(iop), &auio); if (error == 0) size = td->td_retval[0]; } @@ -1091,7 +1027,7 @@ rtems_bsd_sysgen_readv( auio.uio_resid = total; auio.uio_segflg = UIO_USERSPACE; - error = kern_readv(td, rtems_bsd_libio_iop_to_descriptor(iop), &auio); + error = kern_readv(td, rtems_libio_iop_to_descriptor(iop), &auio); if (error != 0) return rtems_bsd_error_to_status_and_errno(error); @@ -1129,7 +1065,7 @@ rtems_bsd_sysgen_write(rtems_libio_t *iop, const void *buffer, size_t count) auio.uio_resid = count; auio.uio_segflg = UIO_USERSPACE; - error = kern_writev(td, rtems_bsd_libio_iop_to_descriptor(iop), &auio); + error = kern_writev(td, rtems_libio_iop_to_descriptor(iop), &auio); if (error != 0) return rtems_bsd_error_to_status_and_errno(error); @@ -1165,7 +1101,7 @@ rtems_bsd_sysgen_writev( auio.uio_resid = total; auio.uio_segflg = UIO_USERSPACE; - error = kern_writev(td, rtems_bsd_libio_iop_to_descriptor(iop), &auio); + error = kern_writev(td, rtems_libio_iop_to_descriptor(iop), &auio); if (error != 0) return rtems_bsd_error_to_status_and_errno(error); @@ -1191,7 +1127,7 @@ rtems_bsd_sysgen_ioctl( return rtems_bsd_error_to_status_and_errno(ENOMEM); } error = kern_ioctl( - td, rtems_bsd_libio_iop_to_descriptor(iop), com, buffer); + td, rtems_libio_iop_to_descriptor(iop), com, buffer); return rtems_bsd_error_to_status_and_errno(error); } @@ -1211,7 +1147,7 @@ rtems_bsd_sysgen_lseek(rtems_libio_t *iop, off_t offset, int whence) return rtems_bsd_error_to_status_and_errno(ENOMEM); } error = kern_lseek( - td, rtems_bsd_libio_iop_to_descriptor(iop), offset, whence); + td, rtems_libio_iop_to_descriptor(iop), offset, whence); if (error != 0) { return rtems_bsd_error_to_status_and_errno(error); } @@ -1253,9 +1189,7 @@ rtems_bsd_sysgen_fstat( { struct thread *td = curthread; rtems_libio_t *iop = rtems_bsd_libio_loc_to_iop(loc); - struct filedesc *fdp; struct file *fp = NULL; - int fd; int error; if (iop == NULL) { if (RTEMS_BSD_SYSCALL_TRACE) { @@ -1263,22 +1197,13 @@ rtems_bsd_sysgen_fstat( } return rtems_bsd_error_to_status_and_errno(ENXIO); } - fd = rtems_bsd_libio_iop_to_descriptor(iop); - if (RTEMS_BSD_SYSCALL_TRACE) { - printf("bsd: sys: fstat: %d\n", fd); - } if (td == NULL) { if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: fstat: no curthread\n"); } return rtems_bsd_error_to_status_and_errno(ENOMEM); } - fdp = td->td_proc->p_fd; - FILEDESC_XLOCK(fdp); - if (fd < fdp->fd_nfiles) { - fp = fget_locked(fdp, fd); - } - FILEDESC_XUNLOCK(fdp); + fp = rtems_bsd_iop_to_file(iop); if (fp != NULL) { error = fo_stat(fp, buf, NULL, td); } else { @@ -1293,11 +1218,9 @@ rtems_bsd_sysgen_imfsfstat( { struct thread *td = curthread; struct socket *so = rtems_bsd_libio_imfs_loc_to_so(loc); - struct filedesc *fdp; struct file *fp = NULL; - struct socket *fd_so = NULL; - int fd; int error; + int fd; if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: imfsfstat: socket=%p\n", so); } @@ -1307,17 +1230,22 @@ rtems_bsd_sysgen_imfsfstat( } return rtems_bsd_error_to_status_and_errno(ENOMEM); } - fdp = td->td_proc->p_fd; - FILEDESC_XLOCK(fdp); - for (fd = 0; fd < fdp->fd_nfiles; fd++) { - fp = fget_locked(fdp, fd); - fd_so = fp->f_data; - if (so == fd_so) { + rtems_libio_lock(); + for (fd = 0; fd < (int)rtems_libio_number_iops; ++fd) { + rtems_libio_t *iop; + + iop = rtems_libio_iop(fd); + if (iop->pathinfo.handlers == NULL) { + continue; + } + fp = rtems_bsd_iop_to_file(iop); + if (fp != NULL && fp->f_data == so) { break; } + fp = NULL; } - FILEDESC_XUNLOCK(fdp); + rtems_libio_unlock(); if (fp != NULL) { if (RTEMS_BSD_SYSCALL_TRACE) { printf("bsd: sys: imfsfstat: %d\n", fd); @@ -1344,7 +1272,7 @@ rtems_bsd_sysgen_ftruncate(rtems_libio_t *iop, off_t length) return rtems_bsd_error_to_status_and_errno(ENOMEM); } error = kern_ftruncate( - td, rtems_bsd_libio_iop_to_descriptor(iop), length); + td, rtems_libio_iop_to_descriptor(iop), length); return rtems_bsd_error_to_status_and_errno(error); } @@ -1362,7 +1290,7 @@ rtems_bsd_sysgen_fsync(rtems_libio_t *iop) } return rtems_bsd_error_to_status_and_errno(ENOMEM); } - error = kern_fsync(td, rtems_bsd_libio_iop_to_descriptor(iop), true); + error = kern_fsync(td, rtems_libio_iop_to_descriptor(iop), true); return rtems_bsd_error_to_status_and_errno(error); } @@ -1380,7 +1308,7 @@ rtems_bsd_sysgen_fdatasync(rtems_libio_t *iop) } return rtems_bsd_error_to_status_and_errno(ENOMEM); } - error = kern_fsync(td, rtems_bsd_libio_iop_to_descriptor(iop), false); + error = kern_fsync(td, rtems_libio_iop_to_descriptor(iop), false); return rtems_bsd_error_to_status_and_errno(error); } @@ -1416,7 +1344,7 @@ rtems_bsd_sysgen_fcntl(rtems_libio_t *iop, int cmd) } if (arg >= 0) { error = kern_fcntl( - td, rtems_bsd_libio_iop_to_descriptor(iop), cmd, arg); + td, rtems_libio_iop_to_descriptor(iop), cmd, arg); /* no return path with the RTEMS API for get calls */ } return rtems_bsd_error_to_status_and_errno(error); @@ -1425,13 +1353,23 @@ rtems_bsd_sysgen_fcntl(rtems_libio_t *iop, int cmd) int rtems_bsd_sysgen_poll(rtems_libio_t *iop, int events) { - printf("rtems_bsd_sysgen_poll called!\n"); - return rtems_bsd_error_to_status_and_errno(EOPNOTSUPP); + struct thread *td; + struct file *fp; + + td = rtems_bsd_get_curthread_or_null(); + if (td == NULL) { + return (ENOMEM); + } + + fp = iop->data1; + return (fo_poll(fp, events, td->td_ucred, td)); } int rtems_bsd_sysgen_kqfilter(rtems_libio_t *iop, struct knote *kn) { - printf("rtems_bsd_sysgen_kqfilter called!\n"); - return rtems_bsd_error_to_status_and_errno(EOPNOTSUPP); + struct file *fp; + + fp = iop->data1; + return (fo_kqfilter(fp, kn)); } diff --git a/rtemsbsd/rtems/rtems-kernel-fget.c b/rtemsbsd/rtems/rtems-kernel-fget.c new file mode 100644 index 00000000..e51ddb57 --- /dev/null +++ b/rtemsbsd/rtems/rtems-kernel-fget.c @@ -0,0 +1,79 @@ +/* SPDX-License-Identifier: BSD-2-Clause */ + +/** + * @file + * + * @ingroup rtems_bsd_rtems + * + * @brief TODO. + */ + +/* + * Copyright (C) 2022 embedded brains GmbH + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#include <machine/rtems-bsd-kernel-space.h> + +#include <sys/file.h> + +/* Avoid referencing the VFS only through rtems_bsd_fget() */ +__weak_symbol int +rtems_bsd_sysgen_close(rtems_libio_t *iop) +{ + + (void)iop; + return (-1); +} + +int +rtems_bsd_fget(int fd, struct file **fpp, int flags) +{ + rtems_libio_t *iop; + unsigned int actual_flags; + + if ((uint32_t)fd >= rtems_libio_number_iops) { + goto bad; + } + + iop = rtems_libio_iop(fd); + actual_flags = rtems_libio_iop_hold(iop); + + if ((actual_flags & flags) != flags) { + goto drop; + } + + if (iop->pathinfo.handlers->close_h != rtems_bsd_sysgen_close) { + goto drop; + } + + *fpp = iop->data1; + return (0); + +drop: + rtems_libio_iop_drop(iop); + +bad: + *fpp = NULL; + return (EBADF); +} diff --git a/rtemsbsd/rtems/rtems-kernel-init.c b/rtemsbsd/rtems/rtems-kernel-init.c index 90a9c809..454943b3 100644 --- a/rtemsbsd/rtems/rtems-kernel-init.c +++ b/rtemsbsd/rtems/rtems-kernel-init.c @@ -141,6 +141,10 @@ cpu_startup(void *dummy) } SYSINIT(cpu, SI_SUB_CPU, SI_ORDER_FIRST, cpu_startup, NULL); +static struct filedesc p_fd = { + .fd_cmask = CMASK +}; + /* * Create a single process. RTEMS is a single address, single process OS. */ @@ -166,8 +170,7 @@ proc0_init(void *dummy) newcred->cr_ruidinfo = uifind(0); p->p_ucred = newcred; p->p_pid = getpid(); - p->p_fd = fdinit(NULL, false); - p->p_fdtol = NULL; + p->p_fd = &p_fd; rtems_sysvec.sv_flags = SV_ABI_FREEBSD; #ifdef __LP64__ rtems_sysvec.sv_flags |= SV_LP64; -- 2.35.3 _______________________________________________ devel mailing list devel@rtems.org http://lists.rtems.org/mailman/listinfo/devel