Merge tag 'for-5.12/block-2021-02-17' of git://git.kernel.dk/linux-block
[linux-2.6-microblaze.git] / block / partitions / core.c
index 4601a84..f3d9ff2 100644 (file)
@@ -197,7 +197,7 @@ static ssize_t part_start_show(struct device *dev,
 static ssize_t part_ro_show(struct device *dev,
                            struct device_attribute *attr, char *buf)
 {
-       return sprintf(buf, "%d\n", dev_to_bdev(dev)->bd_read_only);
+       return sprintf(buf, "%d\n", bdev_read_only(dev_to_bdev(dev)));
 }
 
 static ssize_t part_alignment_offset_show(struct device *dev,
@@ -289,13 +289,7 @@ struct device_type part_type = {
  */
 void delete_partition(struct block_device *part)
 {
-       struct gendisk *disk = part->bd_disk;
-       struct disk_part_tbl *ptbl =
-               rcu_dereference_protected(disk->part_tbl, 1);
-
-       rcu_assign_pointer(ptbl->part[part->bd_partno], NULL);
-       rcu_assign_pointer(ptbl->last_lookup, NULL);
-
+       xa_erase(&part->bd_disk->part_tbl, part->bd_partno);
        kobject_put(part->bd_holder_dir);
        device_del(&part->bd_device);
 
@@ -327,7 +321,6 @@ static struct block_device *add_partition(struct gendisk *disk, int partno,
        struct device *ddev = disk_to_dev(disk);
        struct device *pdev;
        struct block_device *bdev;
-       struct disk_part_tbl *ptbl;
        const char *dname;
        int err;
 
@@ -343,18 +336,13 @@ static struct block_device *add_partition(struct gendisk *disk, int partno,
        case BLK_ZONED_HA:
                pr_info("%s: disabling host aware zoned block device support due to partitions\n",
                        disk->disk_name);
-               disk->queue->limits.zoned = BLK_ZONED_NONE;
+               blk_queue_set_zoned(disk, BLK_ZONED_NONE);
                break;
        case BLK_ZONED_NONE:
                break;
        }
 
-       err = disk_expand_part_tbl(disk, partno);
-       if (err)
-               return ERR_PTR(err);
-       ptbl = rcu_dereference_protected(disk->part_tbl, 1);
-
-       if (ptbl->part[partno])
+       if (xa_load(&disk->part_tbl, partno))
                return ERR_PTR(-EBUSY);
 
        bdev = bdev_alloc(disk, partno);
@@ -363,7 +351,6 @@ static struct block_device *add_partition(struct gendisk *disk, int partno,
 
        bdev->bd_start_sect = start;
        bdev_set_nr_sectors(bdev, len);
-       bdev->bd_read_only = get_disk_ro(disk);
 
        if (info) {
                err = -ENOMEM;
@@ -408,8 +395,10 @@ static struct block_device *add_partition(struct gendisk *disk, int partno,
        }
 
        /* everything is up and running, commence */
+       err = xa_insert(&disk->part_tbl, partno, bdev, GFP_KERNEL);
+       if (err)
+               goto out_del;
        bdev_add(bdev, devt);
-       rcu_assign_pointer(ptbl->part[partno], bdev);
 
        /* suppress uevent if the disk suppresses it */
        if (!dev_get_uevent_suppress(ddev))
@@ -615,7 +604,7 @@ static bool blk_add_partition(struct gendisk *disk, struct block_device *bdev,
 int blk_add_partitions(struct gendisk *disk, struct block_device *bdev)
 {
        struct parsed_partitions *state;
-       int ret = -EAGAIN, p, highest;
+       int ret = -EAGAIN, p;
 
        if (!disk_part_scan_enabled(disk))
                return 0;
@@ -663,15 +652,6 @@ int blk_add_partitions(struct gendisk *disk, struct block_device *bdev)
        /* tell userspace that the media / partition table may have changed */
        kobject_uevent(&disk_to_dev(disk)->kobj, KOBJ_CHANGE);
 
-       /*
-        * Detect the highest partition number and preallocate disk->part_tbl.
-        * This is an optimization and not strictly necessary.
-        */
-       for (p = 1, highest = 0; p < state->limit; p++)
-               if (state->parts[p].size)
-                       highest = p;
-       disk_expand_part_tbl(disk, highest);
-
        for (p = 1; p < state->limit; p++)
                if (!blk_add_partition(disk, bdev, state, p))
                        goto out_free_state;