📄 mptscsih.c
字号:
dslprintk((KERN_INFO MYNAM ": spinlock#6\n")); spin_lock_irqsave(&mpt_scsih_taskQ_lock, flags); mpt_scsih_taskQ_bh_active = 0; spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags); return;}#endif /* } *//*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//** * mptscsih_taskmgmt_complete - Callback routine, gets registered to * Fusion MPT base driver * @ioc: Pointer to MPT_ADAPTER structure * @mf: Pointer to SCSI task mgmt request frame * @r: Pointer to SCSI task mgmt reply frame * * This routine is called from mptbase.c::mpt_interrupt() at the completion * of any SCSI task management request. * This routine is registered with the MPT (base) driver at driver * load/init time via the mpt_register() API call. * * Returns 1 indicating alloc'd request frame ptr should be freed. */static intmptscsih_taskmgmt_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r){ SCSITaskMgmtReply_t *pScsiTmReply; SCSITaskMgmt_t *pScsiTmReq; u8 tmType;#ifndef MPT_SCSI_USE_NEW_EH unsigned long flags;#endif dprintk((KERN_INFO MYNAM ": SCSI TaskMgmt completed mf=%p, r=%p\n", mf, r));#ifndef MPT_SCSI_USE_NEW_EH dslprintk((KERN_INFO MYNAM ": spinlock#7\n")); spin_lock_irqsave(&mpt_scsih_taskQ_lock, flags); /* It better be the active one! */ if (mf != mpt_scsih_active_taskmgmt_mf) { printk(KERN_ERR MYNAM ": ERROR! Non-active TaskMgmt (=%p) completed!\n", mf); mpt_scsih_active_taskmgmt_mf = NULL; spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags); return 1; }#ifdef MPT_DEBUG if ((mf == NULL) || (mf >= MPT_INDEX_2_MFPTR(ioc, ioc->req_depth))) { printk(KERN_ERR MYNAM ": ERROR! NULL or BAD TaskMgmt ptr (=%p)!\n", mf); mpt_scsih_active_taskmgmt_mf = NULL; spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags); return 1; }#endif spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags);#endif if (r != NULL) { pScsiTmReply = (SCSITaskMgmtReply_t*)r; pScsiTmReq = (SCSITaskMgmt_t*)mf; /* Figure out if this was ABORT_TASK, TARGET_RESET, or BUS_RESET! */ tmType = pScsiTmReq->TaskType; dprintk((KERN_INFO MYNAM ": TaskType = %d\n", tmType)); dprintk((KERN_INFO MYNAM ": TerminationCount = %d\n", le32_to_cpu(pScsiTmReply->TerminationCount))); /* Error? (anything non-zero?) */ if (*(u32 *)&pScsiTmReply->Reserved2[0]) { dprintk((KERN_INFO MYNAM ": SCSI TaskMgmt (%d) - Oops!\n", tmType)); dprintk((KERN_INFO MYNAM ": IOCStatus = %04xh\n", le16_to_cpu(pScsiTmReply->IOCStatus))); dprintk((KERN_INFO MYNAM ": IOCLogInfo = %08xh\n", le32_to_cpu(pScsiTmReply->IOCLogInfo))); } else { dprintk((KERN_INFO MYNAM ": SCSI TaskMgmt (%d) SUCCESS!\n", tmType)); } }#ifndef MPT_SCSI_USE_NEW_EH /* * Signal to _bh thread that we finished. */ dslprintk((KERN_INFO MYNAM ": spinlock#8\n")); spin_lock_irqsave(&mpt_scsih_taskQ_lock, flags); mpt_scsih_active_taskmgmt_mf = NULL; spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags);#endif return 1;}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* * This is anyones guess quite frankly. */intmptscsih_bios_param(Disk * disk, kdev_t dev, int *ip){ int size; size = disk->capacity; ip[0] = 64; /* heads */ ip[1] = 32; /* sectors */ if ((ip[2] = size >> 11) > 1024) { /* cylinders, test for big disk */ ip[0] = 255; /* heads */ ip[1] = 63; /* sectors */ ip[2] = size / (255 * 63); /* cylinders */ } return 0;}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* * Private routines... *//*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* 19991030 -sralston * Return absolute SCSI data direction: * 1 = _DATA_OUT * 0 = _DIR_NONE * -1 = _DATA_IN */static intmptscsih_io_direction(Scsi_Cmnd *cmd){ switch (cmd->cmnd[0]) { /* _DATA_OUT commands */ case WRITE_6: case WRITE_10: case WRITE_12: case WRITE_LONG: case WRITE_SAME: case WRITE_BUFFER: case WRITE_VERIFY: case WRITE_VERIFY_12: case COMPARE: case COPY: case COPY_VERIFY: case SEARCH_EQUAL: case SEARCH_HIGH: case SEARCH_LOW: case SEARCH_EQUAL_12: case SEARCH_HIGH_12: case SEARCH_LOW_12: case MODE_SELECT: case MODE_SELECT_10: case LOG_SELECT: case SEND_DIAGNOSTIC: case CHANGE_DEFINITION: case UPDATE_BLOCK: case SET_WINDOW: case MEDIUM_SCAN: case SEND_VOLUME_TAG: case REASSIGN_BLOCKS: case PERSISTENT_RESERVE_OUT: case 0xea: return 1; /* No data transfer commands */ case SEEK_6: case SEEK_10: case RESERVE: case RELEASE: case TEST_UNIT_READY: case START_STOP: case ALLOW_MEDIUM_REMOVAL: return 0; /* Conditional data transfer commands */ case FORMAT_UNIT: if (cmd->cmnd[1] & 0x10) /* FmtData (data out phase)? */ return 1; else return 0; case VERIFY: if (cmd->cmnd[1] & 0x02) /* VERIFY:BYTCHK (data out phase)? */ return 1; else return 0; case RESERVE_10: if (cmd->cmnd[1] & 0x03) /* RESERSE:{LongID|Extent} (data out phase)? */ return 1; else return 0;#if 0 case REZERO_UNIT: /* (or REWIND) */ case SPACE: case ERASE: case ERASE_10: case SYNCHRONIZE_CACHE: case LOCK_UNLOCK_CACHE:#endif /* Must be data _IN! */ default: return -1; }}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/static voidcopy_sense_data(Scsi_Cmnd *sc, MPT_SCSI_HOST *hd, MPT_FRAME_HDR *mf, SCSIIOReply_t *pScsiReply){ MPT_SCSI_DEV *mpt_sdev = NULL; u32 sense_count = le32_to_cpu(pScsiReply->SenseCount); char devFoo[32]; IO_Info_t thisIo; if (sc && sc->device) mpt_sdev = (MPT_SCSI_DEV*) sc->device->hostdata; if (sense_count) { u8 *sense_data; int req_index; /* Copy the sense received into the scsi command block. */ req_index = le16_to_cpu(mf->u.frame.hwhdr.msgctxu.fld.req_idx); sense_data = ((u8 *)hd->ioc->sense_buf_pool + (req_index * 256)); memcpy(sc->sense_buffer, sense_data, SNS_LEN(sc)); /* Cache SenseData for this SCSI device! */ if (mpt_sdev) { memcpy(mpt_sdev->CachedSense.data, sense_data, sense_count); mpt_sdev->sense_sz = sense_count; } } else { dprintk((KERN_INFO MYNAM ": Hmmm... SenseData len=0! (?)\n")); } thisIo.cdbPtr = sc->cmnd; thisIo.sensePtr = sc->sense_buffer; thisIo.SCSIStatus = pScsiReply->SCSIStatus; thisIo.DoDisplay = 1; sprintf(devFoo, "ioc%d,scsi%d:%d", hd->ioc->id, sc->target, sc->lun); thisIo.DevIDStr = devFoo;/* fubar */ thisIo.dataPtr = NULL; thisIo.inqPtr = NULL; if (sc->device) { thisIo.inqPtr = sc->device->vendor-8; /* FIXME!!! */ } (void) mpt_ScsiHost_ErrorReport(&thisIo); return;}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/static u32SCPNT_TO_MSGCTX(Scsi_Cmnd *sc){ MPT_SCSI_HOST *hd; MPT_FRAME_HDR *mf; int i; hd = (MPT_SCSI_HOST *) sc->host->hostdata; for (i = 0; i < hd->ioc->req_depth; i++) { if (hd->ScsiLookup[i] == sc) { mf = MPT_INDEX_2_MFPTR(hd->ioc, i); return mf->u.frame.hwhdr.msgctxu.MsgContext; } } return -1;}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* see mptscsih.h */#ifdef MPT_SCSIHOST_NEED_ENTRY_EXIT_HOOKUPS static Scsi_Host_Template driver_template = MPT_SCSIHOST;# include "../../scsi/scsi_module.c"#endif/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/static intmptscsih_ioc_reset(MPT_ADAPTER *ioc, int reset_phase){ dprintk((KERN_INFO MYNAM ": IOC %s_reset routed to SCSI host driver!\n", reset_phase==MPT_IOC_PRE_RESET ? "pre" : "post")); if (reset_phase == MPT_IOC_PRE_RESET) { /* FIXME! Do pre-reset cleanup */ } else { /* FIXME! Do post-reset cleanup */ } return 1; /* currently means nothing really */}/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/static intmptscsih_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply){ u8 event = le32_to_cpu(pEvReply->Event) & 0xFF; dprintk((KERN_INFO MYNAM ": MPT event (=%02Xh) routed to SCSI host driver!\n", event)); switch (event) { case MPI_EVENT_UNIT_ATTENTION: /* 03 */ /* FIXME! */ break; case MPI_EVENT_IOC_BUS_RESET: /* 04 */ /* FIXME! */ break; case MPI_EVENT_EXT_BUS_RESET: /* 05 */ /* FIXME! */ break; case MPI_EVENT_LOGOUT: /* 09 */ /* FIXME! */ break; /* * CHECKME! Don't think we need to do * anything for these, but... */ case MPI_EVENT_RESCAN: /* 06 */ case MPI_EVENT_LINK_STATUS_CHANGE: /* 07 */ case MPI_EVENT_LOOP_STATE_CHANGE: /* 08 */ /* * CHECKME! Falling thru... */ case MPI_EVENT_NONE: /* 00 */ case MPI_EVENT_LOG_DATA: /* 01 */ case MPI_EVENT_STATE_CHANGE: /* 02 */ case MPI_EVENT_EVENT_CHANGE: /* 0A */ default: dprintk((KERN_INFO MYNAM ": Ignoring event (=%02Xh)\n", event)); break; } return 1; /* currently means nothing really */}#if 0 /* { *//*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* * scsiherr.c - Fusion MPT SCSI Host driver error handling/reporting. * * drivers/message/fusion/scsiherr.c *///extern const char **mpt_ScsiOpcodesPtr; /* needed by mptscsih.c *///extern ASCQ_Table_t *mpt_ASCQ_TablePtr;//extern int mpt_ASCQ_TableSz;/* Lie! */#define MYNAM "mptscsih"#endif /* } *//*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* * Private data... */static ASCQ_Table_t *mptscsih_ASCQ_TablePtr;/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* old symsense.c stuff... *//*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*//* * Private data... * To protect ourselves against those that would pass us bogus pointers */static u8 dummyInqData[SCSI_STD_INQUIRY_BYTES] = { 0x1F, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };static u8 dummySenseData[SCSI_STD_SENSE_BYTES] = { 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };static u8 dummyCDB[16] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };static u8 dummyScsiData[16] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };#if 0static const char *PeripheralDeviceTypeString[32] = { "Direct-access", /* 00h */ "Sequential-access", /* 01h */ "Printer", /* 02h */ "Processor", /* 03h */ /*"Write-Once-Read-Multiple",*/ /* 04h */ "WORM", /* 04h */ "CD-ROM", /* 05h */ "Scanner", /* 06h */ "Optical memory", /* 07h */ "Media Changer", /* 08h */ "Communications", /* 09h */ "(Graphics arts pre-press)", /* 0Ah */ "(Graphics arts pre-press)", /* 0Bh */ "Array controller", /* 0Ch */ "Enclosure services", /* 0Dh */ "Simplified direct-access", /* 0Eh */ "Reserved-0Fh", /* 0Fh */ "Reserved-10h", /* 10h */ "Reserved-11h", /* 11h */ "Reserved-12h", /* 12h */ "Reserved-13h", /* 13h */ "Reserved-14h", /* 14h */ "Reserved-15h", /* 15h */ "Reserved-16h", /* 16h */ "Reserved-17h", /* 17h */ "Reserved-18h", /* 18h */ "Reserved-19h", /* 19h */ "Reserved-1Ah", /* 1Ah */ "Reserved-1Bh", /* 1Bh */ "Reserved-1Ch", /* 1Ch */ "Reserved-1Dh", /* 1Dh */ "Reserved-1Eh", /* 1Eh */ "Unknown" /* 1Fh */};#endifstatic char *ScsiStatusString[] = { "GOOD", /* 00h */ NULL, /* 01h */ "CHECK CONDITION", /* 02h */ NULL, /* 03h */ "CONDITION MET", /* 04h */ NULL, /* 05h */ NULL, /* 06h */ NULL, /* 07h */ "BUSY", /* 08h */ NULL, /* 09h */ NULL, /* 0Ah */ NULL, /* 0Bh */ NULL, /* 0Ch */ NULL, /* 0Dh */ NULL, /* 0Eh */ NULL, /* 0Fh */ "INTERMEDIATE", /* 10h */ NULL, /* 11h */ NULL, /* 12h */ NULL, /* 13h */ "INTERMEDIATE-CONDITION MET", /* 14h */ NULL, /* 15h */ NULL, /* 16h */ NULL, /* 17h */ "RESERVATION CONFLICT", /* 18h */ NULL, /* 19h */ NULL, /* 1Ah */ NULL, /* 1Bh */ NULL, /* 1Ch */ NULL, /* 1Dh */ NULL, /* 1Eh */ NULL, /* 1Fh */ NULL, /* 20h */ NULL, /* 21h */ "COMMAND TERMINATED", /* 22h */ NULL, /* 23h */ NULL,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -