From beadbad429aeffa66898bd62cc99e76290644ca8 Mon Sep 17 00:00:00 2001 From: Lai Siyao Date: Tue, 15 Aug 2017 11:13:30 +0800 Subject: [PATCH] LU-9857 lmv: stripe dir page may be released mistakenly stripe_dirent_next() may put_stripe_dirent() while its dirent is still in use, e.g. lmv_dirent_next() popped stripe last dirent, when it can't point sd_ent to next, but it shouldn't release stripe dir page. stripe_dirent->sd_ent should be set NULL when its dir page is released, which can avoid misuse. Signed-off-by: Lai Siyao Change-Id: I6d0e119d598e468d6a080b2072514a6bf1d4f786 Reviewed-on: https://review.whamcloud.com/28548 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: Fan Yong Reviewed-by: John L. Hammond Tested-by: John L. Hammond Reviewed-by: Oleg Drokin --- lustre/lmv/lmv_obd.c | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/lustre/lmv/lmv_obd.c b/lustre/lmv/lmv_obd.c index 904a7e0..19bbe64 100644 --- a/lustre/lmv/lmv_obd.c +++ b/lustre/lmv/lmv_obd.c @@ -2082,6 +2082,7 @@ static inline void put_stripe_dirent(struct stripe_dirent *stripe) kunmap(stripe->sd_page); put_page(stripe->sd_page); stripe->sd_page = NULL; + stripe->sd_ent = NULL; } } @@ -2105,20 +2106,23 @@ static struct lu_dirent *stripe_dirent_next(struct lmv_dir_ctxt *ctxt, LASSERT(stripe == &ctxt->ldc_stripes[stripe_index]); + if (stripe->sd_eof) + RETURN(NULL); + if (ent) { ent = lu_dirent_next(ent); if (!ent) { check_eof: end = le64_to_cpu(stripe->sd_dp->ldp_hash_end); - - put_stripe_dirent(stripe); - + LASSERTF(hash <= end, "hash %llx end %llx\n", + hash, end); if (end == MDS_DIR_END_OFF) { stripe->sd_ent = NULL; stripe->sd_eof = true; RETURN(NULL); } - LASSERT(hash <= end); + + put_stripe_dirent(stripe); hash = end; } } @@ -2170,10 +2174,8 @@ check_eof: le16_to_cpu(ent->lde_namelen)) == 0)) continue; - if (le64_to_cpu(ent->lde_hash) < hash) - continue; - - break; + if (le64_to_cpu(ent->lde_hash) >= hash) + break; } if (!ent) -- 1.8.3.1