Skip to content

Commit 764665c

Browse files
author
Andreas Gruenbacher
committed
gfs2: Clean up after gfs2_create_inode rework
Since commit 3d36e57 ("gfs2: gfs2_create_inode rework"), gfs2_evict_inode() and gfs2_create_inode() / gfs2_inode_lookup() will synchronize via the inode hash table and we can be certain that once a new inode is inserted into the inode hash table(), gfs2_evict_inode() has completely destroyed any previous versions. We no longer need to worry about overlapping inode object lifespans. Update the code and comments accordingly. Signed-off-by: Andreas Gruenbacher <[email protected]>
1 parent 97236ad commit 764665c

File tree

2 files changed

+14
-21
lines changed

2 files changed

+14
-21
lines changed

fs/gfs2/glock.h

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -322,20 +322,6 @@ static inline void glock_set_object(struct gfs2_glock *gl, void *object)
322322
/**
323323
* glock_clear_object - clear the gl_object field of a glock
324324
* @gl: the glock
325-
* @object: the object
326-
*
327-
* I'd love to similarly add this:
328-
* else if (gfs2_assert_warn(gl->gl_sbd, gl->gl_object == object))
329-
* gfs2_dump_glock(NULL, gl, true);
330-
* Unfortunately, that's not possible because as soon as gfs2_delete_inode
331-
* frees the block in the rgrp, another process can reassign it for an I_NEW
332-
* inode in gfs2_create_inode because that calls new_inode, not gfs2_iget.
333-
* That means gfs2_delete_inode may subsequently try to call this function
334-
* for a glock that's already pointing to a brand new inode. If we clear the
335-
* new inode's gl_object, we'll introduce metadata corruption. Function
336-
* gfs2_delete_inode calls clear_inode which calls gfs2_clear_inode which also
337-
* tries to clear gl_object, so it's more than just gfs2_delete_inode.
338-
*
339325
*/
340326
static inline void glock_clear_object(struct gfs2_glock *gl, void *object)
341327
{

fs/gfs2/super.c

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1304,14 +1304,21 @@ static int evict_unlinked_inode(struct inode *inode)
13041304
goto out;
13051305
}
13061306

1307-
/* We're about to clear the bitmap for the dinode, but as soon as we
1308-
do, gfs2_create_inode can create another inode at the same block
1309-
location and try to set gl_object again. We clear gl_object here so
1310-
that subsequent inode creates don't see an old gl_object. */
1311-
if (ip->i_gl) {
1312-
glock_clear_object(ip->i_gl, ip);
1307+
if (ip->i_gl)
13131308
gfs2_inode_remember_delete(ip->i_gl, ip->i_no_formal_ino);
1314-
}
1309+
1310+
/*
1311+
* As soon as we clear the bitmap for the dinode, gfs2_create_inode()
1312+
* can get called to recreate it, or even gfs2_inode_lookup() if the
1313+
* inode was recreated on another node in the meantime.
1314+
*
1315+
* However, inserting the new inode into the inode hash table will not
1316+
* succeed until the old inode is removed, and that only happens after
1317+
* ->evict_inode() returns. The new inode is attached to its inode and
1318+
* iopen glocks after inserting it into the inode hash table, so at
1319+
* that point we can be sure that both glocks are unused.
1320+
*/
1321+
13151322
ret = gfs2_dinode_dealloc(ip);
13161323
out:
13171324
return ret;

0 commit comments

Comments
 (0)