diff options
author | Sage Weil <sage@inktank.com> | 2013-08-15 14:11:45 -0400 |
---|---|---|
committer | Sage Weil <sage@inktank.com> | 2013-08-15 14:11:45 -0400 |
commit | ee3e542fec6e69bc9fb668698889a37d93950ddf (patch) | |
tree | e74ee766a4764769ef1d3d45d266b4dea64101d3 /fs/ext4/fsync.c | |
parent | fe2a801b50c0bb8039d627e5ae1fec249d10ff39 (diff) | |
parent | f1d6e17f540af37bb1891480143669ba7636c4cf (diff) |
Merge remote-tracking branch 'linus/master' into testing
Diffstat (limited to 'fs/ext4/fsync.c')
-rw-r--r-- | fs/ext4/fsync.c | 52 |
1 files changed, 12 insertions, 40 deletions
diff --git a/fs/ext4/fsync.c b/fs/ext4/fsync.c index e0ba8a408def..a8bc47f75fa0 100644 --- a/fs/ext4/fsync.c +++ b/fs/ext4/fsync.c | |||
@@ -73,32 +73,6 @@ static int ext4_sync_parent(struct inode *inode) | |||
73 | return ret; | 73 | return ret; |
74 | } | 74 | } |
75 | 75 | ||
76 | /** | ||
77 | * __sync_file - generic_file_fsync without the locking and filemap_write | ||
78 | * @inode: inode to sync | ||
79 | * @datasync: only sync essential metadata if true | ||
80 | * | ||
81 | * This is just generic_file_fsync without the locking. This is needed for | ||
82 | * nojournal mode to make sure this inodes data/metadata makes it to disk | ||
83 | * properly. The i_mutex should be held already. | ||
84 | */ | ||
85 | static int __sync_inode(struct inode *inode, int datasync) | ||
86 | { | ||
87 | int err; | ||
88 | int ret; | ||
89 | |||
90 | ret = sync_mapping_buffers(inode->i_mapping); | ||
91 | if (!(inode->i_state & I_DIRTY)) | ||
92 | return ret; | ||
93 | if (datasync && !(inode->i_state & I_DIRTY_DATASYNC)) | ||
94 | return ret; | ||
95 | |||
96 | err = sync_inode_metadata(inode, 1); | ||
97 | if (ret == 0) | ||
98 | ret = err; | ||
99 | return ret; | ||
100 | } | ||
101 | |||
102 | /* | 76 | /* |
103 | * akpm: A new design for ext4_sync_file(). | 77 | * akpm: A new design for ext4_sync_file(). |
104 | * | 78 | * |
@@ -116,7 +90,7 @@ int ext4_sync_file(struct file *file, loff_t start, loff_t end, int datasync) | |||
116 | struct inode *inode = file->f_mapping->host; | 90 | struct inode *inode = file->f_mapping->host; |
117 | struct ext4_inode_info *ei = EXT4_I(inode); | 91 | struct ext4_inode_info *ei = EXT4_I(inode); |
118 | journal_t *journal = EXT4_SB(inode->i_sb)->s_journal; | 92 | journal_t *journal = EXT4_SB(inode->i_sb)->s_journal; |
119 | int ret, err; | 93 | int ret = 0, err; |
120 | tid_t commit_tid; | 94 | tid_t commit_tid; |
121 | bool needs_barrier = false; | 95 | bool needs_barrier = false; |
122 | 96 | ||
@@ -124,25 +98,24 @@ int ext4_sync_file(struct file *file, loff_t start, loff_t end, int datasync) | |||
124 | 98 | ||
125 | trace_ext4_sync_file_enter(file, datasync); | 99 | trace_ext4_sync_file_enter(file, datasync); |
126 | 100 | ||
127 | ret = filemap_write_and_wait_range(inode->i_mapping, start, end); | 101 | if (inode->i_sb->s_flags & MS_RDONLY) { |
128 | if (ret) | 102 | /* Make sure that we read updated s_mount_flags value */ |
129 | return ret; | 103 | smp_rmb(); |
130 | mutex_lock(&inode->i_mutex); | 104 | if (EXT4_SB(inode->i_sb)->s_mount_flags & EXT4_MF_FS_ABORTED) |
131 | 105 | ret = -EROFS; | |
132 | if (inode->i_sb->s_flags & MS_RDONLY) | ||
133 | goto out; | ||
134 | |||
135 | ret = ext4_flush_unwritten_io(inode); | ||
136 | if (ret < 0) | ||
137 | goto out; | 106 | goto out; |
107 | } | ||
138 | 108 | ||
139 | if (!journal) { | 109 | if (!journal) { |
140 | ret = __sync_inode(inode, datasync); | 110 | ret = generic_file_fsync(file, start, end, datasync); |
141 | if (!ret && !hlist_empty(&inode->i_dentry)) | 111 | if (!ret && !hlist_empty(&inode->i_dentry)) |
142 | ret = ext4_sync_parent(inode); | 112 | ret = ext4_sync_parent(inode); |
143 | goto out; | 113 | goto out; |
144 | } | 114 | } |
145 | 115 | ||
116 | ret = filemap_write_and_wait_range(inode->i_mapping, start, end); | ||
117 | if (ret) | ||
118 | return ret; | ||
146 | /* | 119 | /* |
147 | * data=writeback,ordered: | 120 | * data=writeback,ordered: |
148 | * The caller's filemap_fdatawrite()/wait will sync the data. | 121 | * The caller's filemap_fdatawrite()/wait will sync the data. |
@@ -172,8 +145,7 @@ int ext4_sync_file(struct file *file, loff_t start, loff_t end, int datasync) | |||
172 | if (!ret) | 145 | if (!ret) |
173 | ret = err; | 146 | ret = err; |
174 | } | 147 | } |
175 | out: | 148 | out: |
176 | mutex_unlock(&inode->i_mutex); | ||
177 | trace_ext4_sync_file_exit(inode, ret); | 149 | trace_ext4_sync_file_exit(inode, ret); |
178 | return ret; | 150 | return ret; |
179 | } | 151 | } |