Audit kqueue notifications. The reference behavior is taken from MFS and

is represented in the regression tests.
This commit is contained in:
jmmv 2006-11-09 15:06:03 +00:00
parent 492fddeb4a
commit 117b5f5104
5 changed files with 52 additions and 27 deletions

View File

@ -18,6 +18,3 @@
jmmv: I may agree with the removal of the visual lines, but not with the
vop_*_args assignment. Those are very ugly and add a lot of redundancy.
- Check and fix KNOTE_* calls (e.g. missing NOTE_LINK on link(2), perhaps
others)

View File

@ -1,4 +1,4 @@
/* $NetBSD: tmpfs_subr.c,v 1.28 2006/11/05 19:40:31 jmmv Exp $ */
/* $NetBSD: tmpfs_subr.c,v 1.29 2006/11/09 15:06:03 jmmv Exp $ */
/*
* Copyright (c) 2005, 2006 The NetBSD Foundation, Inc.
@ -42,7 +42,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: tmpfs_subr.c,v 1.28 2006/11/05 19:40:31 jmmv Exp $");
__KERNEL_RCSID(0, "$NetBSD: tmpfs_subr.c,v 1.29 2006/11/09 15:06:03 jmmv Exp $");
#include <sys/param.h>
#include <sys/dirent.h>
@ -155,6 +155,10 @@ tmpfs_alloc_node(struct tmpfs_mount *tmp, enum vtype type,
nnode->tn_spec.tn_dir.tn_readdir_lastp = NULL;
nnode->tn_links++;
nnode->tn_spec.tn_dir.tn_parent->tn_links++;
if (parent != NULL) {
KASSERT(parent->tn_vnode != NULL);
VN_KNOTE(parent->tn_vnode, NOTE_LINK);
}
break;
case VFIFO:
@ -270,7 +274,8 @@ tmpfs_free_node(struct tmpfs_mount *tmp, struct tmpfs_node *node)
* The new directory entry is returned in *de.
*
* The link count of node is increased by one to reflect the new object
* referencing it.
* referencing it. This takes care of notifying kqueue listeners about
* this change.
*
* Returns zero on success or an appropriate error code on failure.
*/
@ -294,6 +299,8 @@ tmpfs_alloc_dirent(struct tmpfs_mount *tmp, struct tmpfs_node *node,
nde->td_node = node;
node->tn_links++;
if (node->tn_links > 1 && node->tn_vnode != NULL)
VN_KNOTE(node->tn_vnode, NOTE_LINK);
*de = nde;
return 0;
@ -309,6 +316,10 @@ tmpfs_alloc_dirent(struct tmpfs_mount *tmp, struct tmpfs_node *node,
* object that referenced it. This only happens if 'node_exists' is true;
* otherwise the function will not access the node referred to by the
* directory entry, as it may already have been released from the outside.
*
* Interested parties (kqueue) are notified of the link count change; note
* that this can include both the node pointed to by the directory entry
* as well as its parent.
*/
void
tmpfs_free_dirent(struct tmpfs_mount *tmp, struct tmpfs_dirent *de,
@ -321,6 +332,12 @@ tmpfs_free_dirent(struct tmpfs_mount *tmp, struct tmpfs_dirent *de,
KASSERT(node->tn_links > 0);
node->tn_links--;
if (node->tn_vnode != NULL)
VN_KNOTE(node->tn_vnode, node->tn_links == 0 ?
NOTE_DELETE : NOTE_LINK);
if (node->tn_type == VDIR)
VN_KNOTE(node->tn_spec.tn_dir.tn_parent->tn_vnode,
NOTE_LINK);
}
tmpfs_str_pool_put(&tmp->tm_str_pool, de->td_name, de->td_namelen);
@ -522,7 +539,6 @@ tmpfs_alloc_file(struct vnode *dvp, struct vnode **vpp, struct vattr *vap,
* insert the new node into the directory, an operation that
* cannot fail. */
tmpfs_dir_attach(dvp, de);
VN_KNOTE(dvp, NOTE_WRITE);
out:
if (error != 0 || !(cnp->cn_flags & SAVESTART))
@ -541,6 +557,9 @@ out:
* Attaches the directory entry de to the directory represented by vp.
* Note that this does not change the link count of the node pointed by
* the directory entry, as this is done by tmpfs_alloc_dirent.
*
* As the "parent" directory changes, interested parties are notified of
* a write to it.
*/
void
tmpfs_dir_attach(struct vnode *vp, struct tmpfs_dirent *de)
@ -554,6 +573,8 @@ tmpfs_dir_attach(struct vnode *vp, struct tmpfs_dirent *de)
dnode->tn_status |= TMPFS_NODE_ACCESSED | TMPFS_NODE_CHANGED | \
TMPFS_NODE_MODIFIED;
uvm_vnp_setsize(vp, dnode->tn_size);
VN_KNOTE(vp, NOTE_WRITE);
}
/* --------------------------------------------------------------------- */
@ -562,6 +583,9 @@ tmpfs_dir_attach(struct vnode *vp, struct tmpfs_dirent *de)
* Detaches the directory entry de from the directory represented by vp.
* Note that this does not change the link count of the node pointed by
* the directory entry, as this is done by tmpfs_free_dirent.
*
* As the "parent" directory changes, interested parties are notified of
* a write to it.
*/
void
tmpfs_dir_detach(struct vnode *vp, struct tmpfs_dirent *de)
@ -582,6 +606,8 @@ tmpfs_dir_detach(struct vnode *vp, struct tmpfs_dirent *de)
dnode->tn_status |= TMPFS_NODE_ACCESSED | TMPFS_NODE_CHANGED | \
TMPFS_NODE_MODIFIED;
uvm_vnp_setsize(vp, dnode->tn_size);
VN_KNOTE(vp, NOTE_WRITE);
}
/* --------------------------------------------------------------------- */
@ -845,6 +871,10 @@ tmpfs_dir_getdents(struct tmpfs_node *node, struct uio *uio, off_t *cntp)
* the size newsize. 'vp' must point to a vnode that represents a regular
* file. 'newsize' must be positive.
*
* If the file is extended, the appropriate kevent is raised. This does
* not rise a write event though because resizing is not the same as
* writing.
*
* Returns zero on success or an appropriate error code on failure.
*/
int
@ -908,6 +938,9 @@ tmpfs_reg_resize(struct vnode *vp, off_t newsize)
error = 0;
if (newsize > oldsize)
VN_KNOTE(vp, NOTE_EXTEND);
out:
return error;
}
@ -1210,6 +1243,7 @@ tmpfs_chtimes(struct vnode *vp, struct timespec *atime, struct timespec *mtime,
node->tn_status |= TMPFS_NODE_MODIFIED;
tmpfs_update(vp, atime, mtime, 0);
VN_KNOTE(vp, NOTE_ATTRIB);
KASSERT(VOP_ISLOCKED(vp));
@ -1296,10 +1330,8 @@ tmpfs_truncate(struct vnode *vp, off_t length)
}
error = tmpfs_reg_resize(vp, length);
if (error == 0) {
VN_KNOTE(vp, NOTE_ATTRIB | (extended ? NOTE_EXTEND : 0));
if (error == 0)
node->tn_status |= TMPFS_NODE_CHANGED | TMPFS_NODE_MODIFIED;
}
out:
tmpfs_update(vp, NULL, NULL, 0);

View File

@ -1,4 +1,4 @@
/* $NetBSD: tmpfs_vfsops.c,v 1.15 2006/10/12 01:32:14 christos Exp $ */
/* $NetBSD: tmpfs_vfsops.c,v 1.16 2006/11/09 15:06:03 jmmv Exp $ */
/*
* Copyright (c) 2005, 2006 The NetBSD Foundation, Inc.
@ -49,7 +49,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: tmpfs_vfsops.c,v 1.15 2006/10/12 01:32:14 christos Exp $");
__KERNEL_RCSID(0, "$NetBSD: tmpfs_vfsops.c,v 1.16 2006/11/09 15:06:03 jmmv Exp $");
#include <sys/param.h>
#include <sys/types.h>
@ -237,6 +237,7 @@ tmpfs_unmount(struct mount *mp, int mntflags, struct lwp *l __unused)
struct tmpfs_dirent *nde;
nde = TAILQ_NEXT(de, td_entries);
KASSERT(de->td_node->tn_vnode == NULL);
tmpfs_free_dirent(tmp, de, FALSE);
de = nde;
node->tn_size -= sizeof(struct tmpfs_dirent);

View File

@ -1,4 +1,4 @@
/* $NetBSD: tmpfs_vnops.c,v 1.30 2006/11/07 14:08:13 jmmv Exp $ */
/* $NetBSD: tmpfs_vnops.c,v 1.31 2006/11/09 15:06:03 jmmv Exp $ */
/*
* Copyright (c) 2005, 2006 The NetBSD Foundation, Inc.
@ -42,7 +42,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: tmpfs_vnops.c,v 1.30 2006/11/07 14:08:13 jmmv Exp $");
__KERNEL_RCSID(0, "$NetBSD: tmpfs_vnops.c,v 1.31 2006/11/09 15:06:03 jmmv Exp $");
#include <sys/param.h>
#include <sys/dirent.h>
@ -630,6 +630,8 @@ tmpfs_write(void *v)
if (error != 0)
(void)tmpfs_reg_resize(vp, oldsize);
VN_KNOTE(vp, NOTE_WRITE);
out:
KASSERT(VOP_ISLOCKED(vp));
KASSERT(IMPLIES(error == 0, uio->uio_resid == 0));
@ -691,10 +693,6 @@ tmpfs_remove(void *v)
* have to change the number of hard links of the directory. */
tmpfs_dir_detach(dvp, de);
/* Notify interested parties about the modification of dvp.
* The removal of vp is notified when it is reclaimed. */
VN_KNOTE(dvp, NOTE_WRITE);
/* Free the directory entry we just deleted. Note that the node
* referred by it will not be removed until the vnode is really
* reclaimed. */
@ -775,7 +773,6 @@ tmpfs_link(void *v)
/* Insert the new directory entry into the appropriate directory. */
tmpfs_dir_attach(dvp, de);
VN_KNOTE(dvp, NOTE_WRITE);
/* vp link count has changed, so update node times. */
node->tn_status |= TMPFS_NODE_CHANGED;
@ -952,8 +949,10 @@ tmpfs_rename(void *v)
}
/* Notify listeners of tdvp about the change in the directory (either
* because a new entry was added or because one was removed). */
* because a new entry was added or because one was removed) and
* listeners of fvp about the rename. */
VN_KNOTE(tdvp, NOTE_WRITE);
VN_KNOTE(fvp, NOTE_RENAME);
error = 0;
@ -1046,8 +1045,7 @@ tmpfs_rmdir(void *v)
node->tn_spec.tn_dir.tn_parent->tn_status |= TMPFS_NODE_ACCESSED | \
TMPFS_NODE_CHANGED | TMPFS_NODE_MODIFIED;
/* Notify modification of parent directory and release it. */
VN_KNOTE(dvp, NOTE_WRITE | NOTE_LINK);
/* Release the parent. */
cache_purge(dvp); /* XXX Is this needed? */
vput(dvp);
@ -1256,9 +1254,6 @@ tmpfs_reclaim(void *v)
node = VP_TO_TMPFS_NODE(vp);
tmp = VFS_TO_TMPFS(vp->v_mount);
if (node->tn_links == 0)
VN_KNOTE(vp, NOTE_DELETE);
cache_purge(vp);
tmpfs_free_vp(vp);

View File

@ -1,4 +1,4 @@
/* $NetBSD: tmpfs_vnops.h,v 1.7 2005/12/03 17:34:44 christos Exp $ */
/* $NetBSD: tmpfs_vnops.h,v 1.8 2006/11/09 15:06:03 jmmv Exp $ */
/*
* Copyright (c) 2005 The NetBSD Foundation, Inc.
@ -67,7 +67,7 @@ int tmpfs_write (void *);
#define tmpfs_fcntl genfs_fcntl
#define tmpfs_ioctl genfs_enoioctl
#define tmpfs_poll genfs_poll
#define tmpfs_kqfilter genfs_eopnotsupp
#define tmpfs_kqfilter genfs_kqfilter
#define tmpfs_revoke genfs_revoke
#define tmpfs_mmap genfs_mmap
int tmpfs_fsync (void *);