Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

sd: Physical block size and alignment support

Extract physical block size and lowest aligned LBA from READ
CAPACITY(16) response and adjust queue parameters.

Report physical block size and alignment when applicable.

[jejb: fix up trailing whitespace]
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>

authored by

Martin K. Petersen and committed by
James Bottomley
ea09bcc9 c277331d

+22 -2
+21 -2
drivers/scsi/sd.c
··· 1307 1307 int sense_valid = 0; 1308 1308 int the_result; 1309 1309 int retries = 3; 1310 + unsigned int alignment; 1310 1311 unsigned long long lba; 1311 1312 unsigned sector_size; 1312 1313 ··· 1358 1357 sdkp->capacity = 0; 1359 1358 return -EOVERFLOW; 1360 1359 } 1360 + 1361 + /* Logical blocks per physical block exponent */ 1362 + sdkp->hw_sector_size = (1 << (buffer[13] & 0xf)) * sector_size; 1363 + 1364 + /* Lowest aligned logical block */ 1365 + alignment = ((buffer[14] & 0x3f) << 8 | buffer[15]) * sector_size; 1366 + blk_queue_alignment_offset(sdp->request_queue, alignment); 1367 + if (alignment && sdkp->first_scan) 1368 + sd_printk(KERN_NOTICE, sdkp, 1369 + "physical block alignment offset: %u\n", alignment); 1361 1370 1362 1371 sdkp->capacity = lba + 1; 1363 1372 return sector_size; ··· 1420 1409 } 1421 1410 1422 1411 sdkp->capacity = lba + 1; 1412 + sdkp->hw_sector_size = sector_size; 1423 1413 return sector_size; 1424 1414 } 1425 1415 ··· 1533 1521 string_get_size(sz, STRING_UNITS_10, cap_str_10, 1534 1522 sizeof(cap_str_10)); 1535 1523 1536 - if (sdkp->first_scan || old_capacity != sdkp->capacity) 1524 + if (sdkp->first_scan || old_capacity != sdkp->capacity) { 1537 1525 sd_printk(KERN_NOTICE, sdkp, 1538 - "%llu %d-byte hardware sectors: (%s/%s)\n", 1526 + "%llu %d-byte logical blocks: (%s/%s)\n", 1539 1527 (unsigned long long)sdkp->capacity, 1540 1528 sector_size, cap_str_10, cap_str_2); 1529 + 1530 + if (sdkp->hw_sector_size != sector_size) 1531 + sd_printk(KERN_NOTICE, sdkp, 1532 + "%u-byte physical blocks\n", 1533 + sdkp->hw_sector_size); 1534 + } 1541 1535 } 1542 1536 1543 1537 /* Rescale capacity to 512-byte units */ ··· 1556 1538 else if (sector_size == 256) 1557 1539 sdkp->capacity >>= 1; 1558 1540 1541 + blk_queue_physical_block_size(sdp->request_queue, sdkp->hw_sector_size); 1559 1542 sdkp->device->sector_size = sector_size; 1560 1543 } 1561 1544
+1
drivers/scsi/sd.h
··· 45 45 unsigned int openers; /* protected by BKL for now, yuck */ 46 46 sector_t capacity; /* size in 512-byte sectors */ 47 47 u32 index; 48 + unsigned short hw_sector_size; 48 49 u8 media_present; 49 50 u8 write_prot; 50 51 u8 protection_type;/* Data Integrity Field */