aboutsummaryrefslogtreecommitdiffstats
path: root/fs/block_dev.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/block_dev.c')
-rw-r--r--fs/block_dev.c36
1 files changed, 36 insertions, 0 deletions
diff --git a/fs/block_dev.c b/fs/block_dev.c
index c2bbe1fb1326..1e519195d45b 100644
--- a/fs/block_dev.c
+++ b/fs/block_dev.c
@@ -1710,3 +1710,39 @@ int __invalidate_device(struct block_device *bdev, bool kill_dirty)
1710 return res; 1710 return res;
1711} 1711}
1712EXPORT_SYMBOL(__invalidate_device); 1712EXPORT_SYMBOL(__invalidate_device);
1713
1714void iterate_bdevs(void (*func)(struct block_device *, void *), void *arg)
1715{
1716 struct inode *inode, *old_inode = NULL;
1717
1718 spin_lock(&inode_sb_list_lock);
1719 list_for_each_entry(inode, &blockdev_superblock->s_inodes, i_sb_list) {
1720 struct address_space *mapping = inode->i_mapping;
1721
1722 spin_lock(&inode->i_lock);
1723 if (inode->i_state & (I_FREEING|I_WILL_FREE|I_NEW) ||
1724 mapping->nrpages == 0) {
1725 spin_unlock(&inode->i_lock);
1726 continue;
1727 }
1728 __iget(inode);
1729 spin_unlock(&inode->i_lock);
1730 spin_unlock(&inode_sb_list_lock);
1731 /*
1732 * We hold a reference to 'inode' so it couldn't have been
1733 * removed from s_inodes list while we dropped the
1734 * inode_sb_list_lock. We cannot iput the inode now as we can
1735 * be holding the last reference and we cannot iput it under
1736 * inode_sb_list_lock. So we keep the reference and iput it
1737 * later.
1738 */
1739 iput(old_inode);
1740 old_inode = inode;
1741
1742 func(I_BDEV(inode), arg);
1743
1744 spin_lock(&inode_sb_list_lock);
1745 }
1746 spin_unlock(&inode_sb_list_lock);
1747 iput(old_inode);
1748}