📄 aiclib.c
字号:
/* * Implementation of Utility functions for all SCSI device types. * * Copyright (c) 1997, 1998, 1999 Justin T. Gibbs. * Copyright (c) 1997, 1998 Kenneth D. Merry. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions, and the following disclaimer, * without modification, immediately at the beginning of the file. * 2. The name of the author may not be used to endorse or promote products * derived from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * $FreeBSD: src/sys/cam/scsi/scsi_all.c,v 1.38 2002/09/23 04:56:35 mjacob Exp $ * $Id$ */#include <linux/blkdev.h>#include <linux/delay.h>#include <linux/version.h>/* Core SCSI definitions */#include "scsi.h"#include <scsi/scsi_host.h>#include "aiclib.h"#include "cam.h"#ifndef FALSE#define FALSE 0#endif /* FALSE */#ifndef TRUE#define TRUE 1#endif /* TRUE */#ifndef ERESTART#define ERESTART -1 /* restart syscall */#endif#ifndef EJUSTRETURN#define EJUSTRETURN -2 /* don't modify regs, just return */#endifstatic int ascentrycomp(const void *key, const void *member);static int senseentrycomp(const void *key, const void *member);static void fetchtableentries(int sense_key, int asc, int ascq, struct scsi_inquiry_data *, const struct sense_key_table_entry **, const struct asc_table_entry **);static void * scsibsearch(const void *key, const void *base, size_t nmemb, size_t size, int (*compar)(const void *, const void *));typedef int (cam_quirkmatch_t)(caddr_t, caddr_t);static int cam_strmatch(const u_int8_t *str, const u_int8_t *pattern, int str_len);static caddr_t cam_quirkmatch(caddr_t target, caddr_t quirk_table, int num_entries, int entry_size, cam_quirkmatch_t *comp_func);#define SCSI_NO_SENSE_STRINGS 1#if !defined(SCSI_NO_SENSE_STRINGS)#define SST(asc, ascq, action, desc) \ asc, ascq, action, desc#else static const char empty_string[] = "";#define SST(asc, ascq, action, desc) \ asc, ascq, action, empty_string#endif static const struct sense_key_table_entry sense_key_table[] = { { SSD_KEY_NO_SENSE, SS_NOP, "NO SENSE" }, { SSD_KEY_RECOVERED_ERROR, SS_NOP|SSQ_PRINT_SENSE, "RECOVERED ERROR" }, { SSD_KEY_NOT_READY, SS_TUR|SSQ_MANY|SSQ_DECREMENT_COUNT|EBUSY, "NOT READY" }, { SSD_KEY_MEDIUM_ERROR, SS_RDEF, "MEDIUM ERROR" }, { SSD_KEY_HARDWARE_ERROR, SS_RDEF, "HARDWARE FAILURE" }, { SSD_KEY_ILLEGAL_REQUEST, SS_FATAL|EINVAL, "ILLEGAL REQUEST" }, { SSD_KEY_UNIT_ATTENTION, SS_FATAL|ENXIO, "UNIT ATTENTION" }, { SSD_KEY_DATA_PROTECT, SS_FATAL|EACCES, "DATA PROTECT" }, { SSD_KEY_BLANK_CHECK, SS_FATAL|ENOSPC, "BLANK CHECK" }, { SSD_KEY_Vendor_Specific, SS_FATAL|EIO, "Vendor Specific" }, { SSD_KEY_COPY_ABORTED, SS_FATAL|EIO, "COPY ABORTED" }, { SSD_KEY_ABORTED_COMMAND, SS_RDEF, "ABORTED COMMAND" }, { SSD_KEY_EQUAL, SS_NOP, "EQUAL" }, { SSD_KEY_VOLUME_OVERFLOW, SS_FATAL|EIO, "VOLUME OVERFLOW" }, { SSD_KEY_MISCOMPARE, SS_NOP, "MISCOMPARE" }, { SSD_KEY_RESERVED, SS_FATAL|EIO, "RESERVED" }};static const int sense_key_table_size = sizeof(sense_key_table)/sizeof(sense_key_table[0]);static struct asc_table_entry quantum_fireball_entries[] = { {SST(0x04, 0x0b, SS_START|SSQ_DECREMENT_COUNT|ENXIO, "Logical unit not ready, initializing cmd. required")}};static struct asc_table_entry sony_mo_entries[] = { {SST(0x04, 0x00, SS_START|SSQ_DECREMENT_COUNT|ENXIO, "Logical unit not ready, cause not reportable")}};static struct scsi_sense_quirk_entry sense_quirk_table[] = { { /* * The Quantum Fireball ST and SE like to return 0x04 0x0b when * they really should return 0x04 0x02. 0x04,0x0b isn't * defined in any SCSI spec, and it isn't mentioned in the * hardware manual for these drives. */ {T_DIRECT, SIP_MEDIA_FIXED, "QUANTUM", "FIREBALL S*", "*"}, /*num_sense_keys*/0, sizeof(quantum_fireball_entries)/sizeof(struct asc_table_entry), /*sense key entries*/NULL, quantum_fireball_entries }, { /* * This Sony MO drive likes to return 0x04, 0x00 when it * isn't spun up. */ {T_DIRECT, SIP_MEDIA_REMOVABLE, "SONY", "SMO-*", "*"}, /*num_sense_keys*/0, sizeof(sony_mo_entries)/sizeof(struct asc_table_entry), /*sense key entries*/NULL, sony_mo_entries }};static const int sense_quirk_table_size = sizeof(sense_quirk_table)/sizeof(sense_quirk_table[0]);static struct asc_table_entry asc_table[] = {/* * From File: ASC-NUM.TXT * SCSI ASC/ASCQ Assignments * Numeric Sorted Listing * as of 5/12/97 * * D - DIRECT ACCESS DEVICE (SBC) device column key * .T - SEQUENTIAL ACCESS DEVICE (SSC) ------------------- * . L - PRINTER DEVICE (SSC) blank = reserved * . P - PROCESSOR DEVICE (SPC) not blank = allowed * . .W - WRITE ONCE READ MULTIPLE DEVICE (SBC) * . . R - CD DEVICE (MMC) * . . S - SCANNER DEVICE (SGC) * . . .O - OPTICAL MEMORY DEVICE (SBC) * . . . M - MEDIA CHANGER DEVICE (SMC) * . . . C - COMMUNICATION DEVICE (SSC) * . . . .A - STORAGE ARRAY DEVICE (SCC) * . . . . E - ENCLOSURE SERVICES DEVICE (SES) * DTLPWRSOMCAE ASC ASCQ Action Description * ------------ ---- ---- ------ -----------------------------------*//* DTLPWRSOMCAE */{SST(0x00, 0x00, SS_NOP, "No additional sense information") },/* T S */{SST(0x00, 0x01, SS_RDEF, "Filemark detected") },/* T S */{SST(0x00, 0x02, SS_RDEF, "End-of-partition/medium detected") },/* T */{SST(0x00, 0x03, SS_RDEF, "Setmark detected") },/* T S */{SST(0x00, 0x04, SS_RDEF, "Beginning-of-partition/medium detected") },/* T S */{SST(0x00, 0x05, SS_RDEF, "End-of-data detected") },/* DTLPWRSOMCAE */{SST(0x00, 0x06, SS_RDEF, "I/O process terminated") },/* R */{SST(0x00, 0x11, SS_FATAL|EBUSY, "Audio play operation in progress") },/* R */{SST(0x00, 0x12, SS_NOP, "Audio play operation paused") },/* R */{SST(0x00, 0x13, SS_NOP, "Audio play operation successfully completed") },/* R */{SST(0x00, 0x14, SS_RDEF, "Audio play operation stopped due to error") },/* R */{SST(0x00, 0x15, SS_NOP, "No current audio status to return") },/* DTLPWRSOMCAE */{SST(0x00, 0x16, SS_FATAL|EBUSY, "Operation in progress") },/* DTL WRSOM AE */{SST(0x00, 0x17, SS_RDEF, "Cleaning requested") },/* D W O */{SST(0x01, 0x00, SS_RDEF, "No index/sector signal") },/* D WR OM */{SST(0x02, 0x00, SS_RDEF, "No seek complete") },/* DTL W SO */{SST(0x03, 0x00, SS_RDEF, "Peripheral device write fault") },/* T */{SST(0x03, 0x01, SS_RDEF, "No write current") },/* T */{SST(0x03, 0x02, SS_RDEF, "Excessive write errors") },/* DTLPWRSOMCAE */{SST(0x04, 0x00, SS_TUR|SSQ_DELAY|SSQ_MANY|SSQ_DECREMENT_COUNT|EIO, "Logical unit not ready, cause not reportable") },/* DTLPWRSOMCAE */{SST(0x04, 0x01, SS_TUR|SSQ_DELAY|SSQ_MANY|SSQ_DECREMENT_COUNT|EBUSY, "Logical unit is in process of becoming ready") },/* DTLPWRSOMCAE */{SST(0x04, 0x02, SS_START|SSQ_DECREMENT_COUNT|ENXIO, "Logical unit not ready, initializing cmd. required") },/* DTLPWRSOMCAE */{SST(0x04, 0x03, SS_FATAL|ENXIO, "Logical unit not ready, manual intervention required")},/* DTL O */{SST(0x04, 0x04, SS_FATAL|EBUSY, "Logical unit not ready, format in progress") },/* DT W OMCA */{SST(0x04, 0x05, SS_FATAL|EBUSY, "Logical unit not ready, rebuild in progress") },/* DT W OMCA */{SST(0x04, 0x06, SS_FATAL|EBUSY, "Logical unit not ready, recalculation in progress") },/* DTLPWRSOMCAE */{SST(0x04, 0x07, SS_FATAL|EBUSY, "Logical unit not ready, operation in progress") },/* R */{SST(0x04, 0x08, SS_FATAL|EBUSY, "Logical unit not ready, long write in progress") },/* DTL WRSOMCAE */{SST(0x05, 0x00, SS_RDEF, "Logical unit does not respond to selection") },/* D WR OM */{SST(0x06, 0x00, SS_RDEF, "No reference position found") },/* DTL WRSOM */{SST(0x07, 0x00, SS_RDEF, "Multiple peripheral devices selected") },/* DTL WRSOMCAE */{SST(0x08, 0x00, SS_RDEF, "Logical unit communication failure") },/* DTL WRSOMCAE */{SST(0x08, 0x01, SS_RDEF, "Logical unit communication time-out") },/* DTL WRSOMCAE */{SST(0x08, 0x02, SS_RDEF, "Logical unit communication parity error") },/* DT R OM */{SST(0x08, 0x03, SS_RDEF, "Logical unit communication crc error (ultra-dma/32)")},/* DT WR O */{SST(0x09, 0x00, SS_RDEF, "Track following error") },/* WR O */{SST(0x09, 0x01, SS_RDEF, "Tracking servo failure") },/* WR O */{SST(0x09, 0x02, SS_RDEF, "Focus servo failure") },/* WR O */{SST(0x09, 0x03, SS_RDEF, "Spindle servo failure") },/* DT WR O */{SST(0x09, 0x04, SS_RDEF, "Head select fault") },/* DTLPWRSOMCAE */{SST(0x0A, 0x00, SS_FATAL|ENOSPC, "Error log overflow") },/* DTLPWRSOMCAE */{SST(0x0B, 0x00, SS_RDEF, "Warning") },/* DTLPWRSOMCAE */{SST(0x0B, 0x01, SS_RDEF, "Specified temperature exceeded") },/* DTLPWRSOMCAE */{SST(0x0B, 0x02, SS_RDEF, "Enclosure degraded") },/* T RS */{SST(0x0C, 0x00, SS_RDEF, "Write error") },/* D W O */{SST(0x0C, 0x01, SS_NOP|SSQ_PRINT_SENSE, "Write error - recovered with auto reallocation") },/* D W O */{SST(0x0C, 0x02, SS_RDEF, "Write error - auto reallocation failed") },/* D W O */{SST(0x0C, 0x03, SS_RDEF, "Write error - recommend reassignment") },/* DT W O */{SST(0x0C, 0x04, SS_RDEF, "Compression check miscompare error") },/* DT W O */{SST(0x0C, 0x05, SS_RDEF, "Data expansion occurred during compression") },/* DT W O */{SST(0x0C, 0x06, SS_RDEF, "Block not compressible") },/* R */{SST(0x0C, 0x07, SS_RDEF, "Write error - recovery needed") },/* R */{SST(0x0C, 0x08, SS_RDEF, "Write error - recovery failed") },/* R */{SST(0x0C, 0x09, SS_RDEF, "Write error - loss of streaming") },/* R */{SST(0x0C, 0x0A, SS_RDEF, "Write error - padding blocks added") },/* D W O */{SST(0x10, 0x00, SS_RDEF, "ID CRC or ECC error") },/* DT WRSO */{SST(0x11, 0x00, SS_RDEF, "Unrecovered read error") },/* DT W SO */{SST(0x11, 0x01, SS_RDEF, "Read retries exhausted") },/* DT W SO */{SST(0x11, 0x02, SS_RDEF, "Error too long to correct") },/* DT W SO */{SST(0x11, 0x03, SS_RDEF, "Multiple read errors") },/* D W O */{SST(0x11, 0x04, SS_RDEF, "Unrecovered read error - auto reallocate failed") },/* WR O */{SST(0x11, 0x05, SS_RDEF, "L-EC uncorrectable error") },/* WR O */{SST(0x11, 0x06, SS_RDEF, "CIRC unrecovered error") },/* W O */{SST(0x11, 0x07, SS_RDEF, "Data re-synchronization error") },/* T */{SST(0x11, 0x08, SS_RDEF, "Incomplete block read") },/* T */{SST(0x11, 0x09, SS_RDEF, "No gap found") },/* DT O */{SST(0x11, 0x0A, SS_RDEF, "Miscorrected error") },/* D W O */{SST(0x11, 0x0B, SS_RDEF, "Unrecovered read error - recommend reassignment") },/* D W O */{SST(0x11, 0x0C, SS_RDEF, "Unrecovered read error - recommend rewrite the data")},/* DT WR O */{SST(0x11, 0x0D, SS_RDEF, "De-compression CRC error") },/* DT WR O */{SST(0x11, 0x0E, SS_RDEF, "Cannot decompress using declared algorithm") },/* R */{SST(0x11, 0x0F, SS_RDEF, "Error reading UPC/EAN number") },/* R */{SST(0x11, 0x10, SS_RDEF, "Error reading ISRC number") },/* R */{SST(0x11, 0x11, SS_RDEF, "Read error - loss of streaming") },/* D W O */{SST(0x12, 0x00, SS_RDEF, "Address mark not found for id field") },/* D W O */{SST(0x13, 0x00, SS_RDEF, "Address mark not found for data field") },/* DTL WRSO */{SST(0x14, 0x00, SS_RDEF, "Recorded entity not found") },/* DT WR O */{SST(0x14, 0x01, SS_RDEF, "Record not found") },/* T */{SST(0x14, 0x02, SS_RDEF, "Filemark or setmark not found") },/* T */{SST(0x14, 0x03, SS_RDEF, "End-of-data not found") },/* T */{SST(0x14, 0x04, SS_RDEF, "Block sequence error") },/* DT W O */{SST(0x14, 0x05, SS_RDEF, "Record not found - recommend reassignment") },/* DT W O */{SST(0x14, 0x06, SS_RDEF, "Record not found - data auto-reallocated") },/* DTL WRSOM */{SST(0x15, 0x00, SS_RDEF, "Random positioning error") },/* DTL WRSOM */{SST(0x15, 0x01, SS_RDEF, "Mechanical positioning error") },/* DT WR O */{SST(0x15, 0x02, SS_RDEF, "Positioning error detected by read of medium") },/* D W O */{SST(0x16, 0x00, SS_RDEF, "Data synchronization mark error") },/* D W O */{SST(0x16, 0x01, SS_RDEF, "Data sync error - data rewritten") },/* D W O */{SST(0x16, 0x02, SS_RDEF, "Data sync error - recommend rewrite") },/* D W O */{SST(0x16, 0x03, SS_NOP|SSQ_PRINT_SENSE, "Data sync error - data auto-reallocated") },/* D W O */{SST(0x16, 0x04, SS_RDEF, "Data sync error - recommend reassignment") },/* DT WRSO */{SST(0x17, 0x00, SS_NOP|SSQ_PRINT_SENSE,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -