aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJens Axboe <jaxboe@fusionio.com>2010-06-01 05:08:43 -0400
committerJens Axboe <jaxboe@fusionio.com>2010-06-01 05:08:43 -0400
commit0e3c9a2284f5417f196e327c254d0b84c9ee8929 (patch)
treee3fb40ebe7d042b4b3c1042bc7f2edaf7fb6eee0
parentf17625b318d9b151e7bd41e31223e9d89b2aaa77 (diff)
Revert "writeback: fix WB_SYNC_NONE writeback from umount"
This reverts commit e913fc825dc685a444cb4c1d0f9d32f372f59861. We are investigating a hang associated with the WB_SYNC_NONE changes, so revert them for now. Conflicts: fs/fs-writeback.c mm/page-writeback.c Signed-off-by: Jens Axboe <jaxboe@fusionio.com>
-rw-r--r--fs/fs-writeback.c48
-rw-r--r--fs/sync.c2
-rw-r--r--include/linux/backing-dev.h2
-rw-r--r--include/linux/writeback.h10
-rw-r--r--mm/page-writeback.c4
5 files changed, 15 insertions, 51 deletions
diff --git a/fs/fs-writeback.c b/fs/fs-writeback.c
index 6753912641b4..408a7877b79d 100644
--- a/fs/fs-writeback.c
+++ b/fs/fs-writeback.c
@@ -45,7 +45,6 @@ struct wb_writeback_args {
45 unsigned int for_kupdate:1; 45 unsigned int for_kupdate:1;
46 unsigned int range_cyclic:1; 46 unsigned int range_cyclic:1;
47 unsigned int for_background:1; 47 unsigned int for_background:1;
48 unsigned int sb_pinned:1;
49}; 48};
50 49
51/* 50/*
@@ -231,11 +230,6 @@ static void bdi_sync_writeback(struct backing_dev_info *bdi,
231 .sync_mode = WB_SYNC_ALL, 230 .sync_mode = WB_SYNC_ALL,
232 .nr_pages = LONG_MAX, 231 .nr_pages = LONG_MAX,
233 .range_cyclic = 0, 232 .range_cyclic = 0,
234 /*
235 * Setting sb_pinned is not necessary for WB_SYNC_ALL, but
236 * lets make it explicitly clear.
237 */
238 .sb_pinned = 1,
239 }; 233 };
240 struct bdi_work work; 234 struct bdi_work work;
241 235
@@ -251,23 +245,21 @@ static void bdi_sync_writeback(struct backing_dev_info *bdi,
251 * @bdi: the backing device to write from 245 * @bdi: the backing device to write from
252 * @sb: write inodes from this super_block 246 * @sb: write inodes from this super_block
253 * @nr_pages: the number of pages to write 247 * @nr_pages: the number of pages to write
254 * @sb_locked: caller already holds sb umount sem.
255 * 248 *
256 * Description: 249 * Description:
257 * This does WB_SYNC_NONE opportunistic writeback. The IO is only 250 * This does WB_SYNC_NONE opportunistic writeback. The IO is only
258 * started when this function returns, we make no guarentees on 251 * started when this function returns, we make no guarentees on
259 * completion. Caller specifies whether sb umount sem is held already or not. 252 * completion. Caller need not hold sb s_umount semaphore.
260 * 253 *
261 */ 254 */
262void bdi_start_writeback(struct backing_dev_info *bdi, struct super_block *sb, 255void bdi_start_writeback(struct backing_dev_info *bdi, struct super_block *sb,
263 long nr_pages, int sb_locked) 256 long nr_pages)
264{ 257{
265 struct wb_writeback_args args = { 258 struct wb_writeback_args args = {
266 .sb = sb, 259 .sb = sb,
267 .sync_mode = WB_SYNC_NONE, 260 .sync_mode = WB_SYNC_NONE,
268 .nr_pages = nr_pages, 261 .nr_pages = nr_pages,
269 .range_cyclic = 1, 262 .range_cyclic = 1,
270 .sb_pinned = sb_locked,
271 }; 263 };
272 264
273 /* 265 /*
@@ -592,7 +584,7 @@ static enum sb_pin_state pin_sb_for_writeback(struct writeback_control *wbc,
592 /* 584 /*
593 * Caller must already hold the ref for this 585 * Caller must already hold the ref for this
594 */ 586 */
595 if (wbc->sync_mode == WB_SYNC_ALL || wbc->sb_pinned) { 587 if (wbc->sync_mode == WB_SYNC_ALL) {
596 WARN_ON(!rwsem_is_locked(&sb->s_umount)); 588 WARN_ON(!rwsem_is_locked(&sb->s_umount));
597 return SB_NOT_PINNED; 589 return SB_NOT_PINNED;
598 } 590 }
@@ -766,7 +758,6 @@ static long wb_writeback(struct bdi_writeback *wb,
766 .for_kupdate = args->for_kupdate, 758 .for_kupdate = args->for_kupdate,
767 .for_background = args->for_background, 759 .for_background = args->for_background,
768 .range_cyclic = args->range_cyclic, 760 .range_cyclic = args->range_cyclic,
769 .sb_pinned = args->sb_pinned,
770 }; 761 };
771 unsigned long oldest_jif; 762 unsigned long oldest_jif;
772 long wrote = 0; 763 long wrote = 0;
@@ -1214,18 +1205,6 @@ static void wait_sb_inodes(struct super_block *sb)
1214 iput(old_inode); 1205 iput(old_inode);
1215} 1206}
1216 1207
1217static void __writeback_inodes_sb(struct super_block *sb, int sb_locked)
1218{
1219 unsigned long nr_dirty = global_page_state(NR_FILE_DIRTY);
1220 unsigned long nr_unstable = global_page_state(NR_UNSTABLE_NFS);
1221 long nr_to_write;
1222
1223 nr_to_write = nr_dirty + nr_unstable +
1224 (inodes_stat.nr_inodes - inodes_stat.nr_unused);
1225
1226 bdi_start_writeback(sb->s_bdi, sb, nr_to_write, sb_locked);
1227}
1228
1229/** 1208/**
1230 * writeback_inodes_sb - writeback dirty inodes from given super_block 1209 * writeback_inodes_sb - writeback dirty inodes from given super_block
1231 * @sb: the superblock 1210 * @sb: the superblock
@@ -1237,21 +1216,16 @@ static void __writeback_inodes_sb(struct super_block *sb, int sb_locked)
1237 */ 1216 */
1238void writeback_inodes_sb(struct super_block *sb) 1217void writeback_inodes_sb(struct super_block *sb)
1239{ 1218{
1240 __writeback_inodes_sb(sb, 0); 1219 unsigned long nr_dirty = global_page_state(NR_FILE_DIRTY);
1241} 1220 unsigned long nr_unstable = global_page_state(NR_UNSTABLE_NFS);
1242EXPORT_SYMBOL(writeback_inodes_sb); 1221 long nr_to_write;
1243 1222
1244/** 1223 nr_to_write = nr_dirty + nr_unstable +
1245 * writeback_inodes_sb_locked - writeback dirty inodes from given super_block 1224 (inodes_stat.nr_inodes - inodes_stat.nr_unused);
1246 * @sb: the superblock 1225
1247 * 1226 bdi_start_writeback(sb->s_bdi, sb, nr_to_write);
1248 * Like writeback_inodes_sb(), except the caller already holds the
1249 * sb umount sem.
1250 */
1251void writeback_inodes_sb_locked(struct super_block *sb)
1252{
1253 __writeback_inodes_sb(sb, 1);
1254} 1227}
1228EXPORT_SYMBOL(writeback_inodes_sb);
1255 1229
1256/** 1230/**
1257 * writeback_inodes_sb_if_idle - start writeback if none underway 1231 * writeback_inodes_sb_if_idle - start writeback if none underway
diff --git a/fs/sync.c b/fs/sync.c
index e8cbd415e50a..5a537ccd2e85 100644
--- a/fs/sync.c
+++ b/fs/sync.c
@@ -42,7 +42,7 @@ static int __sync_filesystem(struct super_block *sb, int wait)
42 if (wait) 42 if (wait)
43 sync_inodes_sb(sb); 43 sync_inodes_sb(sb);
44 else 44 else
45 writeback_inodes_sb_locked(sb); 45 writeback_inodes_sb(sb);
46 46
47 if (sb->s_op->sync_fs) 47 if (sb->s_op->sync_fs)
48 sb->s_op->sync_fs(sb, wait); 48 sb->s_op->sync_fs(sb, wait);
diff --git a/include/linux/backing-dev.h b/include/linux/backing-dev.h
index e6e0cb5437e6..aee5f6ce166e 100644
--- a/include/linux/backing-dev.h
+++ b/include/linux/backing-dev.h
@@ -106,7 +106,7 @@ int bdi_register_dev(struct backing_dev_info *bdi, dev_t dev);
106void bdi_unregister(struct backing_dev_info *bdi); 106void bdi_unregister(struct backing_dev_info *bdi);
107int bdi_setup_and_register(struct backing_dev_info *, char *, unsigned int); 107int bdi_setup_and_register(struct backing_dev_info *, char *, unsigned int);
108void bdi_start_writeback(struct backing_dev_info *bdi, struct super_block *sb, 108void bdi_start_writeback(struct backing_dev_info *bdi, struct super_block *sb,
109 long nr_pages, int sb_locked); 109 long nr_pages);
110int bdi_writeback_task(struct bdi_writeback *wb); 110int bdi_writeback_task(struct bdi_writeback *wb);
111int bdi_has_dirty_io(struct backing_dev_info *bdi); 111int bdi_has_dirty_io(struct backing_dev_info *bdi);
112void bdi_arm_supers_timer(void); 112void bdi_arm_supers_timer(void);
diff --git a/include/linux/writeback.h b/include/linux/writeback.h
index cc97d6caf2b3..f64134653a8c 100644
--- a/include/linux/writeback.h
+++ b/include/linux/writeback.h
@@ -65,15 +65,6 @@ struct writeback_control {
65 * so we use a single control to update them 65 * so we use a single control to update them
66 */ 66 */
67 unsigned no_nrwrite_index_update:1; 67 unsigned no_nrwrite_index_update:1;
68
69 /*
70 * For WB_SYNC_ALL, the sb must always be pinned. For WB_SYNC_NONE,
71 * the writeback code will pin the sb for the caller. However,
72 * for eg umount, the caller does WB_SYNC_NONE but already has
73 * the sb pinned. If the below is set, caller already has the
74 * sb pinned.
75 */
76 unsigned sb_pinned:1;
77}; 68};
78 69
79/* 70/*
@@ -82,7 +73,6 @@ struct writeback_control {
82struct bdi_writeback; 73struct bdi_writeback;
83int inode_wait(void *); 74int inode_wait(void *);
84void writeback_inodes_sb(struct super_block *); 75void writeback_inodes_sb(struct super_block *);
85void writeback_inodes_sb_locked(struct super_block *);
86int writeback_inodes_sb_if_idle(struct super_block *); 76int writeback_inodes_sb_if_idle(struct super_block *);
87void sync_inodes_sb(struct super_block *); 77void sync_inodes_sb(struct super_block *);
88void writeback_inodes_wbc(struct writeback_control *wbc); 78void writeback_inodes_wbc(struct writeback_control *wbc);
diff --git a/mm/page-writeback.c b/mm/page-writeback.c
index b289310e2c89..5fa63bdf52e4 100644
--- a/mm/page-writeback.c
+++ b/mm/page-writeback.c
@@ -597,7 +597,7 @@ static void balance_dirty_pages(struct address_space *mapping,
597 (!laptop_mode && ((global_page_state(NR_FILE_DIRTY) 597 (!laptop_mode && ((global_page_state(NR_FILE_DIRTY)
598 + global_page_state(NR_UNSTABLE_NFS)) 598 + global_page_state(NR_UNSTABLE_NFS))
599 > background_thresh))) 599 > background_thresh)))
600 bdi_start_writeback(bdi, NULL, 0, 0); 600 bdi_start_writeback(bdi, NULL, 0);
601} 601}
602 602
603void set_page_dirty_balance(struct page *page, int page_mkwrite) 603void set_page_dirty_balance(struct page *page, int page_mkwrite)
@@ -707,7 +707,7 @@ void laptop_mode_timer_fn(unsigned long data)
707 */ 707 */
708 708
709 if (bdi_has_dirty_io(&q->backing_dev_info)) 709 if (bdi_has_dirty_io(&q->backing_dev_info))
710 bdi_start_writeback(&q->backing_dev_info, NULL, nr_pages, 0); 710 bdi_start_writeback(&q->backing_dev_info, NULL, nr_pages);
711} 711}
712 712
713/* 713/*