aboutsummaryrefslogtreecommitdiffstats
path: root/fs/fs-writeback.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/fs-writeback.c')
-rw-r--r--fs/fs-writeback.c24
1 files changed, 23 insertions, 1 deletions
diff --git a/fs/fs-writeback.c b/fs/fs-writeback.c
index 66889b06d00f..eb8dc1f22775 100644
--- a/fs/fs-writeback.c
+++ b/fs/fs-writeback.c
@@ -165,6 +165,28 @@ static void redirty_tail(struct inode *inode)
165} 165}
166 166
167/* 167/*
168 * Redirty an inode, but mark it as the very next-to-be-written inode on its
169 * superblock's dirty-inode list.
170 * We need to preserve s_dirty's reverse-time-orderedness, so we cheat by
171 * setting this inode's dirtied_when to the same value as that of the inode
172 * which is presently head-of-list, if present head-of-list is newer than this
173 * inode. (head-of-list is the least-recently-dirtied inode: the oldest one).
174 */
175static void redirty_head(struct inode *inode)
176{
177 struct super_block *sb = inode->i_sb;
178
179 if (!list_empty(&sb->s_dirty)) {
180 struct inode *head_inode;
181
182 head_inode = list_entry(sb->s_dirty.prev, struct inode, i_list);
183 if (time_after(inode->dirtied_when, head_inode->dirtied_when))
184 inode->dirtied_when = head_inode->dirtied_when;
185 }
186 list_move_tail(&inode->i_list, &sb->s_dirty);
187}
188
189/*
168 * Write a single inode's dirty pages and inode data out to disk. 190 * Write a single inode's dirty pages and inode data out to disk.
169 * If `wait' is set, wait on the writeout. 191 * If `wait' is set, wait on the writeout.
170 * 192 *
@@ -225,7 +247,7 @@ __sync_single_inode(struct inode *inode, struct writeback_control *wbc)
225 * uncongested. 247 * uncongested.
226 */ 248 */
227 inode->i_state |= I_DIRTY_PAGES; 249 inode->i_state |= I_DIRTY_PAGES;
228 list_move_tail(&inode->i_list, &sb->s_dirty); 250 redirty_head(inode);
229 } else { 251 } else {
230 /* 252 /*
231 * Otherwise fully redirty the inode so that 253 * Otherwise fully redirty the inode so that