diff options
author | phk <phk@FreeBSD.org> | 2004-11-17 09:09:55 +0000 |
---|---|---|
committer | phk <phk@FreeBSD.org> | 2004-11-17 09:09:55 +0000 |
commit | d6a49a1565bec352a92f40326206665b53769de2 (patch) | |
tree | 3e96ca6c2f3203ce32ec61d3746561cf0c4bd761 | |
parent | 313ccfcf9e23e29fc79adcefe9b9e1b52f7643ff (diff) | |
download | FreeBSD-src-d6a49a1565bec352a92f40326206665b53769de2.zip FreeBSD-src-d6a49a1565bec352a92f40326206665b53769de2.tar.gz |
Push Giant down through ioctl.
Don't grab Giant in the upper syscall/wrapper code
NET_LOCK_GIANT in the socket code (sockets/fifos).
mtx_lock(&Giant) in the vnode code.
mtx_lock(&Giant) in the opencrypto code. (This may actually not be
needed, but better safe than sorry).
Devfs grabs Giant if the driver is marked as needing Giant.
-rw-r--r-- | sys/kern/sys_generic.c | 7 | ||||
-rw-r--r-- | sys/kern/sys_socket.c | 2 | ||||
-rw-r--r-- | sys/kern/vfs_vnops.c | 70 | ||||
-rw-r--r-- | sys/opencrypto/cryptodev.c | 19 |
4 files changed, 27 insertions, 71 deletions
diff --git a/sys/kern/sys_generic.c b/sys/kern/sys_generic.c index c90ce5c..fae094c 100644 --- a/sys/kern/sys_generic.c +++ b/sys/kern/sys_generic.c @@ -474,10 +474,8 @@ ioctl(struct thread *td, struct ioctl_args *uap) if ((error = fget(td, uap->fd, &fp)) != 0) return (error); - mtx_lock(&Giant); if ((fp->f_flag & (FREAD | FWRITE)) == 0) { fdrop(fp, td); - mtx_unlock(&Giant); return (EBADF); } fdp = td->td_proc->p_fd; @@ -487,14 +485,12 @@ ioctl(struct thread *td, struct ioctl_args *uap) fdp->fd_ofileflags[uap->fd] &= ~UF_EXCLOSE; FILEDESC_UNLOCK_FAST(fdp); fdrop(fp, td); - mtx_unlock(&Giant); return (0); case FIOCLEX: FILEDESC_LOCK_FAST(fdp); fdp->fd_ofileflags[uap->fd] |= UF_EXCLOSE; FILEDESC_UNLOCK_FAST(fdp); fdrop(fp, td); - mtx_unlock(&Giant); return (0); } @@ -508,7 +504,6 @@ ioctl(struct thread *td, struct ioctl_args *uap) ((com & IOC_VOID) && size > 0) || ((com & (IOC_IN | IOC_OUT)) && size == 0)) { fdrop(fp, td); - mtx_unlock(&Giant); return (ENOTTY); } @@ -524,7 +519,6 @@ ioctl(struct thread *td, struct ioctl_args *uap) if (error) { free(memp, M_IOCTLOPS); fdrop(fp, td); - mtx_unlock(&Giant); return (error); } } else if (com & IOC_OUT) { @@ -561,7 +555,6 @@ ioctl(struct thread *td, struct ioctl_args *uap) if (memp != NULL) free(memp, M_IOCTLOPS); fdrop(fp, td); - mtx_unlock(&Giant); return (error); } diff --git a/sys/kern/sys_socket.c b/sys/kern/sys_socket.c index 4a7911d..5772262 100644 --- a/sys/kern/sys_socket.c +++ b/sys/kern/sys_socket.c @@ -129,6 +129,7 @@ soo_ioctl(fp, cmd, data, active_cred, td) struct socket *so = fp->f_data; int error = 0; + NET_LOCK_GIANT(); switch (cmd) { case FIONBIO: @@ -210,6 +211,7 @@ soo_ioctl(fp, cmd, data, active_cred, td) (so, cmd, data, 0, td)); break; } + NET_UNLOCK_GIANT(); return(error); } diff --git a/sys/kern/vfs_vnops.c b/sys/kern/vfs_vnops.c index cd5e669..c69558c 100644 --- a/sys/kern/vfs_vnops.c +++ b/sys/kern/vfs_vnops.c @@ -759,82 +759,30 @@ vn_ioctl(fp, com, data, active_cred, td) struct thread *td; { struct vnode *vp = fp->f_vnode; - struct vnode *vpold; struct vattr vattr; int error; - GIANT_REQUIRED; - + mtx_lock(&Giant); + error = ENOTTY; switch (vp->v_type) { - case VREG: case VDIR: if (com == FIONREAD) { vn_lock(vp, LK_EXCLUSIVE | LK_RETRY, td); error = VOP_GETATTR(vp, &vattr, active_cred, td); VOP_UNLOCK(vp, 0, td); - if (error) - return (error); - *(int *)data = vattr.va_size - fp->f_offset; - return (0); + if (!error) + *(int *)data = vattr.va_size - fp->f_offset; } if (com == FIONBIO || com == FIOASYNC) /* XXX */ - return (0); /* XXX */ - /* FALLTHROUGH */ + error = 0; + break; default: -#if 0 - return (ENOTTY); -#endif - case VFIFO: - case VCHR: - case VBLK: - if (com == FIODTYPE) { - dev_lock(); - if (vp->v_type != VCHR && vp->v_type != VBLK) - error = ENOTTY; - else if (vp->v_rdev == NULL) - error = ENXIO; - else if (vp->v_rdev->si_devsw == NULL) - error = ENXIO; - else { - error = 0; - *(int *)data = - vp->v_rdev->si_devsw->d_flags & D_TYPEMASK; - } - dev_unlock(); - return (error); - } - error = VOP_IOCTL(vp, com, data, fp->f_flag, active_cred, td); - if (error == ENOIOCTL) { -#ifdef DIAGNOSTIC - kdb_enter("ENOIOCTL leaked through"); -#endif - error = ENOTTY; - } - if (error == 0 && com == TIOCSCTTY) { - - /* Do nothing if reassigning same control tty */ - sx_slock(&proctree_lock); - if (td->td_proc->p_session->s_ttyvp == vp) { - sx_sunlock(&proctree_lock); - return (0); - } - - vpold = td->td_proc->p_session->s_ttyvp; - VREF(vp); - SESS_LOCK(td->td_proc->p_session); - td->td_proc->p_session->s_ttyvp = vp; - SESS_UNLOCK(td->td_proc->p_session); - - sx_sunlock(&proctree_lock); - - /* Get rid of reference to old control tty */ - if (vpold) - vrele(vpold); - } - return (error); + break; } + mtx_unlock(&Giant); + return (error); } /* diff --git a/sys/opencrypto/cryptodev.c b/sys/opencrypto/cryptodev.c index 9b0da7c..b9d26a9 100644 --- a/sys/opencrypto/cryptodev.c +++ b/sys/opencrypto/cryptodev.c @@ -147,6 +147,10 @@ cryptof_ioctl( u_int32_t ses; int error = 0; + /* + * XXX: Not sure Giant is needed, but better safe than sorry + */ + mtx_lock(&Giant); switch (cmd) { case CIOCGSESSION: sop = (struct session_op *)data; @@ -178,6 +182,7 @@ cryptof_ioctl( txform = &enc_xform_arc4; break; default: + mtx_unlock(&Giant); return (EINVAL); } @@ -197,8 +202,10 @@ cryptof_ioctl( thash = &auth_hash_hmac_sha2_384; else if (sop->mackeylen == auth_hash_hmac_sha2_512.keysize) thash = &auth_hash_hmac_sha2_512; - else + else { + mtx_unlock(&Giant); return (EINVAL); + } break; case CRYPTO_RIPEMD160_HMAC: thash = &auth_hash_hmac_ripemd_160_96; @@ -215,6 +222,7 @@ cryptof_ioctl( thash = &auth_hash_null; break; default: + mtx_unlock(&Giant); return (EINVAL); } @@ -282,16 +290,20 @@ bail: case CIOCFSESSION: ses = *(u_int32_t *)data; cse = csefind(fcr, ses); - if (cse == NULL) + if (cse == NULL) { + mtx_unlock(&Giant); return (EINVAL); + } csedelete(fcr, cse); error = csefree(cse); break; case CIOCCRYPT: cop = (struct crypt_op *)data; cse = csefind(fcr, cop->ses); - if (cse == NULL) + if (cse == NULL) { + mtx_unlock(&Giant); return (EINVAL); + } error = cryptodev_op(cse, cop, active_cred, td); break; case CIOCKEY: @@ -303,6 +315,7 @@ bail: default: error = EINVAL; } + mtx_unlock(&Giant); return (error); } |