diff options
author | Jens Axboe <jens.axboe@oracle.com> | 2007-07-20 15:18:12 +0200 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-07-20 18:07:01 +0200 |
commit | 6a860c979b35469e4d77da781a96bdb2ca05ae64 (patch) | |
tree | 3160a7a4c76743fa4ca9a9eb9ccb0d67bc363d9b /fs/splice.c | |
parent | lguest: override sched_clock (diff) | |
download | linux-6a860c979b35469e4d77da781a96bdb2ca05ae64.tar.xz linux-6a860c979b35469e4d77da781a96bdb2ca05ae64.zip |
splice: fix bad unlock_page() in error case
If add_to_page_cache_lru() fails, the page will not be locked. But
splice jumps to an error path that does a page release and unlock,
causing a BUG() in unlock_page().
Fix this by adding one more label that just releases the page. This bug
was actually triggered on EL5 by gurudas pai <gurudas.pai@oracle.com>
using fio.
Signed-off-by: Jens Axboe <jens.axboe@oracle.com>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'fs/splice.c')
-rw-r--r-- | fs/splice.c | 5 |
1 files changed, 3 insertions, 2 deletions
diff --git a/fs/splice.c b/fs/splice.c index 22496d2a73fa..0a0973218084 100644 --- a/fs/splice.c +++ b/fs/splice.c @@ -594,7 +594,7 @@ find_page: ret = add_to_page_cache_lru(page, mapping, index, GFP_KERNEL); if (unlikely(ret)) - goto out; + goto out_release; } ret = mapping->a_ops->prepare_write(file, page, offset, offset+this_len); @@ -650,8 +650,9 @@ find_page: */ mark_page_accessed(page); out: - page_cache_release(page); unlock_page(page); +out_release: + page_cache_release(page); out_ret: return ret; } |