block: unhash the block device inodes earlier
authorChristoph Hellwig <hch@lst.de>
Thu, 22 Jul 2021 04:56:29 +0000 (06:56 +0200)
committerChristoph Hellwig <hch@lst.de>
Thu, 22 Jul 2021 13:20:26 +0000 (15:20 +0200)
Unhash the block device inodes as early as possible.  This ensures that
the inode and thus block_device an't be found in the inode hash as soon
as we start deleting the disk, instead of finding it and rejecting it
later because GENHD_FL_UP is cleared.

Signed-off-by: Christoph Hellwig <hch@lst.de>
block/genhd.c
block/partitions/core.c

index 298ee78c1bdac63bc3378b2a97dd6101cd649413..7b4beadaa6947726c709cb39687b4c73be6a9d62 100644 (file)
@@ -581,6 +581,8 @@ void del_gendisk(struct gendisk *disk)
        if (WARN_ON_ONCE(!disk->queue))
                return;
 
+       remove_inode_hash(disk->part0->bd_inode);
+
        blk_integrity_del(disk);
        disk_del_events(disk);
 
@@ -592,12 +594,6 @@ void del_gendisk(struct gendisk *disk)
        fsync_bdev(disk->part0);
        __invalidate_device(disk->part0, true);
 
-       /*
-        * Unhash the bdev inode for this device so that it can't be looked
-        * up any more even if openers still hold references to it.
-        */
-       remove_inode_hash(disk->part0->bd_inode);
-
        set_capacity(disk, 0);
 
        if (!(disk->flags & GENHD_FL_HIDDEN)) {
index 9902b1635b7d99d9a1d7c605138595dbb167f918..4540232e68f9aec821a1b79c4e2753a5d872741d 100644 (file)
@@ -285,6 +285,8 @@ static void delete_partition(struct block_device *part)
 {
        lockdep_assert_held(&part->bd_disk->open_mutex);
 
+       remove_inode_hash(part->bd_inode);
+
        fsync_bdev(part);
        __invalidate_device(part, true);
 
@@ -292,12 +294,6 @@ static void delete_partition(struct block_device *part)
        kobject_put(part->bd_holder_dir);
        device_del(&part->bd_device);
 
-       /*
-        * Remove the block device from the inode hash, so that it cannot be
-        * looked up any more even when openers still hold references.
-        */
-       remove_inode_hash(part->bd_inode);
-
        put_device(&part->bd_device);
 }