tech-kern archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Vnode API change: mnt_vnodelist traversal



Current support for iterating over mnt_vnodelist (the list of vnodes
attached to a specific mount point) is rudimentary.  All we have is
vmark() / vunmark() to set a marker on the list.  Every caller has
to care about list and vnode mutexes, reference count being zero,
intermediate vnode states like VI_CLEAN, VI_XLOCK, VI_MARKER and so on.


Add an interface to iterate over a vnode list:

    void vfs_vnode_iterator_init(struct mount *mp, void **marker)
    void vfs_vnode_iterator_destroy(void *marker)
    bool vfs_vnode_iterator_next(void *marker, struct vnode **vpp)

where vfs_vnode_iterator_next() returns either "false / *vpp == NULL"
when done or "true / *vpp != NULL" to return the next referenced vnode
from the list.

To make vrecycle() work in this environment change it to

    bool vrecycle(struct vnode *vp)

where "vp" is a referenced vnode to be destroyed if this is the last
reference.


Typical usage is like

    struct vnode *vp;
    void *marker;

    vfs_vnode_iterator_init(mp, &marker);
    while (vfs_vnode_iterator_next(marker, &vp) {
        if (vrecycle(vp))
            continue;
        if (destroy_all)
            vgone(vp);
        else
            vrele(vp);
    }
    vfs_vnode_iterator_destroy(marker);

to clean or purge the list or

    struct vnode *vp;
    void *marker;

    vfs_vnode_iterator_init(mp, &marker);
    while (vfs_vnode_iterator_next(marker, &vp) {
        error = vn_lock(vp, LK_EXCLUSIVE);
        if (error == ENOENT) {
            vrele(vp);
            continue;
        }
        KASSERT(error == 0);
        /* process this vnode */
        vput(vp);
    }
    vfs_vnode_iterator_destroy(marker);

to do something on all vnodes attached to this mount point.


A diff implementing this and using it for those operations running
vrecycle() is at http://www.netbsd.org/~hannken/vnode-pass4-1.diff

Once all operations are converted, vmark() / vunmark() will go and
man pages will be updated.

Comments or objections anyone?

--
J. Hannken-Illjes - hannken%eis.cs.tu-bs.de@localhost - TU Braunschweig 
(Germany)



Home | Main Index | Thread Index | Old Index