1 /* $OpenBSD: atascsi.h,v 1.54 2022/04/09 20:10:26 naddy Exp $ */ 2 3 /* 4 * Copyright (c) 2007 David Gwynne <dlg@openbsd.org> 5 * Copyright (c) 2010 Conformal Systems LLC <info@conformal.com> 6 * Copyright (c) 2010 Jonathan Matthew <jonathan@d14n.org> 7 * 8 * Permission to use, copy, modify, and distribute this software for any 9 * purpose with or without fee is hereby granted, provided that the above 10 * copyright notice and this permission notice appear in all copies. 11 * 12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 13 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 14 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 15 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 16 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 17 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 18 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 19 */ 20 21 #ifndef _DEV_ATA_ATASCSI_H_ 22 #define _DEV_ATA_ATASCSI_H_ 23 24 #include <sys/task.h> 25 26 struct atascsi; 27 struct scsi_link; 28 29 /* 30 * ATA commands 31 */ 32 33 #define ATA_C_READDMA_EXT 0x25 34 #define ATA_C_READ_LOG_EXT 0x2f 35 #define ATA_C_WRITEDMA_EXT 0x35 36 #define ATA_C_READ_FPDMA 0x60 37 #define ATA_C_WRITE_FPDMA 0x61 38 #define ATA_C_PACKET 0xa0 39 #define ATA_C_IDENTIFY_PACKET 0xa1 40 #define ATA_C_READDMA 0xc8 41 #define ATA_C_WRITEDMA 0xca 42 #define ATA_C_STANDBY_IMMED 0xe0 43 #define ATA_C_READ_PM 0xe4 44 #define ATA_C_WRITE_PM 0xe8 45 #define ATA_C_FLUSH_CACHE 0xe7 46 #define ATA_C_FLUSH_CACHE_EXT 0xea /* lba48 */ 47 #define ATA_C_IDENTIFY 0xec 48 #define ATA_C_SET_FEATURES 0xef 49 #define ATA_C_SEC_FREEZE_LOCK 0xf5 50 #define ATA_C_DSM 0x06 51 52 /* 53 * ATA SET FEATURES subcommands (feature field) 54 */ 55 #define ATA_SF_WRITECACHE_EN 0x02 56 #define ATA_SF_XFERMODE 0x03 57 #define ATA_SF_SATA_FEATURE_EN 0x10 58 #define ATA_SF_XFERMODE_UDMA 0x40 59 #define ATA_SF_SATA_FEATURE_DIS 0x90 60 #define ATA_SF_LOOKAHEAD_EN 0xaa 61 62 /* 63 * ATA SET FEATURES args (count field) 64 */ 65 #define ATA_SF_SATA_DEVIPS 0x03 /* Device-initiated power management */ 66 #define ATA_SF_SATA_DEVAPS 0x07 /* Device Automatic Partial to Slumber transitions */ 67 #define ATA_SF_SATA_DEVSLEEP 0x09 /* DevSleep power management state */ 68 69 struct ata_identify { 70 u_int16_t config; /* 0 */ 71 u_int16_t ncyls; /* 1 */ 72 u_int16_t reserved1; /* 2 */ 73 u_int16_t nheads; /* 3 */ 74 u_int16_t track_size; /* 4 */ 75 u_int16_t sector_size; /* 5 */ 76 u_int16_t nsectors; /* 6 */ 77 u_int16_t reserved2[3]; /* 7 vendor unique */ 78 u_int8_t serial[20]; /* 10 */ 79 u_int16_t buffer_type; /* 20 */ 80 u_int16_t buffer_size; /* 21 */ 81 u_int16_t ecc; /* 22 */ 82 u_int8_t firmware[8]; /* 23 */ 83 u_int8_t model[40]; /* 27 */ 84 u_int16_t multi; /* 47 */ 85 u_int16_t dwcap; /* 48 */ 86 u_int16_t cap; /* 49 */ 87 u_int16_t reserved3; /* 50 */ 88 u_int16_t piomode; /* 51 */ 89 u_int16_t dmamode; /* 52 */ 90 u_int16_t validinfo; /* 53 */ 91 #define ATA_ID_VALIDINFO_ULTRADMA 0x0004 92 u_int16_t curcyls; /* 54 */ 93 u_int16_t curheads; /* 55 */ 94 u_int16_t cursectrk; /* 56 */ 95 u_int16_t curseccp[2]; /* 57 */ 96 u_int16_t mult2; /* 59 */ 97 u_int16_t addrsec[2]; /* 60 */ 98 u_int16_t worddma; /* 62 */ 99 u_int16_t dworddma; /* 63 */ 100 u_int16_t advpiomode; /* 64 */ 101 u_int16_t minmwdma; /* 65 */ 102 u_int16_t recmwdma; /* 66 */ 103 u_int16_t minpio; /* 67 */ 104 u_int16_t minpioflow; /* 68 */ 105 u_int16_t add_support; /* 69 */ 106 #define ATA_ID_ADD_SUPPORT_DRT 0x4000 107 u_int16_t reserved4; /* 70 */ 108 u_int16_t typtime[2]; /* 71 */ 109 u_int16_t reserved5[2]; /* 73 */ 110 u_int16_t qdepth; /* 75 */ 111 #define ATA_QDEPTH(_q) (((_q) & 0x1f) + 1) 112 u_int16_t satacap; /* 76 */ 113 #define ATA_SATACAP_GEN1 0x0002 114 #define ATA_SATACAP_GEN2 0x0004 115 #define ATA_SATACAP_GEN3 0x0008 116 #define ATA_SATACAP_NCQ 0x0100 117 #define ATA_SATACAP_HIPM 0x0200 118 #define ATA_SATACAP_HOSTAPS 0x2000 119 #define ATA_SATACAP_DEVAPS 0x4000 120 u_int16_t reserved6; /* 77 */ 121 u_int16_t satafsup; /* 78 */ 122 #define ATA_SATAFSUP_DIPM 0x0008 123 #define ATA_SATAFSUP_DEVSLP 0x0100 124 u_int16_t satafen; /* 79 */ 125 #define ATA_SATAFEN_DIPM 0x0008 126 #define ATA_SATAFEN_DEVSLP 0x0100 127 u_int16_t majver; /* 80 */ 128 u_int16_t minver; /* 81 */ 129 u_int16_t cmdset82; /* 82 */ 130 u_int16_t cmdset83; /* 83 */ 131 u_int16_t cmdset84; /* 84 */ 132 u_int16_t features85; /* 85 */ 133 u_int16_t features86; /* 86 */ 134 u_int16_t features87; /* 87 */ 135 #define ATA_ID_F87_WWN (1<<8) 136 u_int16_t ultradma; /* 88 */ 137 u_int16_t erasetime; /* 89 */ 138 u_int16_t erasetimex; /* 90 */ 139 u_int16_t apm; /* 91 */ 140 u_int16_t masterpw; /* 92 */ 141 u_int16_t hwreset; /* 93 */ 142 u_int16_t acoustic; /* 94 */ 143 u_int16_t stream_min; /* 95 */ 144 u_int16_t stream_xfer_d; /* 96 */ 145 u_int16_t stream_lat; /* 97 */ 146 u_int16_t streamperf[2]; /* 98 */ 147 u_int16_t addrsecxt[4]; /* 100 */ 148 u_int16_t stream_xfer_p; /* 104 */ 149 u_int16_t padding1; /* 105 */ 150 u_int16_t p2l_sect; /* 106 */ 151 #define ATA_ID_P2L_SECT_MASK 0xc000 152 #define ATA_ID_P2L_SECT_VALID 0x4000 153 #define ATA_ID_P2L_SECT_SET 0x2000 154 #define ATA_ID_P2L_SECT_SIZESET 0x1000 155 #define ATA_ID_P2L_SECT_SIZE 0x000f 156 u_int16_t seek_delay; /* 107 */ 157 u_int16_t naa_ieee_oui; /* 108 */ 158 u_int16_t ieee_oui_uid; /* 109 */ 159 u_int16_t uid_mid; /* 110 */ 160 u_int16_t uid_low; /* 111 */ 161 u_int16_t resv_wwn[4]; /* 112 */ 162 u_int16_t incits; /* 116 */ 163 u_int16_t words_lsec[2]; /* 117 */ 164 u_int16_t cmdset119; /* 119 */ 165 u_int16_t features120; /* 120 */ 166 u_int16_t padding2[6]; 167 u_int16_t rmsn; /* 127 */ 168 u_int16_t securestatus; /* 128 */ 169 u_int16_t vendor[31]; /* 129 */ 170 u_int16_t padding3[8]; /* 160 */ 171 u_int16_t form; /* 168 */ 172 #define ATA_ID_FORM_MASK 0x000f 173 u_int16_t data_set_mgmt; /* 169 */ 174 #define ATA_ID_DATA_SET_MGMT_TRIM 0x0001 175 u_int16_t padding4[6]; /* 170 */ 176 u_int16_t curmedser[30]; /* 176 */ 177 u_int16_t sctsupport; /* 206 */ 178 u_int16_t rpm; /* 207 */ 179 u_int16_t padding5[1]; /* 208 */ 180 u_int16_t logical_align; /* 209 */ 181 #define ATA_ID_LALIGN_MASK 0xc000 182 #define ATA_ID_LALIGN_VALID 0x4000 183 #define ATA_ID_LALIGN 0x3fff 184 u_int16_t padding6[45]; /* 210 */ 185 u_int16_t integrity; /* 255 */ 186 } __packed; 187 188 /* 189 * IDENTIFY DEVICE data 190 */ 191 #define ATA_IDENTIFY_WRITECACHE (1 << 5) 192 #define ATA_IDENTIFY_LOOKAHEAD (1 << 6) 193 194 /* 195 * ATA DSM (Data Set Management) subcommands 196 */ 197 #define ATA_DSM_TRIM 0x01 198 199 #define ATA_DSM_TRIM_DESC(_lba, _len) ((_lba) | ((u_int64_t)(_len) << 48)) 200 #define ATA_DSM_TRIM_MAX_LEN 0xffff 201 202 /* 203 * Frame Information Structures 204 */ 205 206 #define ATA_FIS_LENGTH 20 207 208 struct ata_fis_h2d { 209 u_int8_t type; 210 #define ATA_FIS_TYPE_H2D 0x27 211 u_int8_t flags; 212 #define ATA_H2D_FLAGS_CMD (1<<7) 213 u_int8_t command; 214 u_int8_t features; 215 #define ATA_H2D_FEATURES_DMA (1<<0) 216 #define ATA_H2D_FEATURES_DIR (1<<2) 217 #define ATA_H2D_FEATURES_DIR_READ (1<<2) 218 #define ATA_H2D_FEATURES_DIR_WRITE (0<<2) 219 220 u_int8_t lba_low; 221 u_int8_t lba_mid; 222 u_int8_t lba_high; 223 u_int8_t device; 224 #define ATA_H2D_DEVICE_LBA 0x40 225 226 u_int8_t lba_low_exp; 227 u_int8_t lba_mid_exp; 228 u_int8_t lba_high_exp; 229 u_int8_t features_exp; 230 231 u_int8_t sector_count; 232 u_int8_t sector_count_exp; 233 u_int8_t reserved0; 234 u_int8_t control; 235 #define ATA_FIS_CONTROL_SRST 0x04 236 #define ATA_FIS_CONTROL_4BIT 0x08 237 238 u_int8_t reserved1; 239 u_int8_t reserved2; 240 u_int8_t reserved3; 241 u_int8_t reserved4; 242 } __packed; 243 244 struct ata_fis_d2h { 245 u_int8_t type; 246 #define ATA_FIS_TYPE_D2H 0x34 247 u_int8_t flags; 248 #define ATA_D2H_FLAGS_INTR (1<<6) 249 u_int8_t status; 250 u_int8_t error; 251 252 u_int8_t lba_low; 253 u_int8_t lba_mid; 254 u_int8_t lba_high; 255 u_int8_t device; 256 257 u_int8_t lba_low_exp; 258 u_int8_t lba_mid_exp; 259 u_int8_t lba_high_exp; 260 u_int8_t reserved0; 261 262 u_int8_t sector_count; 263 u_int8_t sector_count_exp; 264 u_int8_t reserved1; 265 u_int8_t reserved2; 266 267 u_int8_t reserved3; 268 u_int8_t reserved4; 269 u_int8_t reserved5; 270 u_int8_t reserved6; 271 } __packed; 272 273 /* 274 * SATA log page 10h - 275 * looks like a D2H FIS, with errored tag number in first byte. 276 */ 277 struct ata_log_page_10h { 278 struct ata_fis_d2h err_regs; 279 #define ATA_LOG_10H_TYPE_NOTQUEUED 0x80 280 #define ATA_LOG_10H_TYPE_TAG_MASK 0x1f 281 u_int8_t reserved[256 - sizeof(struct ata_fis_d2h)]; 282 u_int8_t vendor_specific[255]; 283 u_int8_t checksum; 284 } __packed; 285 286 /* 287 * SATA registers 288 */ 289 290 #define SATA_SStatus_DET 0x00f 291 #define SATA_SStatus_DET_NODEV 0x000 292 #define SATA_SStatus_DET_NOPHY 0x001 293 #define SATA_SStatus_DET_DEV 0x003 294 #define SATA_SStatus_DET_OFFLINE 0x004 295 296 #define SATA_SStatus_SPD 0x0f0 297 #define SATA_SStatus_SPD_NONE 0x000 298 #define SATA_SStatus_SPD_1_5 0x010 299 #define SATA_SStatus_SPD_3_0 0x020 300 #define SATA_SStatus_SPD_6_0 0x030 301 302 #define SATA_SStatus_IPM 0xf00 303 #define SATA_SStatus_IPM_NODEV 0x000 304 #define SATA_SStatus_IPM_ACTIVE 0x100 305 #define SATA_SStatus_IPM_PARTIAL 0x200 306 #define SATA_SStatus_IPM_SLUMBER 0x600 307 #define SATA_SStatus_IPM_DEVSLEEP 0x800 308 309 #define SATA_SIGNATURE_PORT_MULTIPLIER 0x96690101 310 #define SATA_SIGNATURE_ATAPI 0xeb140101 311 #define SATA_SIGNATURE_DISK 0x00000101 312 313 /* 314 * ATA interface 315 */ 316 317 struct ata_xfer { 318 struct ata_fis_h2d *fis; 319 struct ata_fis_d2h rfis; 320 u_int8_t *packetcmd; 321 u_int8_t tag; 322 323 void *data; 324 size_t datalen; 325 size_t resid; 326 327 void (*complete)(struct ata_xfer *); 328 struct task task; 329 struct timeout stimeout; 330 u_int timeout; 331 332 int flags; 333 #define ATA_F_READ (1<<0) 334 #define ATA_F_WRITE (1<<1) 335 #define ATA_F_NOWAIT (1<<2) 336 #define ATA_F_POLL (1<<3) 337 #define ATA_F_PIO (1<<4) 338 #define ATA_F_PACKET (1<<5) 339 #define ATA_F_NCQ (1<<6) 340 #define ATA_F_DONE (1<<7) 341 #define ATA_F_GET_RFIS (1<<8) 342 #define ATA_FMT_FLAGS "\020" "\011GET_RFIS" "\010DONE" \ 343 "\007NCQ" "\006PACKET" "\005PIO" \ 344 "\004POLL" "\003NOWAIT" "\002WRITE" \ 345 "\001READ" 346 347 volatile int state; 348 #define ATA_S_SETUP 0 349 #define ATA_S_PENDING 1 350 #define ATA_S_COMPLETE 2 351 #define ATA_S_ERROR 3 352 #define ATA_S_TIMEOUT 4 353 #define ATA_S_ONCHIP 5 354 #define ATA_S_PUT 6 355 #define ATA_S_DONE 7 356 357 void *atascsi_private; 358 359 int pmp_port; 360 }; 361 362 /* 363 * atascsi 364 */ 365 366 struct atascsi_methods { 367 int (*ata_probe)(void *, int, int); 368 void (*ata_free)(void *, int, int); 369 struct ata_xfer * (*ata_get_xfer)(void *, int); 370 void (*ata_put_xfer)(struct ata_xfer *); 371 void (*ata_cmd)(struct ata_xfer *); 372 }; 373 374 struct atascsi_attach_args { 375 void *aaa_cookie; 376 377 const struct atascsi_methods *aaa_methods; 378 void (*aaa_minphys)(struct buf *, 379 struct scsi_link *); 380 int aaa_nports; 381 int aaa_ncmds; 382 int aaa_capability; 383 #define ASAA_CAP_NCQ (1 << 0) 384 #define ASAA_CAP_NEEDS_RESERVED (1 << 1) 385 #define ASAA_CAP_PMP_NCQ (1 << 2) 386 }; 387 388 #define ATA_PORT_T_NONE 0 389 #define ATA_PORT_T_DISK 1 390 #define ATA_PORT_T_ATAPI 2 391 #define ATA_PORT_T_PM 3 392 393 struct atascsi *atascsi_attach(struct device *, struct atascsi_attach_args *); 394 int atascsi_detach(struct atascsi *, int); 395 396 void ata_complete(struct ata_xfer *); 397 398 #endif /* _DEV_ATA_ATASCSI_H_ */ 399