aboutsummaryrefslogtreecommitdiff
path: root/fs/ext4/file.c
diff options
context:
space:
mode:
authorThomas Gleixner <[email protected]>2020-06-11 15:17:57 +0200
committerThomas Gleixner <[email protected]>2020-06-11 15:17:57 +0200
commitf77d26a9fc525286bcef3d4f98b52e17482cf49c (patch)
tree6b179c9aa84787773cb601a14a64255e2912154b /fs/ext4/file.c
parentb6bea24d41519e8c31e4798f1c1a3f67e540c5d0 (diff)
parentf0178fc01fe46bab6a95415f5647d1a74efcad1b (diff)
Merge branch 'x86/entry' into ras/core
to fixup conflicts in arch/x86/kernel/cpu/mce/core.c so MCE specific follow up patches can be applied without creating a horrible merge conflict afterwards.
Diffstat (limited to 'fs/ext4/file.c')
-rw-r--r--fs/ext4/file.c17
1 files changed, 15 insertions, 2 deletions
diff --git a/fs/ext4/file.c b/fs/ext4/file.c
index 0d624250a62b..2a01e31a032c 100644
--- a/fs/ext4/file.c
+++ b/fs/ext4/file.c
@@ -287,6 +287,7 @@ static ssize_t ext4_handle_inode_extension(struct inode *inode, loff_t offset,
bool truncate = false;
u8 blkbits = inode->i_blkbits;
ext4_lblk_t written_blk, end_blk;
+ int ret;
/*
* Note that EXT4_I(inode)->i_disksize can get extended up to
@@ -327,8 +328,14 @@ static ssize_t ext4_handle_inode_extension(struct inode *inode, loff_t offset,
goto truncate;
}
- if (ext4_update_inode_size(inode, offset + written))
- ext4_mark_inode_dirty(handle, inode);
+ if (ext4_update_inode_size(inode, offset + written)) {
+ ret = ext4_mark_inode_dirty(handle, inode);
+ if (unlikely(ret)) {
+ written = ret;
+ ext4_journal_stop(handle);
+ goto truncate;
+ }
+ }
/*
* We may need to truncate allocated but not written blocks beyond EOF.
@@ -495,6 +502,12 @@ static ssize_t ext4_dio_write_iter(struct kiocb *iocb, struct iov_iter *from)
if (ret <= 0)
return ret;
+ /* if we're going to block and IOCB_NOWAIT is set, return -EAGAIN */
+ if ((iocb->ki_flags & IOCB_NOWAIT) && (unaligned_io || extend)) {
+ ret = -EAGAIN;
+ goto out;
+ }
+
offset = iocb->ki_pos;
count = ret;