summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJinshan Xiong <jinshan.xiong@intel.com>2016-06-20 20:55:28 (GMT)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2016-06-20 21:28:39 (GMT)
commita6307ff9aaeda8691204dc0ea30cd3680d06f6b3 (patch)
treeadc7cf002ec1a340ef972d5cd79d59367c7392db
parentc9cc8d0f6f770635b206784686a16157db3d43b8 (diff)
downloadlinux-a6307ff9aaeda8691204dc0ea30cd3680d06f6b3.tar.xz
staging/lustre/osc: osc_lock_weight endless loop fix
With huge number of pages to scan by osc_lock_weight() it is likely CLP_GANG_RESCHED is returned from osc_page_gang_lookup() and the scan will be repeated again from the start. To be sure that the scan is progressing across those restarts, next scan should be started from the last scanned page index plus one. Xyratex-bug-id: MRP-2145 Signed-off-by: Alexander Zarochentsev <alexander.zarochentsev@seagate.com> Signed-off-by: Jinshan Xiong <jinshan.xiong@intel.com> Reviewed-on: http://review.whamcloud.com/12362 Intel-bug-id: https://jira.hpdd.intel.com/browse/LU-5781 Reviewed-by: Bobi Jam <bobijam@hotmail.com> Reviewed-by: James Simmons <uja.ornl@gmail.com> Signed-off-by: Oleg Drokin <green@linuxhacker.ru> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--drivers/staging/lustre/lustre/osc/osc_lock.c14
1 files changed, 7 insertions, 7 deletions
diff --git a/drivers/staging/lustre/lustre/osc/osc_lock.c b/drivers/staging/lustre/lustre/osc/osc_lock.c
index 42def38..d856775 100644
--- a/drivers/staging/lustre/lustre/osc/osc_lock.c
+++ b/drivers/staging/lustre/lustre/osc/osc_lock.c
@@ -634,11 +634,10 @@ static int weigh_cb(const struct lu_env *env, struct cl_io *io,
if (cl_page_is_vmlocked(env, page) ||
PageDirty(page->cp_vmpage) || PageWriteback(page->cp_vmpage)
- ) {
- (*(unsigned long *)cbdata)++;
+ )
return CLP_GANG_ABORT;
- }
+ *(pgoff_t *)cbdata = osc_index(ops) + 1;
return CLP_GANG_OKAY;
}
@@ -648,7 +647,7 @@ static unsigned long osc_lock_weight(const struct lu_env *env,
{
struct cl_io *io = &osc_env_info(env)->oti_io;
struct cl_object *obj = cl_object_top(&oscobj->oo_cl);
- unsigned long npages = 0;
+ pgoff_t page_index;
int result;
io->ci_obj = obj;
@@ -657,11 +656,12 @@ static unsigned long osc_lock_weight(const struct lu_env *env,
if (result != 0)
return result;
+ page_index = cl_index(obj, extent->start);
do {
result = osc_page_gang_lookup(env, io, oscobj,
- cl_index(obj, extent->start),
+ page_index,
cl_index(obj, extent->end),
- weigh_cb, (void *)&npages);
+ weigh_cb, (void *)&page_index);
if (result == CLP_GANG_ABORT)
break;
if (result == CLP_GANG_RESCHED)
@@ -669,7 +669,7 @@ static unsigned long osc_lock_weight(const struct lu_env *env,
} while (result != CLP_GANG_OKAY);
cl_io_fini(env, io);
- return npages;
+ return result == CLP_GANG_ABORT ? 1 : 0;
}
/**