When vnode bypass cannot be performed on the cdev file descriptor for
read/write/poll/ioctl, call standard vnode filedescriptor fop. This restores the special handling for terminals by calling the deadfs VOP, instead of always returning ENXIO for destroyed devices or revoked terminals. Since destroyed (and not revoked) device would use devfs_specops VOP vector, make dead_read/write/poll non-static and fill VOP table with pointers to the functions, to instead of VOP_PANIC. Noted and reviewed by: bde Sponsored by: The FreeBSD Foundation MFC after: 1 week
This commit is contained in:
parent
66572524ce
commit
6b880aa521
@ -43,9 +43,6 @@
|
||||
*/
|
||||
static vop_lookup_t dead_lookup;
|
||||
static vop_open_t dead_open;
|
||||
static vop_poll_t dead_poll;
|
||||
static vop_read_t dead_read;
|
||||
static vop_write_t dead_write;
|
||||
static vop_getwritemount_t dead_getwritemount;
|
||||
static vop_rename_t dead_rename;
|
||||
|
||||
@ -130,7 +127,7 @@ dead_open(ap)
|
||||
* Vnode op for read
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
static int
|
||||
int
|
||||
dead_read(ap)
|
||||
struct vop_read_args /* {
|
||||
struct vnode *a_vp;
|
||||
@ -151,7 +148,7 @@ dead_read(ap)
|
||||
* Vnode op for write
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
static int
|
||||
int
|
||||
dead_write(ap)
|
||||
struct vop_write_args /* {
|
||||
struct vnode *a_vp;
|
||||
@ -163,7 +160,7 @@ dead_write(ap)
|
||||
return (EIO);
|
||||
}
|
||||
|
||||
static int
|
||||
int
|
||||
dead_poll(ap)
|
||||
struct vop_poll_args *ap;
|
||||
{
|
||||
|
@ -737,8 +737,10 @@ devfs_ioctl_f(struct file *fp, u_long com, void *data, struct ucred *cred, struc
|
||||
|
||||
fpop = td->td_fpop;
|
||||
error = devfs_fp_check(fp, &dev, &dsw, &ref);
|
||||
if (error)
|
||||
if (error != 0) {
|
||||
error = vnops.fo_ioctl(fp, com, data, cred, td);
|
||||
return (error);
|
||||
}
|
||||
|
||||
if (com == FIODTYPE) {
|
||||
*(int *)data = dsw->d_flags & D_TYPEMASK;
|
||||
@ -1152,8 +1154,10 @@ devfs_poll_f(struct file *fp, int events, struct ucred *cred, struct thread *td)
|
||||
|
||||
fpop = td->td_fpop;
|
||||
error = devfs_fp_check(fp, &dev, &dsw, &ref);
|
||||
if (error)
|
||||
return (poll_no_poll(events));
|
||||
if (error != 0) {
|
||||
error = vnops.fo_poll(fp, events, cred, td);
|
||||
return (error);
|
||||
}
|
||||
error = dsw->d_poll(dev, events, td);
|
||||
td->td_fpop = fpop;
|
||||
dev_relthread(dev, ref);
|
||||
@ -1185,8 +1189,10 @@ devfs_read_f(struct file *fp, struct uio *uio, struct ucred *cred,
|
||||
return (EINVAL);
|
||||
fpop = td->td_fpop;
|
||||
error = devfs_fp_check(fp, &dev, &dsw, &ref);
|
||||
if (error)
|
||||
if (error != 0) {
|
||||
error = vnops.fo_read(fp, uio, cred, flags, td);
|
||||
return (error);
|
||||
}
|
||||
resid = uio->uio_resid;
|
||||
ioflag = fp->f_flag & (O_NONBLOCK | O_DIRECT);
|
||||
if (ioflag & O_DIRECT)
|
||||
@ -1660,8 +1666,10 @@ devfs_write_f(struct file *fp, struct uio *uio, struct ucred *cred,
|
||||
return (EINVAL);
|
||||
fpop = td->td_fpop;
|
||||
error = devfs_fp_check(fp, &dev, &dsw, &ref);
|
||||
if (error)
|
||||
if (error != 0) {
|
||||
error = vnops.fo_write(fp, uio, cred, flags, td);
|
||||
return (error);
|
||||
}
|
||||
KASSERT(uio->uio_td == td, ("uio_td %p is not td %p", uio->uio_td, td));
|
||||
ioflag = fp->f_flag & (O_NONBLOCK | O_DIRECT | O_FSYNC);
|
||||
if (ioflag & O_DIRECT)
|
||||
@ -1744,8 +1752,9 @@ static struct vop_vector devfs_specops = {
|
||||
.vop_mknod = VOP_PANIC,
|
||||
.vop_open = devfs_open,
|
||||
.vop_pathconf = devfs_pathconf,
|
||||
.vop_poll = dead_poll,
|
||||
.vop_print = devfs_print,
|
||||
.vop_read = VOP_PANIC,
|
||||
.vop_read = dead_read,
|
||||
.vop_readdir = VOP_PANIC,
|
||||
.vop_readlink = VOP_PANIC,
|
||||
.vop_reallocblks = VOP_PANIC,
|
||||
@ -1761,7 +1770,7 @@ static struct vop_vector devfs_specops = {
|
||||
.vop_strategy = VOP_PANIC,
|
||||
.vop_symlink = VOP_PANIC,
|
||||
.vop_vptocnp = devfs_vptocnp,
|
||||
.vop_write = VOP_PANIC,
|
||||
.vop_write = dead_write,
|
||||
};
|
||||
|
||||
/*
|
||||
|
@ -758,6 +758,9 @@ int vop_enoent(struct vop_generic_args *ap);
|
||||
int vop_enotty(struct vop_generic_args *ap);
|
||||
int vop_null(struct vop_generic_args *ap);
|
||||
int vop_panic(struct vop_generic_args *ap);
|
||||
int dead_poll(struct vop_poll_args *ap);
|
||||
int dead_read(struct vop_read_args *ap);
|
||||
int dead_write(struct vop_write_args *ap);
|
||||
|
||||
/* These are called from within the actual VOPS. */
|
||||
void vop_create_post(void *a, int rc);
|
||||
|
Loading…
Reference in New Issue
Block a user