From 9a03228e9b3ec54282a2f5df380cea6cb632cd17 Mon Sep 17 00:00:00 2001 From: Jinshan Xiong Date: Tue, 28 Jan 2014 14:31:36 -0800 Subject: [PATCH] LU-4540 llite: deadlock for page write Writing thread already locked page #1, and then wait for the Writeback bit of page #2; Ptlrpc thread is composing a write RPC, so it sets Writeback on page #2 and tries to lock page #1 to make it ready. Deadlocked. Signed-off-by: Jinshan Xiong Change-Id: I2da547b4c93c3464e520a1f593985adae9360bc9 Reviewed-on: http://review.whamcloud.com/9036 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: wangdi Reviewed-by: Oleg Drokin --- lustre/llite/rw26.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/lustre/llite/rw26.c b/lustre/llite/rw26.c index 9365c74..447dc43 100644 --- a/lustre/llite/rw26.c +++ b/lustre/llite/rw26.c @@ -546,7 +546,8 @@ static int ll_write_begin(struct file *file, struct address_space *mapping, /* To avoid deadlock, try to lock page first. */ vmpage = grab_cache_page_nowait(mapping, index); - if (unlikely(vmpage == NULL || PageDirty(vmpage))) { + if (unlikely(vmpage == NULL || + PageDirty(vmpage) || PageWriteback(vmpage))) { struct ccc_io *cio = ccc_env_io(env); struct cl_page_list *plist = &cio->u.write.cui_queue; @@ -555,7 +556,7 @@ static int ll_write_begin(struct file *file, struct address_space *mapping, * because it holds page lock of a dirty page and request for * more grants. It's okay for the dirty page to be the first * one in commit page list, though. */ - if (vmpage != NULL && PageDirty(vmpage) && plist->pl_nr > 0) { + if (vmpage != NULL && plist->pl_nr > 0) { unlock_page(vmpage); page_cache_release(vmpage); vmpage = NULL; -- 1.8.3.1