Commit 515ce606 authored by Masato Suzuki's avatar Masato Suzuki Committed by Martin K. Petersen

scsi: sd_zbc: Fix sd_zbc_report_zones() buffer allocation

The function sd_zbc_do_report_zones() issues a REPORT ZONES command with a
buffer size calculated based on the number of zones requested by the
caller. This value should however not exceed the capabilities of the
hardware maximum command size, that is, should not exceed the
max_hw_sectors limit of the device. This problem leads to failures of
report zones commands when re-validating disks with some SAS HBAs.

Fix this by limiting a report zone command buffer size to the minimum of
the device max_hw_sectors and calculated value based on the requested
number of zones. This does not change the semantic of the report_zones file
operation as report zones can always return less zone reports than
requested. Short reports are handled using a loop execution of the
report_zones file operation in the function blk_report_zones().

Before patch 'e76239a3 ("block: add a report_zones method")', report
zones buffer allocation was limited to max_sectors when allocated in
blk_report_zones(). This however does not consider the actual format of the
device reply which is interface dependent.  Limiting the allocation based
on the size of the expected reply format rather than the size of the array
of generic sturct blkzone passed by blk_report_zones() makes more sense.

Fixes: e76239a3 ("block: add a report_zones method")
Cc: [email protected]
Signed-off-by: default avatarMasato Suzuki <[email protected]>
Signed-off-by: Damien Le Moal's avatarDamien Le Moal <[email protected]>
Signed-off-by: Martin K. Petersen's avatarMartin K. Petersen <[email protected]>
parent 79edd00d
......@@ -142,10 +142,12 @@ int sd_zbc_report_zones(struct gendisk *disk, sector_t sector,
* Get a reply buffer for the number of requested zones plus a header.
* For ATA, buffers must be aligned to 512B.
* Get a reply buffer for the number of requested zones plus a header,
* without exceeding the device maximum command size. For ATA disks,
* buffers must be aligned to 512B.
buflen = roundup((nrz + 1) * 64, 512);
buflen = min(queue_max_hw_sectors(disk->queue) << 9,
roundup((nrz + 1) * 64, 512));
buf = kmalloc(buflen, gfp_mask);
if (!buf)
return -ENOMEM;
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment