diff options
author | Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com> | 2009-09-09 22:36:03 -0400 |
---|---|---|
committer | Theodore Ts'o <tytso@mit.edu> | 2009-09-09 22:36:03 -0400 |
commit | a827eaffff07c7d58a4cb32158cbeb4849f4e33a (patch) | |
tree | 6167caf1619f0d9555fd67a2facbf2351a0a7905 /fs/ext4/inode.c | |
parent | 44fc48f7048ab9657b524938a832fec4e0acea98 (diff) |
ext4: Take page lock before looking at attached buffer_heads flags
In order to check whether the buffer_heads are mapped we need to hold
page lock. Otherwise a reclaim can cleanup the attached buffer_heads.
Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
Diffstat (limited to 'fs/ext4/inode.c')
-rw-r--r-- | fs/ext4/inode.c | 13 |
1 files changed, 11 insertions, 2 deletions
diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index 17802a96af9f..5c0d17066f4a 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c | |||
@@ -5286,12 +5286,21 @@ int ext4_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) | |||
5286 | else | 5286 | else |
5287 | len = PAGE_CACHE_SIZE; | 5287 | len = PAGE_CACHE_SIZE; |
5288 | 5288 | ||
5289 | lock_page(page); | ||
5290 | /* | ||
5291 | * return if we have all the buffers mapped. This avoid | ||
5292 | * the need to call write_begin/write_end which does a | ||
5293 | * journal_start/journal_stop which can block and take | ||
5294 | * long time | ||
5295 | */ | ||
5289 | if (page_has_buffers(page)) { | 5296 | if (page_has_buffers(page)) { |
5290 | /* return if we have all the buffers mapped */ | ||
5291 | if (!walk_page_buffers(NULL, page_buffers(page), 0, len, NULL, | 5297 | if (!walk_page_buffers(NULL, page_buffers(page), 0, len, NULL, |
5292 | ext4_bh_unmapped)) | 5298 | ext4_bh_unmapped)) { |
5299 | unlock_page(page); | ||
5293 | goto out_unlock; | 5300 | goto out_unlock; |
5301 | } | ||
5294 | } | 5302 | } |
5303 | unlock_page(page); | ||
5295 | /* | 5304 | /* |
5296 | * OK, we need to fill the hole... Do write_begin write_end | 5305 | * OK, we need to fill the hole... Do write_begin write_end |
5297 | * to do block allocation/reservation.We are not holding | 5306 | * to do block allocation/reservation.We are not holding |