[v2] fix "NULL pointer dereference in gfs2_recover_func"

Chunjie Zhu posted 1 patch 10 months ago
fs/gfs2/recovery.c | 14 +++++++++-----
1 file changed, 9 insertions(+), 5 deletions(-)
[v2] fix "NULL pointer dereference in gfs2_recover_func"
Posted by Chunjie Zhu 10 months ago
before checking WITHDRAW flag, we have to check inode pointer

v2:
  fix gfs2_sbd NULL pointer deference

Signed-off-by: Chunjie Zhu <chunjie.zhu@cloud.com>
---
 fs/gfs2/recovery.c | 14 +++++++++-----
 1 file changed, 9 insertions(+), 5 deletions(-)

diff --git a/fs/gfs2/recovery.c b/fs/gfs2/recovery.c
index 44806513fc06..8434dd385ac5 100644
--- a/fs/gfs2/recovery.c
+++ b/fs/gfs2/recovery.c
@@ -400,7 +400,7 @@ static void recover_local_statfs(struct gfs2_jdesc *jd,
 
 void gfs2_recover_func(struct work_struct *work)
 {
-	struct gfs2_jdesc *jd = NULL;
+	struct gfs2_jdesc *jd = container_of(work, struct gfs2_jdesc, jd_work);
 	struct gfs2_inode *ip = NULL;
 	struct gfs2_sbd *sdp = NULL;
 	struct gfs2_log_header_host head;
@@ -411,16 +411,20 @@ void gfs2_recover_func(struct work_struct *work)
 	int error = 0;
 	int jlocked = 0;
 
-	if (gfs2_withdrawn(sdp)) {
-		fs_err(sdp, "jid=%u: Recovery not attempted due to withdraw.\n",
-		       jd->jd_jid);
+	if (unlikely(!jd->jd_inode)) {
+		fs_err(sdp, "jid=%u: Looks like withdraw is ongoing, skip recovery.\n",
+			   jd->jd_jid);
 		goto fail;
 	}
 
-	jd = container_of(work, struct gfs2_jdesc, jd_work);
 	ip = GFS2_I(jd->jd_inode);
 	sdp = GFS2_SB(jd->jd_inode);
 
+	if (gfs2_withdrawn(sdp)) {
+		fs_err(sdp, "jid=%u: Recovery not attempted due to withdraw.\n",
+		       jd->jd_jid);
+		goto fail;
+	}
 	t_start = ktime_get();
 	if (sdp->sd_args.ar_spectator)
 		goto fail;
-- 
2.34.1