@@ -388,6 +388,24 @@ dev_t dm_get_dev_t(const char *path)
EXPORT_SYMBOL_GPL(dm_get_dev_t);
/*
+ * Check if the target supports supports host-managed zoned block devices.
+ */
+static bool device_supported(struct dm_target *ti, struct dm_dev *dev)
+{
+ struct block_device *bdev = dev->bdev;
+ char b[BDEVNAME_SIZE];
+
+ if (bdev_zoned_model(bdev) == BLK_ZONED_HM &&
+ !dm_target_zoned_hm(ti->type)) {
+ DMWARN("%s: Unsupported host-managed zoned block device %s",
+ dm_device_name(ti->table->md), bdevname(bdev, b));
+ return false;
+ }
+
+ return true;
+}
+
+/*
* Add a device to the list, or just increment the usage count if
* it's already present.
*/
@@ -426,6 +444,11 @@ int dm_get_device(struct dm_target *ti, const char *path, fmode_t mode,
}
atomic_inc(&dd->count);
+ if (!device_supported(ti, dd->dm_dev)) {
+ dm_put_device(ti, dd->dm_dev);
+ return -ENOTSUPP;
+ }
+
*result = dd->dm_dev;
return 0;
}
@@ -214,6 +214,12 @@ struct target_type {
#define dm_target_is_wildcard(type) ((type)->features & DM_TARGET_WILDCARD)
/*
+ * Indicates that a target supports host-managed zoned block devices.
+ */
+#define DM_TARGET_ZONED_HM 0x00000010
+#define dm_target_zoned_hm(type) ((type)->features & DM_TARGET_ZONED_HM)
+
+/*
* Some targets need to be sent the same WRITE bio severals times so
* that they can send copies of it to different devices. This function
* examines any supplied bio and returns the number of copies of it the