From b28b3bd9094ee7be8e3c11a531383246a71d5dec Mon Sep 17 00:00:00 2001 From: Wang Shilong Date: Sat, 29 Feb 2020 22:02:55 +0800 Subject: [PATCH] LU-13312 ldlm: fix to stop iterating tree early in ldlm_kms_shift_cb() It is very possible that old_kms is equal (last extent end + 1), and if we fail last one check, we will have to iterate all PR extent locks in tree which is O(N). This is very likely to happen in IO500 hard mode, because firstly we try to write which generates a lot of PW locks, after that read is triggered which need cancel all PW locks to PR locks. Be careful to avoid overflow, as @l_extent.end could be OBD_OBJECT_EOF, if that is case, it just means we could stop iterating. Signed-off-by: Li Dongyang Signed-off-by: Wang Shilong Change-Id: Ie142fb738482a8abcc7d0c9d67d6e6eb520459db Reviewed-on: https://review.whamcloud.com/37762 Reviewed-by: Andreas Dilger Tested-by: jenkins Tested-by: Maloo Reviewed-by: Gu Zheng --- lustre/ldlm/ldlm_extent.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lustre/ldlm/ldlm_extent.c b/lustre/ldlm/ldlm_extent.c index 9e046c9..2cfd006 100644 --- a/lustre/ldlm/ldlm_extent.c +++ b/lustre/ldlm/ldlm_extent.c @@ -890,7 +890,8 @@ static enum interval_iter ldlm_kms_shift_cb(struct interval_node *n, /* If we find a lock with a greater or equal kms, we are not the * highest lock (or we share that distinction with another lock), and * don't need to update KMS. Return old_kms and stop looking. */ - if (lock->l_policy_data.l_extent.end >= arg->old_kms) { + if (lock->l_policy_data.l_extent.end == OBD_OBJECT_EOF || + lock->l_policy_data.l_extent.end + 1 >= arg->old_kms) { arg->kms = arg->old_kms; arg->complete = true; RETURN(INTERVAL_ITER_STOP); -- 1.8.3.1