This patch fixes a problem whereby simultaneous delete operations (e.g. rm -fR *) from multiple nodes on the same GFS2 file system can cause kernel panics, hangs, and/or memory corruption.
Regards, Bob Peterson Signed-off-by: Bob Peterson <[EMAIL PROTECTED]> -- fs/gfs2/ops_inode.c | 24 ++++++------------------ 1 files changed, 6 insertions(+), 18 deletions(-) diff --git a/fs/gfs2/ops_inode.c b/fs/gfs2/ops_inode.c index e2c62f7..a072c9a 100644 --- a/fs/gfs2/ops_inode.c +++ b/fs/gfs2/ops_inode.c @@ -288,25 +288,17 @@ static int gfs2_unlink(struct inode *dir, struct dentry *dentry) gfs2_holder_init(rgd->rd_gl, LM_ST_EXCLUSIVE, 0, ghs + 2); - error = gfs2_glock_nq(ghs); /* parent */ - if (error) - goto out_parent; - - error = gfs2_glock_nq(ghs + 1); /* child */ - if (error) - goto out_child; - - error = gfs2_glock_nq(ghs + 2); /* rgrp */ + error = gfs2_glock_nq_m(3, ghs); if (error) - goto out_rgrp; + goto out; error = gfs2_unlink_ok(dip, &dentry->d_name, ip); if (error) - goto out_rgrp; + goto out; error = gfs2_trans_begin(sdp, 2*RES_DINODE + RES_LEAF + RES_RG_BIT, 0); if (error) - goto out_rgrp; + goto out; error = gfs2_dir_del(dip, &dentry->d_name); if (error) @@ -316,14 +308,10 @@ static int gfs2_unlink(struct inode *dir, struct dentry *dentry) out_end_trans: gfs2_trans_end(sdp); - gfs2_glock_dq(ghs + 2); -out_rgrp: +out: + gfs2_glock_dq_m(3, ghs); gfs2_holder_uninit(ghs + 2); - gfs2_glock_dq(ghs + 1); -out_child: gfs2_holder_uninit(ghs + 1); - gfs2_glock_dq(ghs); -out_parent: gfs2_holder_uninit(ghs); gfs2_glock_dq_uninit(&ri_gh); return error;