Skip to content

Commit

Permalink
sed-opal: geometry feature reporting command
Browse files Browse the repository at this point in the history
Locking range start and locking range length
attributes may be require to satisfy restrictions
exposed by OPAL2 geometry feature reporting.

Geometry reporting feature is described in TCG OPAL SSC,
section 3.1.1.4 (ALIGN, LogicalBlockSize, AlignmentGranularity
and LowestAlignedLBA).

4.3.5.2.1.1 RangeStart Behavior:

[ StartAlignment = (RangeStart modulo AlignmentGranularity) - LowestAlignedLBA ]

When processing a Set method or CreateRow method on the Locking
table for a non-Global Range row, if:

a) the AlignmentRequired (ALIGN above) column in the LockingInfo
   table is TRUE;
b) RangeStart is non-zero; and
c) StartAlignment is non-zero, then the method SHALL fail and
   return an error status code INVALID_PARAMETER.

4.3.5.2.1.2 RangeLength Behavior:

If RangeStart is zero, then
	[ LengthAlignment = (RangeLength modulo AlignmentGranularity) - LowestAlignedLBA ]

If RangeStart is non-zero, then
	[ LengthAlignment = (RangeLength modulo AlignmentGranularity) ]

When processing a Set method or CreateRow method on the Locking
table for a non-Global Range row, if:

a) the AlignmentRequired (ALIGN above) column in the LockingInfo
   table is TRUE;
b) RangeLength is non-zero; and
c) LengthAlignment is non-zero, then the method SHALL fail and
   return an error status code INVALID_PARAMETER

In userspace we stuck to logical block size reported by general
block device (via sysfs or ioctl), but we can not read
'AlignmentGranularity' or 'LowestAlignedLBA' anywhere else and
we need to get those values from sed-opal interface otherwise
we will not be able to report or avoid locking range setup
INVALID_PARAMETER errors above.

Signed-off-by: Ondrej Kozina <[email protected]>
Reviewed-by: Christoph Hellwig <[email protected]>
Reviewed-by: Christian Brauner <[email protected]>
Tested-by: Milan Broz <[email protected]>
Link: https://lore.kernel.org/r/[email protected]
Signed-off-by: Jens Axboe <[email protected]>
  • Loading branch information
oniko authored and axboe committed Apr 19, 2023
1 parent 63f8793 commit 9e05a25
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 1 deletion.
29 changes: 28 additions & 1 deletion block/sed-opal.c
Original file line number Diff line number Diff line change
Expand Up @@ -83,8 +83,10 @@ struct opal_dev {
u16 comid;
u32 hsn;
u32 tsn;
u64 align;
u64 align; /* alignment granularity */
u64 lowest_lba;
u32 logical_block_size;
u8 align_required; /* ALIGN: 0 or 1 */

size_t pos;
u8 *cmd;
Expand Down Expand Up @@ -409,6 +411,8 @@ static void check_geometry(struct opal_dev *dev, const void *data)

dev->align = be64_to_cpu(geo->alignment_granularity);
dev->lowest_lba = be64_to_cpu(geo->lowest_aligned_lba);
dev->logical_block_size = be32_to_cpu(geo->logical_block_size);
dev->align_required = geo->reserved01 & 1;
}

static int execute_step(struct opal_dev *dev,
Expand Down Expand Up @@ -2956,6 +2960,26 @@ static int opal_get_status(struct opal_dev *dev, void __user *data)
return 0;
}

static int opal_get_geometry(struct opal_dev *dev, void __user *data)
{
struct opal_geometry geo = {0};

if (check_opal_support(dev))
return -EINVAL;

geo.align = dev->align_required;
geo.logical_block_size = dev->logical_block_size;
geo.alignment_granularity = dev->align;
geo.lowest_aligned_lba = dev->lowest_lba;

if (copy_to_user(data, &geo, sizeof(geo))) {
pr_debug("Error copying geometry data to userspace\n");
return -EFAULT;
}

return 0;
}

int sed_ioctl(struct opal_dev *dev, unsigned int cmd, void __user *arg)
{
void *p;
Expand Down Expand Up @@ -3029,6 +3053,9 @@ int sed_ioctl(struct opal_dev *dev, unsigned int cmd, void __user *arg)
case IOC_OPAL_GET_LR_STATUS:
ret = opal_locking_range_status(dev, p, arg);
break;
case IOC_OPAL_GET_GEOMETRY:
ret = opal_get_geometry(dev, arg);
break;
default:
break;
}
Expand Down
1 change: 1 addition & 0 deletions include/linux/sed-opal.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ static inline bool is_sed_ioctl(unsigned int cmd)
case IOC_OPAL_GENERIC_TABLE_RW:
case IOC_OPAL_GET_STATUS:
case IOC_OPAL_GET_LR_STATUS:
case IOC_OPAL_GET_GEOMETRY:
return true;
}
return false;
Expand Down
13 changes: 13 additions & 0 deletions include/uapi/linux/sed-opal.h
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,18 @@ struct opal_status {
__u32 reserved;
};

/*
* Geometry Reporting per TCG Storage OPAL SSC
* section 3.1.1.4
*/
struct opal_geometry {
__u8 align;
__u32 logical_block_size;
__u64 alignment_granularity;
__u64 lowest_aligned_lba;
__u8 __align[3];
};

#define IOC_OPAL_SAVE _IOW('p', 220, struct opal_lock_unlock)
#define IOC_OPAL_LOCK_UNLOCK _IOW('p', 221, struct opal_lock_unlock)
#define IOC_OPAL_TAKE_OWNERSHIP _IOW('p', 222, struct opal_key)
Expand All @@ -179,5 +191,6 @@ struct opal_status {
#define IOC_OPAL_GENERIC_TABLE_RW _IOW('p', 235, struct opal_read_write_table)
#define IOC_OPAL_GET_STATUS _IOR('p', 236, struct opal_status)
#define IOC_OPAL_GET_LR_STATUS _IOW('p', 237, struct opal_lr_status)
#define IOC_OPAL_GET_GEOMETRY _IOR('p', 238, struct opal_geometry)

#endif /* _UAPI_SED_OPAL_H */

0 comments on commit 9e05a25

Please sign in to comment.