summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBob Peterson <rpeterso@redhat.com>2020-04-22 22:14:30 +0300
committerAndreas Gruenbacher <agruenba@redhat.com>2020-05-06 22:25:26 +0300
commitac9155842829a811c12d3e1868a133fdb8300df0 (patch)
treef654df998850da2390db3900214cc670a114b24f
parent8f3d9f354286745c751374f5f1fcafee6b3f3136 (diff)
downloadlinux-ac9155842829a811c12d3e1868a133fdb8300df0.tar.xz
gfs2: fix withdraw sequence deadlock
After a gfs2 file system withdraw, any attempt to read metadata is automatically rejected by function gfs2_meta_read() except for reads of the journal inode. This turns out to be a problem because function signal_our_withdraw() repeatedly calls check_journal_clean() which reads the metadata (both its dinode and indirect blocks) to see if the entire journal is mapped. The dinode read works, but reading the indirect blocks returns -EIO which gets sent back up and causes a consistency error. This results in withdraw-from-withdraw, which becomes a deadlock. This patch changes the test in gfs2_meta_read() to allow all metadata reads for the journal. Instead of checking the journal block, it now checks for the journal inode glock which is the same for all blocks in the journal. This allows check_journal_clean() to properly check the journal without trying to withdraw recursively. Signed-off-by: Bob Peterson <rpeterso@redhat.com> Signed-off-by: Andreas Gruenbacher <agruenba@redhat.com>
-rw-r--r--fs/gfs2/meta_io.c2
1 files changed, 1 insertions, 1 deletions
diff --git a/fs/gfs2/meta_io.c b/fs/gfs2/meta_io.c
index 4b72abcf83b2..9856cc2e0795 100644
--- a/fs/gfs2/meta_io.c
+++ b/fs/gfs2/meta_io.c
@@ -252,7 +252,7 @@ int gfs2_meta_read(struct gfs2_glock *gl, u64 blkno, int flags,
int num = 0;
if (unlikely(gfs2_withdrawn(sdp)) &&
- (!sdp->sd_jdesc || (blkno != sdp->sd_jdesc->jd_no_addr))) {
+ (!sdp->sd_jdesc || gl != sdp->sd_jinode_gl)) {
*bhp = NULL;
return -EIO;
}