aboutsummaryrefslogtreecommitdiffstats
path: root/mm
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2009-10-29 12:17:19 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2009-10-29 12:17:19 -0400
commit68e71d1902a820c9bc7a5a6c23260841caafff33 (patch)
treea9ba52bdfef99e7bdc5f8623772d76789f7b7c8b /mm
parent066455d471e997adbcc98dda62eaf461e8b6556e (diff)
parent592b09a42fc3ae6737a0f3ecf4fee42ecd0296f8 (diff)
Merge branch 'for-linus' of git://git.kernel.dk/linux-2.6-block
* 'for-linus' of git://git.kernel.dk/linux-2.6-block: backing-dev: ensure that a removed bdi no longer has super_block referencing it block: use after free bug in __blkdev_get block: silently error unsupported empty barriers too
Diffstat (limited to 'mm')
-rw-r--r--mm/backing-dev.c16
1 files changed, 16 insertions, 0 deletions
diff --git a/mm/backing-dev.c b/mm/backing-dev.c
index 5a37e2055717..1065b715ef64 100644
--- a/mm/backing-dev.c
+++ b/mm/backing-dev.c
@@ -610,6 +610,21 @@ static void bdi_wb_shutdown(struct backing_dev_info *bdi)
610 kthread_stop(wb->task); 610 kthread_stop(wb->task);
611} 611}
612 612
613/*
614 * This bdi is going away now, make sure that no super_blocks point to it
615 */
616static void bdi_prune_sb(struct backing_dev_info *bdi)
617{
618 struct super_block *sb;
619
620 spin_lock(&sb_lock);
621 list_for_each_entry(sb, &super_blocks, s_list) {
622 if (sb->s_bdi == bdi)
623 sb->s_bdi = NULL;
624 }
625 spin_unlock(&sb_lock);
626}
627
613void bdi_unregister(struct backing_dev_info *bdi) 628void bdi_unregister(struct backing_dev_info *bdi)
614{ 629{
615 if (bdi->dev) { 630 if (bdi->dev) {
@@ -682,6 +697,7 @@ void bdi_destroy(struct backing_dev_info *bdi)
682 spin_unlock(&inode_lock); 697 spin_unlock(&inode_lock);
683 } 698 }
684 699
700 bdi_prune_sb(bdi);
685 bdi_unregister(bdi); 701 bdi_unregister(bdi);
686 702
687 for (i = 0; i < NR_BDI_STAT_ITEMS; i++) 703 for (i = 0; i < NR_BDI_STAT_ITEMS; i++)