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.c49
1 files changed, 32 insertions, 17 deletions
diff --git a/fs/block_dev.c b/fs/block_dev.c
index 4a181fcb5175..fe09ef9c21f3 100644
--- a/fs/block_dev.c
+++ b/fs/block_dev.c
@@ -1058,6 +1058,27 @@ retry:
1058 return 0; 1058 return 0;
1059} 1059}
1060 1060
1061static struct gendisk *bdev_get_gendisk(struct block_device *bdev, int *partno)
1062{
1063 struct gendisk *disk = get_gendisk(bdev->bd_dev, partno);
1064
1065 if (!disk)
1066 return NULL;
1067 /*
1068 * Now that we hold gendisk reference we make sure bdev we looked up is
1069 * not stale. If it is, it means device got removed and created before
1070 * we looked up gendisk and we fail open in such case. Associating
1071 * unhashed bdev with newly created gendisk could lead to two bdevs
1072 * (and thus two independent caches) being associated with one device
1073 * which is bad.
1074 */
1075 if (inode_unhashed(bdev->bd_inode)) {
1076 put_disk_and_module(disk);
1077 return NULL;
1078 }
1079 return disk;
1080}
1081
1061/** 1082/**
1062 * bd_start_claiming - start claiming a block device 1083 * bd_start_claiming - start claiming a block device
1063 * @bdev: block device of interest 1084 * @bdev: block device of interest
@@ -1094,7 +1115,7 @@ static struct block_device *bd_start_claiming(struct block_device *bdev,
1094 * @bdev might not have been initialized properly yet, look up 1115 * @bdev might not have been initialized properly yet, look up
1095 * and grab the outer block device the hard way. 1116 * and grab the outer block device the hard way.
1096 */ 1117 */
1097 disk = get_gendisk(bdev->bd_dev, &partno); 1118 disk = bdev_get_gendisk(bdev, &partno);
1098 if (!disk) 1119 if (!disk)
1099 return ERR_PTR(-ENXIO); 1120 return ERR_PTR(-ENXIO);
1100 1121
@@ -1111,8 +1132,7 @@ static struct block_device *bd_start_claiming(struct block_device *bdev,
1111 else 1132 else
1112 whole = bdgrab(bdev); 1133 whole = bdgrab(bdev);
1113 1134
1114 module_put(disk->fops->owner); 1135 put_disk_and_module(disk);
1115 put_disk(disk);
1116 if (!whole) 1136 if (!whole)
1117 return ERR_PTR(-ENOMEM); 1137 return ERR_PTR(-ENOMEM);
1118 1138
@@ -1407,10 +1427,10 @@ static void __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part);
1407static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) 1427static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1408{ 1428{
1409 struct gendisk *disk; 1429 struct gendisk *disk;
1410 struct module *owner;
1411 int ret; 1430 int ret;
1412 int partno; 1431 int partno;
1413 int perm = 0; 1432 int perm = 0;
1433 bool first_open = false;
1414 1434
1415 if (mode & FMODE_READ) 1435 if (mode & FMODE_READ)
1416 perm |= MAY_READ; 1436 perm |= MAY_READ;
@@ -1430,14 +1450,14 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1430 restart: 1450 restart:
1431 1451
1432 ret = -ENXIO; 1452 ret = -ENXIO;
1433 disk = get_gendisk(bdev->bd_dev, &partno); 1453 disk = bdev_get_gendisk(bdev, &partno);
1434 if (!disk) 1454 if (!disk)
1435 goto out; 1455 goto out;
1436 owner = disk->fops->owner;
1437 1456
1438 disk_block_events(disk); 1457 disk_block_events(disk);
1439 mutex_lock_nested(&bdev->bd_mutex, for_part); 1458 mutex_lock_nested(&bdev->bd_mutex, for_part);
1440 if (!bdev->bd_openers) { 1459 if (!bdev->bd_openers) {
1460 first_open = true;
1441 bdev->bd_disk = disk; 1461 bdev->bd_disk = disk;
1442 bdev->bd_queue = disk->queue; 1462 bdev->bd_queue = disk->queue;
1443 bdev->bd_contains = bdev; 1463 bdev->bd_contains = bdev;
@@ -1463,8 +1483,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1463 bdev->bd_queue = NULL; 1483 bdev->bd_queue = NULL;
1464 mutex_unlock(&bdev->bd_mutex); 1484 mutex_unlock(&bdev->bd_mutex);
1465 disk_unblock_events(disk); 1485 disk_unblock_events(disk);
1466 put_disk(disk); 1486 put_disk_and_module(disk);
1467 module_put(owner);
1468 goto restart; 1487 goto restart;
1469 } 1488 }
1470 } 1489 }
@@ -1524,15 +1543,15 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1524 if (ret) 1543 if (ret)
1525 goto out_unlock_bdev; 1544 goto out_unlock_bdev;
1526 } 1545 }
1527 /* only one opener holds refs to the module and disk */
1528 put_disk(disk);
1529 module_put(owner);
1530 } 1546 }
1531 bdev->bd_openers++; 1547 bdev->bd_openers++;
1532 if (for_part) 1548 if (for_part)
1533 bdev->bd_part_count++; 1549 bdev->bd_part_count++;
1534 mutex_unlock(&bdev->bd_mutex); 1550 mutex_unlock(&bdev->bd_mutex);
1535 disk_unblock_events(disk); 1551 disk_unblock_events(disk);
1552 /* only one opener holds refs to the module and disk */
1553 if (!first_open)
1554 put_disk_and_module(disk);
1536 return 0; 1555 return 0;
1537 1556
1538 out_clear: 1557 out_clear:
@@ -1546,8 +1565,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part)
1546 out_unlock_bdev: 1565 out_unlock_bdev:
1547 mutex_unlock(&bdev->bd_mutex); 1566 mutex_unlock(&bdev->bd_mutex);
1548 disk_unblock_events(disk); 1567 disk_unblock_events(disk);
1549 put_disk(disk); 1568 put_disk_and_module(disk);
1550 module_put(owner);
1551 out: 1569 out:
1552 bdput(bdev); 1570 bdput(bdev);
1553 1571
@@ -1770,8 +1788,6 @@ static void __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part)
1770 disk->fops->release(disk, mode); 1788 disk->fops->release(disk, mode);
1771 } 1789 }
1772 if (!bdev->bd_openers) { 1790 if (!bdev->bd_openers) {
1773 struct module *owner = disk->fops->owner;
1774
1775 disk_put_part(bdev->bd_part); 1791 disk_put_part(bdev->bd_part);
1776 bdev->bd_part = NULL; 1792 bdev->bd_part = NULL;
1777 bdev->bd_disk = NULL; 1793 bdev->bd_disk = NULL;
@@ -1779,8 +1795,7 @@ static void __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part)
1779 victim = bdev->bd_contains; 1795 victim = bdev->bd_contains;
1780 bdev->bd_contains = NULL; 1796 bdev->bd_contains = NULL;
1781 1797
1782 put_disk(disk); 1798 put_disk_and_module(disk);
1783 module_put(owner);
1784 } 1799 }
1785 mutex_unlock(&bdev->bd_mutex); 1800 mutex_unlock(&bdev->bd_mutex);
1786 bdput(bdev); 1801 bdput(bdev);