1 /* 2 * Largely written by Julian Elischer (julian@tfs.com) 3 * for TRW Financial Systems. 4 * 5 * TRW Financial Systems, in accordance with their agreement with Carnegie 6 * Mellon University, makes this software available to CMU to distribute 7 * or use in any manner that they see fit as long as this message is kept with 8 * the software. For this reason TFS also grants any other persons or 9 * organisations permission to use or modify this software. 10 * 11 * TFS supplies this software to be publicly redistributed 12 * on the understanding that TFS is not responsible for the correct 13 * functioning of this software in any circumstances. 14 * 15 * Ported to run under 386BSD by Julian Elischer (julian@tfs.com) Sept 1992 16 * 17 * $FreeBSD: src/sys/cam/scsi/scsi_all.h,v 1.14.2.5 2003/08/24 03:26:37 ken Exp $ 18 * $DragonFly: src/sys/bus/cam/scsi/scsi_all.h,v 1.3 2003/12/29 06:42:10 dillon Exp $ 19 */ 20 21 /* 22 * SCSI general interface description 23 */ 24 25 #ifndef _SCSI_SCSI_ALL_H 26 #define _SCSI_SCSI_ALL_H 1 27 28 #include <sys/cdefs.h> 29 30 #ifdef _KERNEL 31 #include "opt_scsi.h" 32 /* 33 * This is the number of seconds we wait for devices to settle after a SCSI 34 * bus reset. 35 */ 36 #ifndef SCSI_DELAY 37 #define SCSI_DELAY 2000 38 #endif 39 /* 40 * If someone sets this to 0, we assume that they want the minimum 41 * allowable bus settle delay. All devices need _some_ sort of bus settle 42 * delay, so we'll set it to a minimum value of 100ms. 43 */ 44 #if (SCSI_DELAY == 0) 45 #undef SCSI_DELAY 46 #define SCSI_DELAY 100 47 #endif 48 49 /* 50 * Make sure the user isn't using seconds instead of milliseconds. 51 */ 52 #if (SCSI_DELAY < 100) 53 #error "SCSI_DELAY is in milliseconds, not seconds! Please use a larger value" 54 #endif 55 #endif /* _KERNEL */ 56 57 /* 58 * SCSI command format 59 */ 60 61 /* 62 * Define dome bits that are in ALL (or a lot of) scsi commands 63 */ 64 #define SCSI_CTL_LINK 0x01 65 #define SCSI_CTL_FLAG 0x02 66 #define SCSI_CTL_VENDOR 0xC0 67 #define SCSI_CMD_LUN 0xA0 /* these two should not be needed */ 68 #define SCSI_CMD_LUN_SHIFT 5 /* LUN in the cmd is no longer SCSI */ 69 70 #define SCSI_MAX_CDBLEN 16 /* 71 * 16 byte commands are in the 72 * SCSI-3 spec 73 */ 74 #if defined(CAM_MAX_CDBLEN) && (CAM_MAX_CDBLEN < SCSI_MAX_CDBLEN) 75 #error "CAM_MAX_CDBLEN cannot be less than SCSI_MAX_CDBLEN" 76 #endif 77 78 /* 6byte CDBs special case 0 length to be 256 */ 79 #define SCSI_CDB6_LEN(len) ((len) == 0 ? 256 : len) 80 81 /* 82 * This type defines actions to be taken when a particular sense code is 83 * received. Right now, these flags are only defined to take up 16 bits, 84 * but can be expanded in the future if necessary. 85 */ 86 typedef enum { 87 SS_NOP = 0x000000, /* Do nothing */ 88 SS_RETRY = 0x010000, /* Retry the command */ 89 SS_FAIL = 0x020000, /* Bail out */ 90 SS_START = 0x030000, /* Send a Start Unit command to the device, 91 * then retry the original command. 92 */ 93 SS_TUR = 0x040000, /* Send a Test Unit Ready command to the 94 * device, then retry the original command. 95 */ 96 SS_MANUAL = 0x050000, /* 97 * This error must be handled manually, 98 * i.e. the code must look at the asc and 99 * ascq values and determine the proper 100 * course of action. 101 */ 102 SS_TURSTART = 0x060000, /* 103 * Send a Test Unit Ready command to the 104 * device, and if that fails, send a start 105 * unit. 106 */ 107 SS_MASK = 0xff0000 108 } scsi_sense_action; 109 110 typedef enum { 111 SSQ_NONE = 0x0000, 112 SSQ_DECREMENT_COUNT = 0x0100, /* Decrement the retry count */ 113 SSQ_MANY = 0x0200, /* send lots of recovery commands */ 114 SSQ_RANGE = 0x0400, /* 115 * Yes, this is a hack. Basically, 116 * if this flag is set then it 117 * represents an ascq range. The 118 * "correct" way to implement the 119 * ranges might be to add a special 120 * field to the sense code table, 121 * but that would take up a lot of 122 * additional space. This solution 123 * isn't as elegant, but is more 124 * space efficient. 125 */ 126 SSQ_PRINT_SENSE = 0x0800, 127 SSQ_MASK = 0xff00 128 } scsi_sense_action_qualifier; 129 130 /* Mask for error status values */ 131 #define SS_ERRMASK 0xff 132 133 /* The default error action */ 134 #define SS_DEF SS_RETRY|SSQ_DECREMENT_COUNT|SSQ_PRINT_SENSE|EIO 135 136 /* Default error action, without an error return value */ 137 #define SS_NEDEF SS_RETRY|SSQ_DECREMENT_COUNT|SSQ_PRINT_SENSE 138 139 /* Default error action, without sense printing or an error return value */ 140 #define SS_NEPDEF SS_RETRY|SSQ_DECREMENT_COUNT 141 142 struct scsi_generic 143 { 144 u_int8_t opcode; 145 u_int8_t bytes[11]; 146 }; 147 148 struct scsi_request_sense 149 { 150 u_int8_t opcode; 151 u_int8_t byte2; 152 u_int8_t unused[2]; 153 u_int8_t length; 154 u_int8_t control; 155 }; 156 157 struct scsi_test_unit_ready 158 { 159 u_int8_t opcode; 160 u_int8_t byte2; 161 u_int8_t unused[3]; 162 u_int8_t control; 163 }; 164 165 struct scsi_send_diag 166 { 167 u_int8_t opcode; 168 u_int8_t byte2; 169 #define SSD_UOL 0x01 170 #define SSD_DOL 0x02 171 #define SSD_SELFTEST 0x04 172 #define SSD_PF 0x10 173 u_int8_t unused[1]; 174 u_int8_t paramlen[2]; 175 u_int8_t control; 176 }; 177 178 struct scsi_sense 179 { 180 u_int8_t opcode; 181 u_int8_t byte2; 182 u_int8_t unused[2]; 183 u_int8_t length; 184 u_int8_t control; 185 }; 186 187 struct scsi_inquiry 188 { 189 u_int8_t opcode; 190 u_int8_t byte2; 191 #define SI_EVPD 0x01 192 u_int8_t page_code; 193 u_int8_t reserved; 194 u_int8_t length; 195 u_int8_t control; 196 }; 197 198 struct scsi_mode_sense_6 199 { 200 u_int8_t opcode; 201 u_int8_t byte2; 202 #define SMS_DBD 0x08 203 u_int8_t page; 204 #define SMS_PAGE_CODE 0x3F 205 #define SMS_VENDOR_SPECIFIC_PAGE 0x00 206 #define SMS_DISCONNECT_RECONNECT_PAGE 0x02 207 #define SMS_PERIPHERAL_DEVICE_PAGE 0x09 208 #define SMS_CONTROL_MODE_PAGE 0x0A 209 #define SMS_ALL_PAGES_PAGE 0x3F 210 #define SMS_PAGE_CTRL_MASK 0xC0 211 #define SMS_PAGE_CTRL_CURRENT 0x00 212 #define SMS_PAGE_CTRL_CHANGEABLE 0x40 213 #define SMS_PAGE_CTRL_DEFAULT 0x80 214 #define SMS_PAGE_CTRL_SAVED 0xC0 215 u_int8_t unused; 216 u_int8_t length; 217 u_int8_t control; 218 }; 219 220 struct scsi_mode_sense_10 221 { 222 u_int8_t opcode; 223 u_int8_t byte2; /* same bits as small version */ 224 u_int8_t page; /* same bits as small version */ 225 u_int8_t unused[4]; 226 u_int8_t length[2]; 227 u_int8_t control; 228 }; 229 230 struct scsi_mode_select_6 231 { 232 u_int8_t opcode; 233 u_int8_t byte2; 234 #define SMS_SP 0x01 235 #define SMS_PF 0x10 236 u_int8_t unused[2]; 237 u_int8_t length; 238 u_int8_t control; 239 }; 240 241 struct scsi_mode_select_10 242 { 243 u_int8_t opcode; 244 u_int8_t byte2; /* same bits as small version */ 245 u_int8_t unused[5]; 246 u_int8_t length[2]; 247 u_int8_t control; 248 }; 249 250 /* 251 * When sending a mode select to a tape drive, the medium type must be 0. 252 */ 253 struct scsi_mode_hdr_6 254 { 255 u_int8_t datalen; 256 u_int8_t medium_type; 257 u_int8_t dev_specific; 258 u_int8_t block_descr_len; 259 }; 260 261 struct scsi_mode_hdr_10 262 { 263 u_int8_t datalen[2]; 264 u_int8_t medium_type; 265 u_int8_t dev_specific; 266 u_int8_t reserved[2]; 267 u_int8_t block_descr_len[2]; 268 }; 269 270 struct scsi_mode_block_descr 271 { 272 u_int8_t density_code; 273 u_int8_t num_blocks[3]; 274 u_int8_t reserved; 275 u_int8_t block_len[3]; 276 }; 277 278 struct scsi_control_page { 279 u_int8_t page_code; 280 u_int8_t page_length; 281 u_int8_t rlec; 282 #define SCB_RLEC 0x01 /*Report Log Exception Cond*/ 283 u_int8_t queue_flags; 284 #define SCP_QUEUE_ALG_MASK 0xF0 285 #define SCP_QUEUE_ALG_RESTRICTED 0x00 286 #define SCP_QUEUE_ALG_UNRESTRICTED 0x10 287 #define SCP_QUEUE_ERR 0x02 /*Queued I/O aborted for CACs*/ 288 #define SCP_QUEUE_DQUE 0x01 /*Queued I/O disabled*/ 289 u_int8_t eca_and_aen; 290 #define SCP_EECA 0x80 /*Enable Extended CA*/ 291 #define SCP_RAENP 0x04 /*Ready AEN Permission*/ 292 #define SCP_UAAENP 0x02 /*UA AEN Permission*/ 293 #define SCP_EAENP 0x01 /*Error AEN Permission*/ 294 u_int8_t reserved; 295 u_int8_t aen_holdoff_period[2]; 296 }; 297 298 struct scsi_reserve 299 { 300 u_int8_t opcode; 301 u_int8_t byte2; 302 u_int8_t unused[2]; 303 u_int8_t length; 304 u_int8_t control; 305 }; 306 307 struct scsi_release 308 { 309 u_int8_t opcode; 310 u_int8_t byte2; 311 u_int8_t unused[2]; 312 u_int8_t length; 313 u_int8_t control; 314 }; 315 316 struct scsi_prevent 317 { 318 u_int8_t opcode; 319 u_int8_t byte2; 320 u_int8_t unused[2]; 321 u_int8_t how; 322 u_int8_t control; 323 }; 324 #define PR_PREVENT 0x01 325 #define PR_ALLOW 0x00 326 327 struct scsi_sync_cache 328 { 329 u_int8_t opcode; 330 u_int8_t byte2; 331 u_int8_t begin_lba[4]; 332 u_int8_t reserved; 333 u_int8_t lb_count[2]; 334 u_int8_t control; 335 }; 336 337 338 struct scsi_changedef 339 { 340 u_int8_t opcode; 341 u_int8_t byte2; 342 u_int8_t unused1; 343 u_int8_t how; 344 u_int8_t unused[4]; 345 u_int8_t datalen; 346 u_int8_t control; 347 }; 348 349 struct scsi_read_buffer 350 { 351 u_int8_t opcode; 352 u_int8_t byte2; 353 #define RWB_MODE 0x07 354 #define RWB_MODE_HDR_DATA 0x00 355 #define RWB_MODE_DATA 0x02 356 #define RWB_MODE_DOWNLOAD 0x04 357 #define RWB_MODE_DOWNLOAD_SAVE 0x05 358 u_int8_t buffer_id; 359 u_int8_t offset[3]; 360 u_int8_t length[3]; 361 u_int8_t control; 362 }; 363 364 struct scsi_write_buffer 365 { 366 u_int8_t opcode; 367 u_int8_t byte2; 368 u_int8_t buffer_id; 369 u_int8_t offset[3]; 370 u_int8_t length[3]; 371 u_int8_t control; 372 }; 373 374 struct scsi_rw_6 375 { 376 u_int8_t opcode; 377 u_int8_t addr[3]; 378 /* only 5 bits are valid in the MSB address byte */ 379 #define SRW_TOPADDR 0x1F 380 u_int8_t length; 381 u_int8_t control; 382 }; 383 384 struct scsi_rw_10 385 { 386 u_int8_t opcode; 387 #define SRW10_RELADDR 0x01 388 #define SRW10_FUA 0x08 389 #define SRW10_DPO 0x10 390 u_int8_t byte2; 391 u_int8_t addr[4]; 392 u_int8_t reserved; 393 u_int8_t length[2]; 394 u_int8_t control; 395 }; 396 397 struct scsi_rw_12 398 { 399 u_int8_t opcode; 400 #define SRW12_RELADDR 0x01 401 #define SRW12_FUA 0x08 402 #define SRW12_DPO 0x10 403 u_int8_t byte2; 404 u_int8_t addr[4]; 405 u_int8_t length[4]; 406 u_int8_t reserved; 407 u_int8_t control; 408 }; 409 410 struct scsi_start_stop_unit 411 { 412 u_int8_t opcode; 413 u_int8_t byte2; 414 #define SSS_IMMED 0x01 415 u_int8_t reserved[2]; 416 u_int8_t how; 417 #define SSS_START 0x01 418 #define SSS_LOEJ 0x02 419 u_int8_t control; 420 }; 421 422 #define SC_SCSI_1 0x01 423 #define SC_SCSI_2 0x03 424 425 /* 426 * Opcodes 427 */ 428 429 #define TEST_UNIT_READY 0x00 430 #define REQUEST_SENSE 0x03 431 #define READ_6 0x08 432 #define WRITE_6 0x0a 433 #define INQUIRY 0x12 434 #define MODE_SELECT_6 0x15 435 #define MODE_SENSE_6 0x1a 436 #define START_STOP_UNIT 0x1b 437 #define START_STOP 0x1b 438 #define RESERVE 0x16 439 #define RELEASE 0x17 440 #define RECEIVE_DIAGNOSTIC 0x1c 441 #define SEND_DIAGNOSTIC 0x1d 442 #define PREVENT_ALLOW 0x1e 443 #define READ_CAPACITY 0x25 444 #define READ_10 0x28 445 #define WRITE_10 0x2a 446 #define POSITION_TO_ELEMENT 0x2b 447 #define SYNCHRONIZE_CACHE 0x35 448 #define WRITE_BUFFER 0x3b 449 #define READ_BUFFER 0x3c 450 #define CHANGE_DEFINITION 0x40 451 #define MODE_SELECT_10 0x55 452 #define MODE_SENSE_10 0x5A 453 #define MOVE_MEDIUM 0xa5 454 #define READ_12 0xa8 455 #define WRITE_12 0xaa 456 #define READ_ELEMENT_STATUS 0xb8 457 458 459 /* 460 * Device Types 461 */ 462 #define T_DIRECT 0x00 463 #define T_SEQUENTIAL 0x01 464 #define T_PRINTER 0x02 465 #define T_PROCESSOR 0x03 466 #define T_WORM 0x04 467 #define T_CDROM 0x05 468 #define T_SCANNER 0x06 469 #define T_OPTICAL 0x07 470 #define T_CHANGER 0x08 471 #define T_COMM 0x09 472 #define T_ASC0 0x0a 473 #define T_ASC1 0x0b 474 #define T_STORARRAY 0x0c 475 #define T_ENCLOSURE 0x0d 476 #define T_RBC 0x0e 477 #define T_OCRW 0x0f 478 #define T_NODEVICE 0x1F 479 #define T_ANY 0xFF /* Used in Quirk table matches */ 480 481 #define T_REMOV 1 482 #define T_FIXED 0 483 484 /* 485 * This length is the initial inquiry length used by the probe code, as 486 * well as the legnth necessary for scsi_print_inquiry() to function 487 * correctly. If either use requires a different length in the future, 488 * the two values should be de-coupled. 489 */ 490 #define SHORT_INQUIRY_LENGTH 36 491 492 struct scsi_inquiry_data 493 { 494 u_int8_t device; 495 #define SID_TYPE(inq_data) ((inq_data)->device & 0x1f) 496 #define SID_QUAL(inq_data) (((inq_data)->device & 0xE0) >> 5) 497 #define SID_QUAL_LU_CONNECTED 0x00 /* The specified peripheral device 498 * type is currently connected to 499 * logical unit. If the target cannot 500 * determine whether or not a physical 501 * device is currently connected, it 502 * shall also use this peripheral 503 * qualifier when returning the INQUIRY 504 * data. This peripheral qualifier 505 * does not mean that the device is 506 * ready for access by the initiator. 507 */ 508 #define SID_QUAL_LU_OFFLINE 0x01 /* The target is capable of supporting 509 * the specified peripheral device type 510 * on this logical unit; however, the 511 * physical device is not currently 512 * connected to this logical unit. 513 */ 514 #define SID_QUAL_RSVD 0x02 515 #define SID_QUAL_BAD_LU 0x03 /* The target is not capable of 516 * supporting a physical device on 517 * this logical unit. For this 518 * peripheral qualifier the peripheral 519 * device type shall be set to 1Fh to 520 * provide compatibility with previous 521 * versions of SCSI. All other 522 * peripheral device type values are 523 * reserved for this peripheral 524 * qualifier. 525 */ 526 #define SID_QUAL_IS_VENDOR_UNIQUE(inq_data) ((SID_QUAL(inq_data) & 0x08) != 0) 527 u_int8_t dev_qual2; 528 #define SID_QUAL2 0x7F 529 #define SID_IS_REMOVABLE(inq_data) (((inq_data)->dev_qual2 & 0x80) != 0) 530 u_int8_t version; 531 #define SID_ANSI_REV(inq_data) ((inq_data)->version & 0x07) 532 #define SCSI_REV_0 0 533 #define SCSI_REV_CCS 1 534 #define SCSI_REV_2 2 535 #define SCSI_REV_3 3 536 #define SCSI_REV_SPC2 4 537 538 #define SID_ECMA 0x38 539 #define SID_ISO 0xC0 540 u_int8_t response_format; 541 #define SID_AENC 0x80 542 #define SID_TrmIOP 0x40 543 u_int8_t additional_length; 544 u_int8_t reserved[2]; 545 u_int8_t flags; 546 #define SID_SftRe 0x01 547 #define SID_CmdQue 0x02 548 #define SID_Linked 0x08 549 #define SID_Sync 0x10 550 #define SID_WBus16 0x20 551 #define SID_WBus32 0x40 552 #define SID_RelAdr 0x80 553 #define SID_VENDOR_SIZE 8 554 char vendor[SID_VENDOR_SIZE]; 555 #define SID_PRODUCT_SIZE 16 556 char product[SID_PRODUCT_SIZE]; 557 #define SID_REVISION_SIZE 4 558 char revision[SID_REVISION_SIZE]; 559 /* 560 * The following fields were taken from SCSI Primary Commands - 2 561 * (SPC-2) Revision 14, Dated 11 November 1999 562 */ 563 #define SID_VENDOR_SPECIFIC_0_SIZE 20 564 u_int8_t vendor_specific0[SID_VENDOR_SPECIFIC_0_SIZE]; 565 /* 566 * An extension of SCSI Parallel Specific Values 567 */ 568 #define SID_SPI_IUS 0x01 569 #define SID_SPI_QAS 0x02 570 #define SID_SPI_CLOCK_ST 0x00 571 #define SID_SPI_CLOCK_DT 0x04 572 #define SID_SPI_CLOCK_DT_ST 0x0C 573 u_int8_t spi3data; 574 u_int8_t reserved2; 575 /* 576 * Version Descriptors, stored 2 byte values. 577 */ 578 u_int8_t version1[2]; 579 u_int8_t version2[2]; 580 u_int8_t version3[2]; 581 u_int8_t version4[2]; 582 u_int8_t version5[2]; 583 u_int8_t version6[2]; 584 u_int8_t version7[2]; 585 u_int8_t version8[2]; 586 587 u_int8_t reserved3[22]; 588 589 #define SID_VENDOR_SPECIFIC_1_SIZE 160 590 u_int8_t vendor_specific1[SID_VENDOR_SPECIFIC_1_SIZE]; 591 }; 592 593 struct scsi_vpd_unit_serial_number 594 { 595 u_int8_t device; 596 u_int8_t page_code; 597 #define SVPD_UNIT_SERIAL_NUMBER 0x80 598 u_int8_t reserved; 599 u_int8_t length; /* serial number length */ 600 #define SVPD_SERIAL_NUM_SIZE 251 601 u_int8_t serial_num[SVPD_SERIAL_NUM_SIZE]; 602 }; 603 604 struct scsi_read_capacity 605 { 606 u_int8_t opcode; 607 u_int8_t byte2; 608 u_int8_t addr[4]; 609 u_int8_t unused[3]; 610 u_int8_t control; 611 }; 612 613 struct scsi_read_capacity_data 614 { 615 u_int8_t addr[4]; 616 u_int8_t length[4]; 617 }; 618 619 struct scsi_sense_data 620 { 621 u_int8_t error_code; 622 #define SSD_ERRCODE 0x7F 623 #define SSD_CURRENT_ERROR 0x70 624 #define SSD_DEFERRED_ERROR 0x71 625 #define SSD_ERRCODE_VALID 0x80 626 u_int8_t segment; 627 u_int8_t flags; 628 #define SSD_KEY 0x0F 629 #define SSD_KEY_NO_SENSE 0x00 630 #define SSD_KEY_RECOVERED_ERROR 0x01 631 #define SSD_KEY_NOT_READY 0x02 632 #define SSD_KEY_MEDIUM_ERROR 0x03 633 #define SSD_KEY_HARDWARE_ERROR 0x04 634 #define SSD_KEY_ILLEGAL_REQUEST 0x05 635 #define SSD_KEY_UNIT_ATTENTION 0x06 636 #define SSD_KEY_DATA_PROTECT 0x07 637 #define SSD_KEY_BLANK_CHECK 0x08 638 #define SSD_KEY_Vendor_Specific 0x09 639 #define SSD_KEY_COPY_ABORTED 0x0a 640 #define SSD_KEY_ABORTED_COMMAND 0x0b 641 #define SSD_KEY_EQUAL 0x0c 642 #define SSD_KEY_VOLUME_OVERFLOW 0x0d 643 #define SSD_KEY_MISCOMPARE 0x0e 644 #define SSD_KEY_RESERVED 0x0f 645 #define SSD_ILI 0x20 646 #define SSD_EOM 0x40 647 #define SSD_FILEMARK 0x80 648 u_int8_t info[4]; 649 u_int8_t extra_len; 650 u_int8_t cmd_spec_info[4]; 651 u_int8_t add_sense_code; 652 u_int8_t add_sense_code_qual; 653 u_int8_t fru; 654 u_int8_t sense_key_spec[3]; 655 #define SSD_SCS_VALID 0x80 656 #define SSD_FIELDPTR_CMD 0x40 657 #define SSD_BITPTR_VALID 0x08 658 #define SSD_BITPTR_VALUE 0x07 659 #define SSD_MIN_SIZE 18 660 u_int8_t extra_bytes[14]; 661 #define SSD_FULL_SIZE sizeof(struct scsi_sense_data) 662 }; 663 664 struct scsi_mode_header_6 665 { 666 u_int8_t data_length; /* Sense data length */ 667 u_int8_t medium_type; 668 u_int8_t dev_spec; 669 u_int8_t blk_desc_len; 670 }; 671 672 struct scsi_mode_header_10 673 { 674 u_int8_t data_length[2];/* Sense data length */ 675 u_int8_t medium_type; 676 u_int8_t dev_spec; 677 u_int8_t unused[2]; 678 u_int8_t blk_desc_len[2]; 679 }; 680 681 struct scsi_mode_page_header 682 { 683 u_int8_t page_code; 684 u_int8_t page_length; 685 }; 686 687 struct scsi_mode_blk_desc 688 { 689 u_int8_t density; 690 u_int8_t nblocks[3]; 691 u_int8_t reserved; 692 u_int8_t blklen[3]; 693 }; 694 695 #define SCSI_DEFAULT_DENSITY 0x00 /* use 'default' density */ 696 #define SCSI_SAME_DENSITY 0x7f /* use 'same' density- >= SCSI-2 only */ 697 /* 698 * Status Byte 699 */ 700 #define SCSI_STATUS_OK 0x00 701 #define SCSI_STATUS_CHECK_COND 0x02 702 #define SCSI_STATUS_COND_MET 0x04 703 #define SCSI_STATUS_BUSY 0x08 704 #define SCSI_STATUS_INTERMED 0x10 705 #define SCSI_STATUS_INTERMED_COND_MET 0x14 706 #define SCSI_STATUS_RESERV_CONFLICT 0x18 707 #define SCSI_STATUS_CMD_TERMINATED 0x22 708 #define SCSI_STATUS_QUEUE_FULL 0x28 709 710 struct scsi_inquiry_pattern { 711 u_int8_t type; 712 u_int8_t media_type; 713 #define SIP_MEDIA_REMOVABLE 0x01 714 #define SIP_MEDIA_FIXED 0x02 715 const char *vendor; 716 const char *product; 717 const char *revision; 718 }; 719 720 struct scsi_static_inquiry_pattern { 721 u_int8_t type; 722 u_int8_t media_type; 723 char vendor[SID_VENDOR_SIZE+1]; 724 char product[SID_PRODUCT_SIZE+1]; 725 char revision[SID_REVISION_SIZE+1]; 726 }; 727 728 struct scsi_sense_quirk_entry { 729 struct scsi_inquiry_pattern inq_pat; 730 int num_ascs; 731 struct asc_table_entry *asc_info; 732 }; 733 734 struct asc_table_entry { 735 u_int8_t asc; 736 u_int8_t ascq; 737 u_int32_t action; 738 #if !defined(SCSI_NO_SENSE_STRINGS) 739 const char *desc; 740 #endif 741 }; 742 743 struct op_table_entry { 744 u_int8_t opcode; 745 u_int16_t opmask; 746 const char *desc; 747 }; 748 749 struct scsi_op_quirk_entry { 750 struct scsi_inquiry_pattern inq_pat; 751 int num_ops; 752 struct op_table_entry *op_table; 753 }; 754 755 756 struct ccb_scsiio; 757 struct cam_periph; 758 union ccb; 759 #ifndef _KERNEL 760 struct cam_device; 761 #endif 762 763 extern const char *scsi_sense_key_text[]; 764 765 __BEGIN_DECLS 766 const char * scsi_sense_desc(int asc, int ascq, 767 struct scsi_inquiry_data *inq_data); 768 scsi_sense_action scsi_error_action(int asc, int ascq, 769 struct scsi_inquiry_data *inq_data); 770 #ifdef _KERNEL 771 void scsi_sense_print(struct ccb_scsiio *csio); 772 int scsi_interpret_sense(union ccb *ccb, 773 u_int32_t sense_flags, 774 u_int32_t *relsim_flags, 775 u_int32_t *reduction, 776 u_int32_t *timeout, 777 scsi_sense_action error_action); 778 #else 779 char * scsi_sense_string(struct cam_device *device, 780 struct ccb_scsiio *csio, 781 char *str, int str_len); 782 void scsi_sense_print(struct cam_device *device, 783 struct ccb_scsiio *csio, FILE *ofile); 784 int scsi_interpret_sense(struct cam_device *device, 785 union ccb *ccb, 786 u_int32_t sense_flags, 787 u_int32_t *relsim_flags, 788 u_int32_t *reduction, 789 u_int32_t *timeout, 790 scsi_sense_action error_action); 791 #endif /* _KERNEL */ 792 793 #define SF_RETRY_UA 0x01 794 #define SF_NO_PRINT 0x02 795 #define SF_QUIET_IR 0x04 /* Be quiet about Illegal Request reponses */ 796 #define SF_PRINT_ALWAYS 0x08 797 #define SF_RETRY_SELTO 0x10 /* Retry selection timeouts */ 798 799 800 const char * scsi_op_desc(u_int16_t opcode, 801 struct scsi_inquiry_data *inq_data); 802 char * scsi_cdb_string(u_int8_t *cdb_ptr, char *cdb_string, 803 size_t len); 804 805 void scsi_print_inquiry(struct scsi_inquiry_data *inq_data); 806 807 u_int scsi_calc_syncsrate(u_int period_factor); 808 u_int scsi_calc_syncparam(u_int period); 809 810 void scsi_test_unit_ready(struct ccb_scsiio *csio, u_int32_t retries, 811 void (*cbfcnp)(struct cam_periph *, 812 union ccb *), 813 u_int8_t tag_action, 814 u_int8_t sense_len, u_int32_t timeout); 815 816 void scsi_request_sense(struct ccb_scsiio *csio, u_int32_t retries, 817 void (*cbfcnp)(struct cam_periph *, 818 union ccb *), 819 void *data_ptr, u_int8_t dxfer_len, 820 u_int8_t tag_action, u_int8_t sense_len, 821 u_int32_t timeout); 822 823 void scsi_inquiry(struct ccb_scsiio *csio, u_int32_t retries, 824 void (*cbfcnp)(struct cam_periph *, union ccb *), 825 u_int8_t tag_action, u_int8_t *inq_buf, 826 u_int32_t inq_len, int evpd, u_int8_t page_code, 827 u_int8_t sense_len, u_int32_t timeout); 828 829 void scsi_mode_sense(struct ccb_scsiio *csio, u_int32_t retries, 830 void (*cbfcnp)(struct cam_periph *, 831 union ccb *), 832 u_int8_t tag_action, int dbd, 833 u_int8_t page_code, u_int8_t page, 834 u_int8_t *param_buf, u_int32_t param_len, 835 u_int8_t sense_len, u_int32_t timeout); 836 void scsi_mode_sense_len(struct ccb_scsiio *csio, u_int32_t retries, 837 void (*cbfcnp)(struct cam_periph *, 838 union ccb *), 839 u_int8_t tag_action, int dbd, 840 u_int8_t page_code, u_int8_t page, 841 u_int8_t *param_buf, u_int32_t param_len, 842 int minimum_cmd_size, u_int8_t sense_len, 843 u_int32_t timeout); 844 845 void scsi_mode_select(struct ccb_scsiio *csio, u_int32_t retries, 846 void (*cbfcnp)(struct cam_periph *, 847 union ccb *), 848 u_int8_t tag_action, int scsi_page_fmt, 849 int save_pages, u_int8_t *param_buf, 850 u_int32_t param_len, u_int8_t sense_len, 851 u_int32_t timeout); 852 853 void scsi_mode_select_len(struct ccb_scsiio *csio, u_int32_t retries, 854 void (*cbfcnp)(struct cam_periph *, 855 union ccb *), 856 u_int8_t tag_action, int scsi_page_fmt, 857 int save_pages, u_int8_t *param_buf, 858 u_int32_t param_len, int minimum_cmd_size, 859 u_int8_t sense_len, u_int32_t timeout); 860 861 void scsi_read_capacity(struct ccb_scsiio *csio, u_int32_t retries, 862 void (*cbfcnp)(struct cam_periph *, 863 union ccb *), u_int8_t tag_action, 864 struct scsi_read_capacity_data *rcap_buf, 865 u_int8_t sense_len, u_int32_t timeout); 866 867 void scsi_prevent(struct ccb_scsiio *csio, u_int32_t retries, 868 void (*cbfcnp)(struct cam_periph *, union ccb *), 869 u_int8_t tag_action, u_int8_t action, 870 u_int8_t sense_len, u_int32_t timeout); 871 872 void scsi_synchronize_cache(struct ccb_scsiio *csio, 873 u_int32_t retries, 874 void (*cbfcnp)(struct cam_periph *, 875 union ccb *), u_int8_t tag_action, 876 u_int32_t begin_lba, u_int16_t lb_count, 877 u_int8_t sense_len, u_int32_t timeout); 878 879 void scsi_read_write(struct ccb_scsiio *csio, u_int32_t retries, 880 void (*cbfcnp)(struct cam_periph *, union ccb *), 881 u_int8_t tag_action, int readop, u_int8_t byte2, 882 int minimum_cmd_size, u_int32_t lba, 883 u_int32_t block_count, u_int8_t *data_ptr, 884 u_int32_t dxfer_len, u_int8_t sense_len, 885 u_int32_t timeout); 886 887 void scsi_start_stop(struct ccb_scsiio *csio, u_int32_t retries, 888 void (*cbfcnp)(struct cam_periph *, union ccb *), 889 u_int8_t tag_action, int start, int load_eject, 890 int immediate, u_int8_t sense_len, u_int32_t timeout); 891 892 int scsi_inquiry_match(caddr_t inqbuffer, caddr_t table_entry); 893 int scsi_static_inquiry_match(caddr_t inqbuffer, 894 caddr_t table_entry); 895 896 static __inline void scsi_extract_sense(struct scsi_sense_data *sense, 897 int *error_code, int *sense_key, 898 int *asc, int *ascq); 899 static __inline void scsi_ulto2b(u_int32_t val, u_int8_t *bytes); 900 static __inline void scsi_ulto3b(u_int32_t val, u_int8_t *bytes); 901 static __inline void scsi_ulto4b(u_int32_t val, u_int8_t *bytes); 902 static __inline u_int32_t scsi_2btoul(u_int8_t *bytes); 903 static __inline u_int32_t scsi_3btoul(u_int8_t *bytes); 904 static __inline int32_t scsi_3btol(u_int8_t *bytes); 905 static __inline u_int32_t scsi_4btoul(u_int8_t *bytes); 906 static __inline void *find_mode_page_6(struct scsi_mode_header_6 *mode_header); 907 static __inline void *find_mode_page_10(struct scsi_mode_header_10 *mode_header); 908 909 static __inline void scsi_extract_sense(struct scsi_sense_data *sense, 910 int *error_code, int *sense_key, 911 int *asc, int *ascq) 912 { 913 *error_code = sense->error_code & SSD_ERRCODE; 914 *sense_key = sense->flags & SSD_KEY; 915 *asc = (sense->extra_len >= 5) ? sense->add_sense_code : 0; 916 *ascq = (sense->extra_len >= 6) ? sense->add_sense_code_qual : 0; 917 } 918 919 static __inline void 920 scsi_ulto2b(u_int32_t val, u_int8_t *bytes) 921 { 922 923 bytes[0] = (val >> 8) & 0xff; 924 bytes[1] = val & 0xff; 925 } 926 927 static __inline void 928 scsi_ulto3b(u_int32_t val, u_int8_t *bytes) 929 { 930 931 bytes[0] = (val >> 16) & 0xff; 932 bytes[1] = (val >> 8) & 0xff; 933 bytes[2] = val & 0xff; 934 } 935 936 static __inline void 937 scsi_ulto4b(u_int32_t val, u_int8_t *bytes) 938 { 939 940 bytes[0] = (val >> 24) & 0xff; 941 bytes[1] = (val >> 16) & 0xff; 942 bytes[2] = (val >> 8) & 0xff; 943 bytes[3] = val & 0xff; 944 } 945 946 static __inline u_int32_t 947 scsi_2btoul(u_int8_t *bytes) 948 { 949 u_int32_t rv; 950 951 rv = (bytes[0] << 8) | 952 bytes[1]; 953 return (rv); 954 } 955 956 static __inline u_int32_t 957 scsi_3btoul(u_int8_t *bytes) 958 { 959 u_int32_t rv; 960 961 rv = (bytes[0] << 16) | 962 (bytes[1] << 8) | 963 bytes[2]; 964 return (rv); 965 } 966 967 static __inline int32_t 968 scsi_3btol(u_int8_t *bytes) 969 { 970 u_int32_t rc = scsi_3btoul(bytes); 971 972 if (rc & 0x00800000) 973 rc |= 0xff000000; 974 975 return (int32_t) rc; 976 } 977 978 static __inline u_int32_t 979 scsi_4btoul(u_int8_t *bytes) 980 { 981 u_int32_t rv; 982 983 rv = (bytes[0] << 24) | 984 (bytes[1] << 16) | 985 (bytes[2] << 8) | 986 bytes[3]; 987 return (rv); 988 } 989 990 /* 991 * Given the pointer to a returned mode sense buffer, return a pointer to 992 * the start of the first mode page. 993 */ 994 static __inline void * 995 find_mode_page_6(struct scsi_mode_header_6 *mode_header) 996 { 997 void *page_start; 998 999 page_start = (void *)((u_int8_t *)&mode_header[1] + 1000 mode_header->blk_desc_len); 1001 1002 return(page_start); 1003 } 1004 1005 static __inline void * 1006 find_mode_page_10(struct scsi_mode_header_10 *mode_header) 1007 { 1008 void *page_start; 1009 1010 page_start = (void *)((u_int8_t *)&mode_header[1] + 1011 scsi_2btoul(mode_header->blk_desc_len)); 1012 1013 return(page_start); 1014 } 1015 1016 __END_DECLS 1017 1018 #endif /*_SCSI_SCSI_ALL_H*/ 1019