1aa91696eSMartin K. Petersen #ifndef _SCSI_DISK_H 2aa91696eSMartin K. Petersen #define _SCSI_DISK_H 3aa91696eSMartin K. Petersen 4aa91696eSMartin K. Petersen /* 5aa91696eSMartin K. Petersen * More than enough for everybody ;) The huge number of majors 6aa91696eSMartin K. Petersen * is a leftover from 16bit dev_t days, we don't really need that 7aa91696eSMartin K. Petersen * much numberspace. 8aa91696eSMartin K. Petersen */ 9aa91696eSMartin K. Petersen #define SD_MAJORS 16 10aa91696eSMartin K. Petersen 11aa91696eSMartin K. Petersen /* 12aa91696eSMartin K. Petersen * Time out in seconds for disks and Magneto-opticals (which are slower). 13aa91696eSMartin K. Petersen */ 14aa91696eSMartin K. Petersen #define SD_TIMEOUT (30 * HZ) 15aa91696eSMartin K. Petersen #define SD_MOD_TIMEOUT (75 * HZ) 167e660100SJames Bottomley /* 177e660100SJames Bottomley * Flush timeout is a multiplier over the standard device timeout which is 187e660100SJames Bottomley * user modifiable via sysfs but initially set to SD_TIMEOUT 197e660100SJames Bottomley */ 207e660100SJames Bottomley #define SD_FLUSH_TIMEOUT_MULTIPLIER 2 215db44863SMartin K. Petersen #define SD_WRITE_SAME_TIMEOUT (120 * HZ) 22aa91696eSMartin K. Petersen 23aa91696eSMartin K. Petersen /* 24aa91696eSMartin K. Petersen * Number of allowed retries 25aa91696eSMartin K. Petersen */ 26aa91696eSMartin K. Petersen #define SD_MAX_RETRIES 5 27aa91696eSMartin K. Petersen #define SD_PASSTHROUGH_RETRIES 1 2818a4d0a2SMartin K. Petersen #define SD_MAX_MEDIUM_TIMEOUTS 2 29aa91696eSMartin K. Petersen 30aa91696eSMartin K. Petersen /* 31aa91696eSMartin K. Petersen * Size of the initial data buffer for mode and read capacity data 32aa91696eSMartin K. Petersen */ 33aa91696eSMartin K. Petersen #define SD_BUF_SIZE 512 34aa91696eSMartin K. Petersen 3518351070SLinus Torvalds /* 3618351070SLinus Torvalds * Number of sectors at the end of the device to avoid multi-sector 3718351070SLinus Torvalds * accesses to in the case of last_sector_bug 3818351070SLinus Torvalds */ 3918351070SLinus Torvalds #define SD_LAST_BUGGY_SECTORS 8 4018351070SLinus Torvalds 414e7392ecSMartin K. Petersen enum { 424e7392ecSMartin K. Petersen SD_EXT_CDB_SIZE = 32, /* Extended CDB size */ 434e7392ecSMartin K. Petersen SD_MEMPOOL_SIZE = 2, /* CDB pool size */ 444e7392ecSMartin K. Petersen }; 454e7392ecSMartin K. Petersen 46c98a0eb0SMartin K. Petersen enum { 47bcdb247cSMartin K. Petersen SD_DEF_XFER_BLOCKS = 0xffff, 48bcdb247cSMartin K. Petersen SD_MAX_XFER_BLOCKS = 0xffffffff, 495db44863SMartin K. Petersen SD_MAX_WS10_BLOCKS = 0xffff, 505db44863SMartin K. Petersen SD_MAX_WS16_BLOCKS = 0x7fffff, 515db44863SMartin K. Petersen }; 525db44863SMartin K. Petersen 535db44863SMartin K. Petersen enum { 54c98a0eb0SMartin K. Petersen SD_LBP_FULL = 0, /* Full logical block provisioning */ 55c98a0eb0SMartin K. Petersen SD_LBP_UNMAP, /* Use UNMAP command */ 56c98a0eb0SMartin K. Petersen SD_LBP_WS16, /* Use WRITE SAME(16) with UNMAP bit */ 57c98a0eb0SMartin K. Petersen SD_LBP_WS10, /* Use WRITE SAME(10) with UNMAP bit */ 58c98a0eb0SMartin K. Petersen SD_LBP_ZERO, /* Use WRITE SAME(10) with zero payload */ 59c98a0eb0SMartin K. Petersen SD_LBP_DISABLE, /* Discard disabled due to failed cmd */ 60c98a0eb0SMartin K. Petersen }; 61c98a0eb0SMartin K. Petersen 62aa91696eSMartin K. Petersen struct scsi_disk { 63aa91696eSMartin K. Petersen struct scsi_driver *driver; /* always &sd_template */ 64aa91696eSMartin K. Petersen struct scsi_device *device; 65aa91696eSMartin K. Petersen struct device dev; 66aa91696eSMartin K. Petersen struct gendisk *disk; 6789d94756SHannes Reinecke #ifdef CONFIG_BLK_DEV_ZONED 6889d94756SHannes Reinecke unsigned int nr_zones; 6989d94756SHannes Reinecke unsigned int zone_blocks; 7089d94756SHannes Reinecke unsigned int zone_shift; 7189d94756SHannes Reinecke unsigned long *zones_wlock; 7289d94756SHannes Reinecke unsigned int zones_optimal_open; 7389d94756SHannes Reinecke unsigned int zones_optimal_nonseq; 7489d94756SHannes Reinecke unsigned int zones_max_open; 7589d94756SHannes Reinecke #endif 76409f3499SArnd Bergmann atomic_t openers; 77f08bb1e0SMartin K. Petersen sector_t capacity; /* size in logical blocks */ 78bcdb247cSMartin K. Petersen u32 max_xfer_blocks; 79ca369d51SMartin K. Petersen u32 opt_xfer_blocks; 80c98a0eb0SMartin K. Petersen u32 max_ws_blocks; 81c98a0eb0SMartin K. Petersen u32 max_unmap_blocks; 82c98a0eb0SMartin K. Petersen u32 unmap_granularity; 83c98a0eb0SMartin K. Petersen u32 unmap_alignment; 84aa91696eSMartin K. Petersen u32 index; 85526f7c79SMartin K. Petersen unsigned int physical_block_size; 8618a4d0a2SMartin K. Petersen unsigned int max_medium_access_timeouts; 8718a4d0a2SMartin K. Petersen unsigned int medium_access_timed_out; 88aa91696eSMartin K. Petersen u8 media_present; 89aa91696eSMartin K. Petersen u8 write_prot; 90e0597d70SMartin K. Petersen u8 protection_type;/* Data Integrity Field */ 91c98a0eb0SMartin K. Petersen u8 provisioning_mode; 92e0597d70SMartin K. Petersen unsigned ATO : 1; /* state of disk ATO bit */ 9339c60a09SJames Bottomley unsigned cache_override : 1; /* temp override of WCE,RCD */ 94aa91696eSMartin K. Petersen unsigned WCE : 1; /* state of disk WCE bit */ 95aa91696eSMartin K. Petersen unsigned RCD : 1; /* state of disk RCD bit, unused */ 96aa91696eSMartin K. Petersen unsigned DPOFUA : 1; /* state of disk DPOFUA bit */ 9770a9b873SMartin K. Petersen unsigned first_scan : 1; 98c98a0eb0SMartin K. Petersen unsigned lbpme : 1; 99c98a0eb0SMartin K. Petersen unsigned lbprz : 1; 100c98a0eb0SMartin K. Petersen unsigned lbpu : 1; 101c98a0eb0SMartin K. Petersen unsigned lbpws : 1; 102c98a0eb0SMartin K. Petersen unsigned lbpws10 : 1; 103c98a0eb0SMartin K. Petersen unsigned lbpvpd : 1; 10466c28f97SMartin K. Petersen unsigned ws10 : 1; 1055db44863SMartin K. Petersen unsigned ws16 : 1; 10689d94756SHannes Reinecke unsigned rc_basis: 2; 10789d94756SHannes Reinecke unsigned zoned: 2; 10889d94756SHannes Reinecke unsigned urswrz : 1; 1097a38dc0bSHannes Reinecke unsigned ignore_medium_access_errors : 1; 110aa91696eSMartin K. Petersen }; 111aa91696eSMartin K. Petersen #define to_scsi_disk(obj) container_of(obj,struct scsi_disk,dev) 112aa91696eSMartin K. Petersen 1135b635da1SMartin K. Petersen static inline struct scsi_disk *scsi_disk(struct gendisk *disk) 1145b635da1SMartin K. Petersen { 1155b635da1SMartin K. Petersen return container_of(disk->private_data, struct scsi_disk, driver); 1165b635da1SMartin K. Petersen } 1175b635da1SMartin K. Petersen 118aa91696eSMartin K. Petersen #define sd_printk(prefix, sdsk, fmt, a...) \ 119aa91696eSMartin K. Petersen (sdsk)->disk ? \ 12022e0d994SHannes Reinecke sdev_prefix_printk(prefix, (sdsk)->device, \ 12122e0d994SHannes Reinecke (sdsk)->disk->disk_name, fmt, ##a) : \ 122aa91696eSMartin K. Petersen sdev_printk(prefix, (sdsk)->device, fmt, ##a) 123aa91696eSMartin K. Petersen 124b2bff6ceSMartin K. Petersen #define sd_first_printk(prefix, sdsk, fmt, a...) \ 125b2bff6ceSMartin K. Petersen do { \ 126b2bff6ceSMartin K. Petersen if ((sdkp)->first_scan) \ 127b2bff6ceSMartin K. Petersen sd_printk(prefix, sdsk, fmt, ##a); \ 128b2bff6ceSMartin K. Petersen } while (0) 129b2bff6ceSMartin K. Petersen 13018a4d0a2SMartin K. Petersen static inline int scsi_medium_access_command(struct scsi_cmnd *scmd) 13118a4d0a2SMartin K. Petersen { 13218a4d0a2SMartin K. Petersen switch (scmd->cmnd[0]) { 13318a4d0a2SMartin K. Petersen case READ_6: 13418a4d0a2SMartin K. Petersen case READ_10: 13518a4d0a2SMartin K. Petersen case READ_12: 13618a4d0a2SMartin K. Petersen case READ_16: 13718a4d0a2SMartin K. Petersen case SYNCHRONIZE_CACHE: 13818a4d0a2SMartin K. Petersen case VERIFY: 13918a4d0a2SMartin K. Petersen case VERIFY_12: 14018a4d0a2SMartin K. Petersen case VERIFY_16: 14118a4d0a2SMartin K. Petersen case WRITE_6: 14218a4d0a2SMartin K. Petersen case WRITE_10: 14318a4d0a2SMartin K. Petersen case WRITE_12: 14418a4d0a2SMartin K. Petersen case WRITE_16: 14518a4d0a2SMartin K. Petersen case WRITE_SAME: 14618a4d0a2SMartin K. Petersen case WRITE_SAME_16: 14718a4d0a2SMartin K. Petersen case UNMAP: 14818a4d0a2SMartin K. Petersen return 1; 14918a4d0a2SMartin K. Petersen case VARIABLE_LENGTH_CMD: 15018a4d0a2SMartin K. Petersen switch (scmd->cmnd[9]) { 15118a4d0a2SMartin K. Petersen case READ_32: 15218a4d0a2SMartin K. Petersen case VERIFY_32: 15318a4d0a2SMartin K. Petersen case WRITE_32: 15418a4d0a2SMartin K. Petersen case WRITE_SAME_32: 15518a4d0a2SMartin K. Petersen return 1; 15618a4d0a2SMartin K. Petersen } 15718a4d0a2SMartin K. Petersen } 15818a4d0a2SMartin K. Petersen 15918a4d0a2SMartin K. Petersen return 0; 16018a4d0a2SMartin K. Petersen } 16118a4d0a2SMartin K. Petersen 162f08bb1e0SMartin K. Petersen static inline sector_t logical_to_sectors(struct scsi_device *sdev, sector_t blocks) 163f08bb1e0SMartin K. Petersen { 164f08bb1e0SMartin K. Petersen return blocks << (ilog2(sdev->sector_size) - 9); 165f08bb1e0SMartin K. Petersen } 166f08bb1e0SMartin K. Petersen 1676b7e9cdeSMartin K. Petersen static inline unsigned int logical_to_bytes(struct scsi_device *sdev, sector_t blocks) 1686b7e9cdeSMartin K. Petersen { 1696b7e9cdeSMartin K. Petersen return blocks * sdev->sector_size; 1706b7e9cdeSMartin K. Petersen } 1716b7e9cdeSMartin K. Petersen 1726eadc612SDamien Le Moal static inline sector_t bytes_to_logical(struct scsi_device *sdev, unsigned int bytes) 1736eadc612SDamien Le Moal { 1746eadc612SDamien Le Moal return bytes >> ilog2(sdev->sector_size); 1756eadc612SDamien Le Moal } 1766eadc612SDamien Le Moal 17789d94756SHannes Reinecke static inline sector_t sectors_to_logical(struct scsi_device *sdev, sector_t sector) 17889d94756SHannes Reinecke { 17989d94756SHannes Reinecke return sector >> (ilog2(sdev->sector_size) - 9); 18089d94756SHannes Reinecke } 18189d94756SHannes Reinecke 182e0597d70SMartin K. Petersen /* 183c611529eSMartin K. Petersen * Look up the DIX operation based on whether the command is read or 184c611529eSMartin K. Petersen * write and whether dix and dif are enabled. 185c611529eSMartin K. Petersen */ 186c611529eSMartin K. Petersen static inline unsigned int sd_prot_op(bool write, bool dix, bool dif) 187c611529eSMartin K. Petersen { 188c611529eSMartin K. Petersen /* Lookup table: bit 2 (write), bit 1 (dix), bit 0 (dif) */ 189c611529eSMartin K. Petersen const unsigned int ops[] = { /* wrt dix dif */ 190c611529eSMartin K. Petersen SCSI_PROT_NORMAL, /* 0 0 0 */ 191c611529eSMartin K. Petersen SCSI_PROT_READ_STRIP, /* 0 0 1 */ 192c611529eSMartin K. Petersen SCSI_PROT_READ_INSERT, /* 0 1 0 */ 193c611529eSMartin K. Petersen SCSI_PROT_READ_PASS, /* 0 1 1 */ 194c611529eSMartin K. Petersen SCSI_PROT_NORMAL, /* 1 0 0 */ 195c611529eSMartin K. Petersen SCSI_PROT_WRITE_INSERT, /* 1 0 1 */ 196c611529eSMartin K. Petersen SCSI_PROT_WRITE_STRIP, /* 1 1 0 */ 197c611529eSMartin K. Petersen SCSI_PROT_WRITE_PASS, /* 1 1 1 */ 198c611529eSMartin K. Petersen }; 199c611529eSMartin K. Petersen 200c611529eSMartin K. Petersen return ops[write << 2 | dix << 1 | dif]; 201c611529eSMartin K. Petersen } 202c611529eSMartin K. Petersen 203c611529eSMartin K. Petersen /* 204c611529eSMartin K. Petersen * Returns a mask of the protection flags that are valid for a given DIX 205c611529eSMartin K. Petersen * operation. 206c611529eSMartin K. Petersen */ 207c611529eSMartin K. Petersen static inline unsigned int sd_prot_flag_mask(unsigned int prot_op) 208c611529eSMartin K. Petersen { 209c611529eSMartin K. Petersen const unsigned int flag_mask[] = { 210c611529eSMartin K. Petersen [SCSI_PROT_NORMAL] = 0, 211c611529eSMartin K. Petersen 212c611529eSMartin K. Petersen [SCSI_PROT_READ_STRIP] = SCSI_PROT_TRANSFER_PI | 213c611529eSMartin K. Petersen SCSI_PROT_GUARD_CHECK | 214c611529eSMartin K. Petersen SCSI_PROT_REF_CHECK | 215c611529eSMartin K. Petersen SCSI_PROT_REF_INCREMENT, 216c611529eSMartin K. Petersen 217c611529eSMartin K. Petersen [SCSI_PROT_READ_INSERT] = SCSI_PROT_REF_INCREMENT | 218c611529eSMartin K. Petersen SCSI_PROT_IP_CHECKSUM, 219c611529eSMartin K. Petersen 220c611529eSMartin K. Petersen [SCSI_PROT_READ_PASS] = SCSI_PROT_TRANSFER_PI | 221c611529eSMartin K. Petersen SCSI_PROT_GUARD_CHECK | 222c611529eSMartin K. Petersen SCSI_PROT_REF_CHECK | 223c611529eSMartin K. Petersen SCSI_PROT_REF_INCREMENT | 224c611529eSMartin K. Petersen SCSI_PROT_IP_CHECKSUM, 225c611529eSMartin K. Petersen 226c611529eSMartin K. Petersen [SCSI_PROT_WRITE_INSERT] = SCSI_PROT_TRANSFER_PI | 227c611529eSMartin K. Petersen SCSI_PROT_REF_INCREMENT, 228c611529eSMartin K. Petersen 229c611529eSMartin K. Petersen [SCSI_PROT_WRITE_STRIP] = SCSI_PROT_GUARD_CHECK | 230c611529eSMartin K. Petersen SCSI_PROT_REF_CHECK | 231c611529eSMartin K. Petersen SCSI_PROT_REF_INCREMENT | 232c611529eSMartin K. Petersen SCSI_PROT_IP_CHECKSUM, 233c611529eSMartin K. Petersen 234c611529eSMartin K. Petersen [SCSI_PROT_WRITE_PASS] = SCSI_PROT_TRANSFER_PI | 235c611529eSMartin K. Petersen SCSI_PROT_GUARD_CHECK | 236c611529eSMartin K. Petersen SCSI_PROT_REF_CHECK | 237c611529eSMartin K. Petersen SCSI_PROT_REF_INCREMENT | 238c611529eSMartin K. Petersen SCSI_PROT_IP_CHECKSUM, 239c611529eSMartin K. Petersen }; 240c611529eSMartin K. Petersen 241c611529eSMartin K. Petersen return flag_mask[prot_op]; 242c611529eSMartin K. Petersen } 243c611529eSMartin K. Petersen 2444c393e6eSJames Bottomley #ifdef CONFIG_BLK_DEV_INTEGRITY 245af55ff67SMartin K. Petersen 246af55ff67SMartin K. Petersen extern void sd_dif_config_host(struct scsi_disk *); 247c611529eSMartin K. Petersen extern void sd_dif_prepare(struct scsi_cmnd *scmd); 248af55ff67SMartin K. Petersen extern void sd_dif_complete(struct scsi_cmnd *, unsigned int); 249af55ff67SMartin K. Petersen 250af55ff67SMartin K. Petersen #else /* CONFIG_BLK_DEV_INTEGRITY */ 251af55ff67SMartin K. Petersen 2524c393e6eSJames Bottomley static inline void sd_dif_config_host(struct scsi_disk *disk) 2534c393e6eSJames Bottomley { 2544c393e6eSJames Bottomley } 255c611529eSMartin K. Petersen static inline int sd_dif_prepare(struct scsi_cmnd *scmd) 2564c393e6eSJames Bottomley { 2574c393e6eSJames Bottomley return 0; 2584c393e6eSJames Bottomley } 2594c393e6eSJames Bottomley static inline void sd_dif_complete(struct scsi_cmnd *cmd, unsigned int a) 2604c393e6eSJames Bottomley { 2614c393e6eSJames Bottomley } 262af55ff67SMartin K. Petersen 263af55ff67SMartin K. Petersen #endif /* CONFIG_BLK_DEV_INTEGRITY */ 264af55ff67SMartin K. Petersen 26589d94756SHannes Reinecke static inline int sd_is_zoned(struct scsi_disk *sdkp) 26689d94756SHannes Reinecke { 26789d94756SHannes Reinecke return sdkp->zoned == 1 || sdkp->device->type == TYPE_ZBC; 26889d94756SHannes Reinecke } 26989d94756SHannes Reinecke 27089d94756SHannes Reinecke #ifdef CONFIG_BLK_DEV_ZONED 27189d94756SHannes Reinecke 27289d94756SHannes Reinecke extern int sd_zbc_read_zones(struct scsi_disk *sdkp, unsigned char *buffer); 27389d94756SHannes Reinecke extern void sd_zbc_remove(struct scsi_disk *sdkp); 27489d94756SHannes Reinecke extern void sd_zbc_print_zones(struct scsi_disk *sdkp); 275a90dfdc2SDamien Le Moal extern int sd_zbc_write_lock_zone(struct scsi_cmnd *cmd); 276a90dfdc2SDamien Le Moal extern void sd_zbc_write_unlock_zone(struct scsi_cmnd *cmd); 27789d94756SHannes Reinecke extern int sd_zbc_setup_report_cmnd(struct scsi_cmnd *cmd); 27889d94756SHannes Reinecke extern int sd_zbc_setup_reset_cmnd(struct scsi_cmnd *cmd); 27989d94756SHannes Reinecke extern void sd_zbc_complete(struct scsi_cmnd *cmd, unsigned int good_bytes, 28089d94756SHannes Reinecke struct scsi_sense_hdr *sshdr); 28189d94756SHannes Reinecke 28289d94756SHannes Reinecke #else /* CONFIG_BLK_DEV_ZONED */ 28389d94756SHannes Reinecke 28489d94756SHannes Reinecke static inline int sd_zbc_read_zones(struct scsi_disk *sdkp, 28589d94756SHannes Reinecke unsigned char *buf) 28689d94756SHannes Reinecke { 28789d94756SHannes Reinecke return 0; 28889d94756SHannes Reinecke } 28989d94756SHannes Reinecke 29089d94756SHannes Reinecke static inline void sd_zbc_remove(struct scsi_disk *sdkp) {} 29189d94756SHannes Reinecke 29289d94756SHannes Reinecke static inline void sd_zbc_print_zones(struct scsi_disk *sdkp) {} 29389d94756SHannes Reinecke 294a90dfdc2SDamien Le Moal static inline int sd_zbc_write_lock_zone(struct scsi_cmnd *cmd) 29589d94756SHannes Reinecke { 29689d94756SHannes Reinecke /* Let the drive fail requests */ 29789d94756SHannes Reinecke return BLKPREP_OK; 29889d94756SHannes Reinecke } 29989d94756SHannes Reinecke 300a90dfdc2SDamien Le Moal static inline void sd_zbc_write_unlock_zone(struct scsi_cmnd *cmd) {} 30189d94756SHannes Reinecke 30289d94756SHannes Reinecke static inline int sd_zbc_setup_report_cmnd(struct scsi_cmnd *cmd) 30389d94756SHannes Reinecke { 30489d94756SHannes Reinecke return BLKPREP_INVALID; 30589d94756SHannes Reinecke } 30689d94756SHannes Reinecke 30789d94756SHannes Reinecke static inline int sd_zbc_setup_reset_cmnd(struct scsi_cmnd *cmd) 30889d94756SHannes Reinecke { 30989d94756SHannes Reinecke return BLKPREP_INVALID; 31089d94756SHannes Reinecke } 31189d94756SHannes Reinecke 31289d94756SHannes Reinecke static inline void sd_zbc_complete(struct scsi_cmnd *cmd, 31389d94756SHannes Reinecke unsigned int good_bytes, 31489d94756SHannes Reinecke struct scsi_sense_hdr *sshdr) {} 31589d94756SHannes Reinecke 31689d94756SHannes Reinecke #endif /* CONFIG_BLK_DEV_ZONED */ 31789d94756SHannes Reinecke 318aa91696eSMartin K. Petersen #endif /* _SCSI_DISK_H */ 319