kernel/vfs: Fix locking behavior in acquire_vnode and add a missing ASSERT.

vnode deletion is prevent either by owning a reference to the node,
or by being at least a reader of the vnodes lock. Thus, in acquire_vnode,
we have to inc_ref_count while still holding the lock in order to prevent
a race.

This function is used so rarely and quite deep inside FS drivers that
I'm  not sure this race would ever have been a problem. Nonetheless
the old code was incorrect.
This commit is contained in:
Augustin Cavalier
2022-10-29 13:42:19 -04:00
parent b4b1561b6a
commit 1284e971e2
+4 -5
View File
@@ -899,6 +899,8 @@ remove_vnode_from_mount_list(struct vnode* vnode, struct fs_mount* mount)
static struct vnode*
lookup_vnode(dev_t mountID, ino_t vnodeID)
{
ASSERT_READ_LOCKED_RW_LOCK(&sVnodeLock);
struct vnode_hash_key key;
key.device = mountID;
@@ -3894,12 +3896,9 @@ get_vnode(fs_volume* volume, ino_t vnodeID, void** _privateNode)
extern "C" status_t
acquire_vnode(fs_volume* volume, ino_t vnodeID)
{
struct vnode* vnode;
rw_lock_read_lock(&sVnodeLock);
vnode = lookup_vnode(volume->id, vnodeID);
rw_lock_read_unlock(&sVnodeLock);
ReadLocker nodeLocker(sVnodeLock);
struct vnode* vnode = lookup_vnode(volume->id, vnodeID);
if (vnode == NULL)
return B_BAD_VALUE;