Skip to content

Commit

Permalink
ext4: do not ask jbd2 to write data for delalloc buffers
Browse files Browse the repository at this point in the history
Currently we ask jbd2 to write all dirty allocated buffers before
committing a transaction when doing writeback of delay allocated blocks.
However this is unnecessary since we move all pages to writeback state
before dropping a transaction handle and then submit all the necessary
IO. We still need the transaction commit to wait for all the outstanding
writeback before flushing disk caches during transaction commit to avoid
data exposure issues though. Use the new jbd2 capability and ask it to
only wait for outstanding writeback during transaction commit when
writing back data in ext4_writepages().

Tested-by: "HUANG Weller (CM/ESW12-CN)" <Weller.Huang@cn.bosch.com>
Signed-off-by: Jan Kara <jack@suse.cz>
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
  • Loading branch information
Jan Kara authored and Theodore Ts'o committed Apr 24, 2016
1 parent 41617e1 commit ee0876b
Show file tree
Hide file tree
Showing 4 changed files with 22 additions and 5 deletions.
3 changes: 3 additions & 0 deletions fs/ext4/ext4.h
Original file line number Diff line number Diff line change
Expand Up @@ -581,6 +581,9 @@ enum {
#define EXT4_GET_BLOCKS_ZERO 0x0200
#define EXT4_GET_BLOCKS_CREATE_ZERO (EXT4_GET_BLOCKS_CREATE |\
EXT4_GET_BLOCKS_ZERO)
/* Caller will submit data before dropping transaction handle. This
* allows jbd2 to avoid submitting data before commit. */
#define EXT4_GET_BLOCKS_IO_SUBMIT 0x0400

/*
* The bit position of these flags must not overlap with any of the
Expand Down
12 changes: 11 additions & 1 deletion fs/ext4/ext4_jbd2.h
Original file line number Diff line number Diff line change
Expand Up @@ -359,14 +359,24 @@ static inline int ext4_journal_force_commit(journal_t *journal)
return 0;
}

static inline int ext4_jbd2_file_inode(handle_t *handle, struct inode *inode)
static inline int ext4_jbd2_inode_add_write(handle_t *handle,
struct inode *inode)
{
if (ext4_handle_valid(handle))
return jbd2_journal_inode_add_write(handle,
EXT4_I(inode)->jinode);
return 0;
}

static inline int ext4_jbd2_inode_add_wait(handle_t *handle,
struct inode *inode)
{
if (ext4_handle_valid(handle))
return jbd2_journal_inode_add_wait(handle,
EXT4_I(inode)->jinode);
return 0;
}

static inline void ext4_update_inode_fsync_trans(handle_t *handle,
struct inode *inode,
int datasync)
Expand Down
10 changes: 7 additions & 3 deletions fs/ext4/inode.c
Original file line number Diff line number Diff line change
Expand Up @@ -695,7 +695,10 @@ int ext4_map_blocks(handle_t *handle, struct inode *inode,
!(flags & EXT4_GET_BLOCKS_ZERO) &&
!IS_NOQUOTA(inode) &&
ext4_should_order_data(inode)) {
ret = ext4_jbd2_file_inode(handle, inode);
if (flags & EXT4_GET_BLOCKS_IO_SUBMIT)
ret = ext4_jbd2_inode_add_wait(handle, inode);
else
ret = ext4_jbd2_inode_add_write(handle, inode);
if (ret)
return ret;
}
Expand Down Expand Up @@ -2319,7 +2322,8 @@ static int mpage_map_one_extent(handle_t *handle, struct mpage_da_data *mpd)
* the data was copied into the page cache.
*/
get_blocks_flags = EXT4_GET_BLOCKS_CREATE |
EXT4_GET_BLOCKS_METADATA_NOFAIL;
EXT4_GET_BLOCKS_METADATA_NOFAIL |
EXT4_GET_BLOCKS_IO_SUBMIT;
dioread_nolock = ext4_should_dioread_nolock(inode);
if (dioread_nolock)
get_blocks_flags |= EXT4_GET_BLOCKS_IO_CREATE_EXT;
Expand Down Expand Up @@ -3634,7 +3638,7 @@ static int __ext4_block_zero_page_range(handle_t *handle,
err = 0;
mark_buffer_dirty(bh);
if (ext4_should_order_data(inode))
err = ext4_jbd2_file_inode(handle, inode);
err = ext4_jbd2_inode_add_write(handle, inode);
}

unlock:
Expand Down
2 changes: 1 addition & 1 deletion fs/ext4/move_extent.c
Original file line number Diff line number Diff line change
Expand Up @@ -400,7 +400,7 @@ move_extent_per_page(struct file *o_filp, struct inode *donor_inode,

/* Even in case of data=writeback it is reasonable to pin
* inode to transaction, to prevent unexpected data loss */
*err = ext4_jbd2_file_inode(handle, orig_inode);
*err = ext4_jbd2_inode_add_write(handle, orig_inode);

unlock_pages:
unlock_page(pagep[0]);
Expand Down

0 comments on commit ee0876b

Please sign in to comment.