diff options
| author | Linus Torvalds <torvalds@athlon.transmeta.com> | 2002-02-04 20:13:37 -0800 |
|---|---|---|
| committer | Linus Torvalds <torvalds@athlon.transmeta.com> | 2002-02-04 20:13:37 -0800 |
| commit | 1c3cefa582a6b598d204bad02676df300e457efa (patch) | |
| tree | c56196ce6e35589c43b227887932a5caf1bbe576 /drivers/message | |
| parent | 991b3ae8019276269816512425f102c4687f2291 (diff) | |
v2.4.9.4 -> v2.4.9.5
- Merge with Alan
- Trond Myklebust: NFS fixes - kmap and root inode special case
- Al Viro: more superblock cleanups, inode leak in rd.c, minix
directories in page cache
- Paul Mackerras: clean up rubbish from sl82c105.c
- Neil Brown: md/raid cleanups, NFS filehandles
- Johannes Erdfelt: USB update (usb-2.0 support, visor fix, Clie fix,
pl2303 driver update)
- David Miller: sparc and net update
- Eric Biederman: simplify and correct bootdata allocation - don't
overwrite ramdisks
- Tim Waugh: support multiple SuperIO devices, parport doc updates
Diffstat (limited to 'drivers/message')
| -rw-r--r-- | drivers/message/fusion/Makefile | 8 | ||||
| -rw-r--r-- | drivers/message/fusion/isense.c | 4 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/fc_log.h | 16 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi.h | 13 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_cnfg.h | 698 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_fc.h | 26 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_history.txt | 83 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_init.h | 128 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_ioc.h | 527 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_lan.h | 131 | ||||
| -rw-r--r-- | drivers/message/fusion/lsi/mpi_targ.h | 241 | ||||
| -rw-r--r-- | drivers/message/fusion/mptbase.c | 913 | ||||
| -rw-r--r-- | drivers/message/fusion/mptbase.h | 67 | ||||
| -rw-r--r-- | drivers/message/fusion/mptctl.c | 97 | ||||
| -rw-r--r-- | drivers/message/fusion/mptlan.c | 210 | ||||
| -rw-r--r-- | drivers/message/fusion/mptlan.h | 3 | ||||
| -rw-r--r-- | drivers/message/fusion/mptscsih.c | 211 | ||||
| -rw-r--r-- | drivers/message/fusion/scsi3.h | 5 |
18 files changed, 2090 insertions, 1291 deletions
diff --git a/drivers/message/fusion/Makefile b/drivers/message/fusion/Makefile index 46df6571dfc5..a1ddc8e105df 100644 --- a/drivers/message/fusion/Makefile +++ b/drivers/message/fusion/Makefile @@ -27,18 +27,22 @@ EXTRA_CFLAGS += -I. ${MPT_CFLAGS} #EXTRA_CFLAGS += -DDEBUG #EXTRA_CFLAGS += -DMPT_DEBUG #EXTRA_CFLAGS += -DMPT_DEBUG_MSG_FRAME -#EXTRA_CFLAGS += -DMPT_DEBUG_SPINLOCK +# # driver/module specifics... +# # For mptbase: #CFLAGS_mptbase.o += -DMPT_DEBUG_HANDSHAKE #CFLAGS_mptbase.o += -DMPT_DEBUG_IRQ +# # For {mptscsih, mptctl}: #CFLAGS_mptscsih.o += -DMPT_SCSI_USE_NEW_EH -#CFLAGS_mptscsih.o += -DMPT_SCSI_CACHE_AUTOSENSE +#CFLAGS_mptscsih.o += -DMPT_DEBUG_SCANDV #CFLAGS_mptscsih.o += -DMPT_DEBUG_SG #CFLAGS_mptctl.o += -DMPT_DEBUG_SG +# # For mptlan: #CFLAGS_mptlan.o += -DMPT_LAN_IO_DEBUG +# # For isense: # EXP... diff --git a/drivers/message/fusion/isense.c b/drivers/message/fusion/isense.c index 553c8db6a37d..457c3e819a77 100644 --- a/drivers/message/fusion/isense.c +++ b/drivers/message/fusion/isense.c @@ -10,7 +10,7 @@ * (yes I wrote some of the orig. code back in 1991!) * (mailto:Steve.Ralston@lsil.com) * - * $Id: isense.c,v 1.28 2001/01/14 23:11:09 sralston Exp $ + * $Id: isense.c,v 1.28.14.1 2001/08/24 20:07:04 sralston Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -61,7 +61,7 @@ #endif #define MODULEAUTHOR "Steven J. Ralston" -#define COPYRIGHT "Copyright (c) 2000 " MODULEAUTHOR +#define COPYRIGHT "Copyright (c) 2001 " MODULEAUTHOR #include "mptbase.h" #include "isense.h" diff --git a/drivers/message/fusion/lsi/fc_log.h b/drivers/message/fusion/lsi/fc_log.h index 57597172ee31..82166de4a2c4 100644 --- a/drivers/message/fusion/lsi/fc_log.h +++ b/drivers/message/fusion/lsi/fc_log.h @@ -7,7 +7,7 @@ * in the IOCLogInfo field of a MPI Default Reply Message. * * CREATION DATE: 6/02/2000 - * ID: $Id: fc_log.h,v 4.2 2001/03/01 18:28:59 fibre Exp $ + * ID: $Id: fc_log.h,v 4.5 2001/06/07 19:18:00 sschremm Exp $ */ @@ -38,11 +38,16 @@ typedef enum _MpiIocLogInfoFc { MPI_IOCLOGINFO_FC_INIT_BASE = 0x20000000, MPI_IOCLOGINFO_FC_INIT_ERROR_OUT_OF_ORDER_FRAME = 0x20000001, /* received an out of order frame - unsupported */ - MPI_IOCLOGINFO_FC_INIT_ERROR_BAD_START_OF_FRAME = 0x20000002, /* bad start of frame primative */ - MPI_IOCLOGINFO_FC_INIT_ERROR_BAD_END_OF_FRAME = 0x20000003, /* bad end of frame primative */ - MPI_IOCLOGINFO_FC_INIT_ERROR_OVER_RUN = 0x20000004, /* Receiver hardware detected overrun */ + MPI_IOCLOGINFO_FC_INIT_ERROR_BAD_START_OF_FRAME = 0x20000002, /* Bad Rx Frame, bad start of frame primative */ + MPI_IOCLOGINFO_FC_INIT_ERROR_BAD_END_OF_FRAME = 0x20000003, /* Bad Rx Frame, bad end of frame primative */ + MPI_IOCLOGINFO_FC_INIT_ERROR_OVER_RUN = 0x20000004, /* Bad Rx Frame, overrun */ MPI_IOCLOGINFO_FC_INIT_ERROR_RX_OTHER = 0x20000005, /* Other errors caught by IOC which require retries */ MPI_IOCLOGINFO_FC_INIT_ERROR_SUBPROC_DEAD = 0x20000006, /* Main processor could not initialize sub-processor */ + MPI_IOCLOGINFO_FC_INIT_ERROR_RX_OVERRUN = 0x20000007, /* Scatter Gather overrun */ + MPI_IOCLOGINFO_FC_INIT_ERROR_RX_BAD_STATUS = 0x20000008, /* Receiver detected context mismatch via invalid header */ + MPI_IOCLOGINFO_FC_INIT_ERROR_RX_UNEXPECTED_FRAME= 0x20000009, /* CtxMgr detected unsupported frame type */ + MPI_IOCLOGINFO_FC_INIT_ERROR_LINK_FAILURE = 0x2000000A, /* Link failure occurred */ + MPI_IOCLOGINFO_FC_INIT_ERROR_TX_TIMEOUT = 0x2000000B, /* Transmitter timeout error */ MPI_IOCLOGINFO_FC_TARGET_BASE = 0x21000000, MPI_IOCLOGINFO_FC_TARGET_NO_PDISC = 0x21000001, /* not sent because we are waiting for a PDISC from the initiator */ @@ -72,10 +77,11 @@ typedef enum _MpiIocLogInfoFc MPI_IOCLOGINFO_FC_LINK_LOOP_INIT_TIMEOUT = 0x24000001, /* Loop initialization timed out */ MPI_IOCLOGINFO_FC_LINK_ALREADY_INITIALIZED = 0x24000002, /* Another system controller already initialized the loop */ MPI_IOCLOGINFO_FC_LINK_LINK_NOT_ESTABLISHED = 0x24000003, /* Not synchronized to signal or still negotiating (possible cable problem) */ + MPI_IOCLOGINFO_FC_LINK_CRC_ERROR = 0x24000004, /* CRC check detected error on received frame */ MPI_IOCLOGINFO_FC_CTX_BASE = 0x25000000, - MPI_IOCLOGINFO_FC_INVALID_FIELD_BYTE_OFFSET = 0x26000000, /* The lower 24 bits give the byte offset of the field in the request message that is invalid. */ + MPI_IOCLOGINFO_FC_INVALID_FIELD_BYTE_OFFSET = 0x26000000, /* The lower 24 bits give the byte offset of the field in the request message that is invalid */ MPI_IOCLOGINFO_FC_INVALID_FIELD_MAX_OFFSET = 0x26ffffff, MPI_IOCLOGINFO_FC_STATE_CHANGE = 0x27000000 /* The lower 24 bits give additional information concerning state change */ diff --git a/drivers/message/fusion/lsi/mpi.h b/drivers/message/fusion/lsi/mpi.h index bf0a662e50f5..9aba9138bbf9 100644 --- a/drivers/message/fusion/lsi/mpi.h +++ b/drivers/message/fusion/lsi/mpi.h @@ -6,7 +6,7 @@ * Title: MPI Message independent structures and definitions * Creation Date: July 27, 2000 * - * MPI Version: 01.01.06 + * MPI Version: 01.01.07 * * Version History * --------------- @@ -37,6 +37,8 @@ * Obsoleted MPI_IOCSTATUS_TARGET_FC_ defines. * 02-27-01 01.01.06 Removed MPI_HOST_INDEX_REGISTER define. * Added function codes for RAID. + * 04-09-01 01.01.07 Added alternate define for MPI_DOORBELL_ACTIVE, + * MPI_DOORBELL_USED, to better match the spec. * -------------------------------------------------------------------------- */ @@ -90,7 +92,8 @@ /* S y s t e m D o o r b e l l */ #define MPI_DOORBELL_OFFSET (0x00000000) -#define MPI_DOORBELL_ACTIVE (0x08000000) +#define MPI_DOORBELL_ACTIVE (0x08000000) /* DoorbellUsed */ +#define MPI_DOORBELL_USED (MPI_DOORBELL_ACTIVE) #define MPI_DOORBELL_ACTIVE_SHIFT (27) #define MPI_DOORBELL_WHO_INIT_MASK (0x07000000) #define MPI_DOORBELL_WHO_INIT_SHIFT (24) @@ -634,9 +637,9 @@ typedef struct _MSG_DEFAULT_REPLY /****************************************************************************/ #define MPI_IOCLOGINFO_TYPE_MASK (0xF0000000) -#define MPI_IOCLOGINFO_TYPE_NONE (0x00) -#define MPI_IOCLOGINFO_TYPE_SCSI (0x01) -#define MPI_IOCLOGINFO_TYPE_FC (0x02) +#define MPI_IOCLOGINFO_TYPE_NONE (0x0) +#define MPI_IOCLOGINFO_TYPE_SCSI (0x1) +#define MPI_IOCLOGINFO_TYPE_FC (0x2) #define MPI_IOCLOGINFO_LOG_DATA_MASK (0x0FFFFFFF) diff --git a/drivers/message/fusion/lsi/mpi_cnfg.h b/drivers/message/fusion/lsi/mpi_cnfg.h index dd81a65e25b5..573cc277b46b 100644 --- a/drivers/message/fusion/lsi/mpi_cnfg.h +++ b/drivers/message/fusion/lsi/mpi_cnfg.h @@ -6,7 +6,7 @@ * Title: MPI Config message, structures, and Pages * Creation Date: July 27, 2000 * - * MPI Version: 01.01.09 + * MPI Version: 01.01.11 * * Version History * --------------- @@ -60,6 +60,18 @@ * MPI_CONFIG_PAGETYPE_RAID_VOLUME. * Added definitions and structures for IOC Page 2 and * RAID Volume Page 2. + * 03-27-01 01.01.10 Added CONFIG_PAGE_FC_PORT_8 and CONFIG_PAGE_FC_PORT_9. + * CONFIG_PAGE_FC_PORT_3 now supports persistent by DID. + * Added VendorId and ProductRevLevel fields to + * RAIDVOL2_IM_PHYS_ID struct. + * Modified values for MPI_FCPORTPAGE0_FLAGS_ATTACH_ + * defines to make them compatible to MPI version 1.0. + * Added structure offset comments. + * 04-09-01 01.01.11 Added some new defines for the PageAddress field and + * removed some obsolete ones. + * Added IO Unit Page 3. + * Modified defines for Scsi Port Page 2. + * Modified RAID Volume Pages. * -------------------------------------------------------------------------- */ @@ -75,10 +87,10 @@ typedef struct _CONFIG_PAGE_HEADER { - U8 PageVersion; - U8 PageLength; - U8 PageNumber; - U8 PageType; + U8 PageVersion; /* 00h */ + U8 PageLength; /* 01h */ + U8 PageNumber; /* 02h */ + U8 PageType; /* 03h */ } fCONFIG_PAGE_HEADER, MPI_POINTER PTR_CONFIG_PAGE_HEADER, ConfigPageHeader_t, MPI_POINTER pConfigPageHeader_t; @@ -120,17 +132,19 @@ typedef union _CONFIG_PAGE_HEADER_UNION ****************************************************************************/ #define MPI_SCSI_PORT_PGAD_PORT_MASK (0x000000FF) +#define MPI_SCSI_DEVICE_FORM_MASK (0xF0000000) +#define MPI_SCSI_DEVICE_FORM_TARGETID (0x00000000) +#define MPI_SCSI_DEVICE_FORM_RAID_PHYS_DEV_NUM (0x10000000) #define MPI_SCSI_DEVICE_TARGET_ID_MASK (0x000000FF) #define MPI_SCSI_DEVICE_TARGET_ID_SHIFT (0) #define MPI_SCSI_DEVICE_BUS_MASK (0x0000FF00) #define MPI_SCSI_DEVICE_BUS_SHIFT (8) - -#define MPI_SCSI_LUN_TARGET_ID_MASK (0x000000FF) -#define MPI_SCSI_LUN_TARGET_ID_SHIFT (0) -#define MPI_SCSI_LUN_BUS_MASK (0x0000FF00) -#define MPI_SCSI_LUN_BUS_SHIFT (8) -#define MPI_SCSI_LUN_LUN_MASK (0x00FF0000) -#define MPI_SCSI_LUN_LUN_SHIFT (16) +#define MPI_SCSI_DEVICE_VOLUME_TARG_ID_MASK (0x000000FF) +#define MPI_SCSI_DEVICE_VOLUME_TARG_ID_SHIFT (0) +#define MPI_SCSI_DEVICE_VOLUME_BUS_MASK (0x0000FF00) +#define MPI_SCSI_DEVICE_VOLUME_BUS_SHIFT (8) +#define MPI_SCSI_DEVICE_PHYS_DISK_NUM_MASK (0x00FF0000) +#define MPI_SCSI_DEVICE_PHYS_DISK_NUM_SHIFT (16) #define MPI_FC_PORT_PGAD_PORT_MASK (0xF0000000) #define MPI_FC_PORT_PGAD_PORT_SHIFT (28) @@ -159,17 +173,17 @@ typedef union _CONFIG_PAGE_HEADER_UNION /****************************************************************************/ typedef struct _MSG_CONFIG { - U8 Action; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U8 Reserved2[8]; - fCONFIG_PAGE_HEADER Header; - U32 PageAddress; - SGE_IO_UNION PageBufferSGE; + U8 Action; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 Reserved2[8]; /* 0Ch */ + fCONFIG_PAGE_HEADER Header; /* 14h */ + U32 PageAddress; /* 18h */ + SGE_IO_UNION PageBufferSGE; /* 1Ch */ } MSG_CONFIG, MPI_POINTER PTR_MSG_CONFIG, Config_t, MPI_POINTER pConfig_t; @@ -178,12 +192,9 @@ typedef struct _MSG_CONFIG /* Action field values */ /****************************************************************************/ #define MPI_CONFIG_ACTION_PAGE_HEADER (0x00) -/*#define MPI_CONFIG_ACTION_PAGE_READ (0x01) *//* obsolete */ #define MPI_CONFIG_ACTION_PAGE_READ_CURRENT (0x01) -/*#define MPI_CONFIG_ACTION_PAGE_WRITE (0x02) *//* obsolete */ #define MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT (0x02) #define MPI_CONFIG_ACTION_PAGE_DEFAULT (0x03) -/*#define MPI_CONFIG_ACTION_PAGE_WRITE_COMMIT (0x04) */ /* obsolete */ #define MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM (0x04) #define MPI_CONFIG_ACTION_PAGE_READ_DEFAULT (0x05) #define MPI_CONFIG_ACTION_PAGE_READ_NVRAM (0x06) @@ -192,17 +203,17 @@ typedef struct _MSG_CONFIG /* Config Reply Message */ typedef struct _MSG_CONFIG_REPLY { - U8 Action; - U8 Reserved; - U8 MsgLength; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U8 Reserved2[2]; - U16 IOCStatus; - U32 IOCLogInfo; - fCONFIG_PAGE_HEADER Header; + U8 Action; /* 00h */ + U8 Reserved; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 Reserved2[2]; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + fCONFIG_PAGE_HEADER Header; /* 14h */ } MSG_CONFIG_REPLY, MPI_POINTER PTR_MSG_CONFIG_REPLY, ConfigReply_t, MPI_POINTER pConfigReply_t; @@ -226,12 +237,12 @@ typedef struct _MSG_CONFIG_REPLY typedef struct _CONFIG_PAGE_MANUFACTURING_0 { - fCONFIG_PAGE_HEADER Header; - U8 ChipName[16]; - U8 ChipRevision[8]; - U8 BoardName[16]; - U8 BoardAssembly[16]; - U8 BoardTracerNumber[16]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U8 ChipName[16]; /* 04h */ + U8 ChipRevision[8]; /* 14h */ + U8 BoardName[16]; /* 1Ch */ + U8 BoardAssembly[16]; /* 2Ch */ + U8 BoardTracerNumber[16]; /* 3Ch */ } fCONFIG_PAGE_MANUFACTURING_0, MPI_POINTER PTR_CONFIG_PAGE_MANUFACTURING_0, ManufacturingPage0_t, MPI_POINTER pManufacturingPage0_t; @@ -241,8 +252,8 @@ typedef struct _CONFIG_PAGE_MANUFACTURING_0 typedef struct _CONFIG_PAGE_MANUFACTURING_1 { - fCONFIG_PAGE_HEADER Header; - U8 VPD[256]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U8 VPD[256]; /* 04h */ } fCONFIG_PAGE_MANUFACTURING_1, MPI_POINTER PTR_CONFIG_PAGE_MANUFACTURING_1, ManufacturingPage1_t, MPI_POINTER pManufacturingPage1_t; @@ -251,18 +262,18 @@ typedef struct _CONFIG_PAGE_MANUFACTURING_1 typedef struct _MPI_CHIP_REVISION_ID { - U16 DeviceID; - U8 PCIRevisionID; - U8 Reserved; + U16 DeviceID; /* 00h */ + U8 PCIRevisionID; /* 02h */ + U8 Reserved; /* 03h */ } MPI_CHIP_REVISION_ID, MPI_POINTER PTR_MPI_CHIP_REVISION_ID, MpiChipRevisionId_t, MPI_POINTER pMpiChipRevisionId_t; typedef struct _CONFIG_PAGE_MANUFACTURING_2 { - fCONFIG_PAGE_HEADER Header; - MPI_CHIP_REVISION_ID ChipId; - U32 HwSettings[1]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + MPI_CHIP_REVISION_ID ChipId; /* 04h */ + U32 HwSettings[1]; /* 08h */ } fCONFIG_PAGE_MANUFACTURING_2, MPI_POINTER PTR_CONFIG_PAGE_MANUFACTURING_2, ManufacturingPage2_t, MPI_POINTER pManufacturingPage2_t; @@ -271,9 +282,9 @@ typedef struct _CONFIG_PAGE_MANUFACTURING_2 typedef struct _CONFIG_PAGE_MANUFACTURING_3 { - fCONFIG_PAGE_HEADER Header; - MPI_CHIP_REVISION_ID ChipId; - U32 Info[1]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + MPI_CHIP_REVISION_ID ChipId; /* 04h */ + U32 Info[1]; /* 08h */ } fCONFIG_PAGE_MANUFACTURING_3, MPI_POINTER PTR_CONFIG_PAGE_MANUFACTURING_3, ManufacturingPage3_t, MPI_POINTER pManufacturingPage3_t; @@ -286,8 +297,8 @@ typedef struct _CONFIG_PAGE_MANUFACTURING_3 typedef struct _CONFIG_PAGE_IO_UNIT_0 { - fCONFIG_PAGE_HEADER Header; - U64 UniqueValue; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U64 UniqueValue; /* 04h */ } fCONFIG_PAGE_IO_UNIT_0, MPI_POINTER PTR_CONFIG_PAGE_IO_UNIT_0, IOUnitPage0_t, MPI_POINTER pIOUnitPage0_t; @@ -296,8 +307,8 @@ typedef struct _CONFIG_PAGE_IO_UNIT_0 typedef struct _CONFIG_PAGE_IO_UNIT_1 { - fCONFIG_PAGE_HEADER Header; - U32 Flags; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Flags; /* 04h */ } fCONFIG_PAGE_IO_UNIT_1, MPI_POINTER PTR_CONFIG_PAGE_IO_UNIT_1, IOUnitPage1_t, MPI_POINTER pIOUnitPage1_t; @@ -313,9 +324,9 @@ typedef struct _CONFIG_PAGE_IO_UNIT_1 typedef struct _MPI_ADAPTER_INFO { - U8 PciBusNumber; - U8 PciDeviceAndFunctionNumber; - U16 AdapterFlags; + U8 PciBusNumber; /* 00h */ + U8 PciDeviceAndFunctionNumber; /* 01h */ + U16 AdapterFlags; /* 02h */ } MPI_ADAPTER_INFO, MPI_POINTER PTR_MPI_ADAPTER_INFO, MpiAdapterInfo_t, MPI_POINTER pMpiAdapterInfo_t; @@ -324,10 +335,10 @@ typedef struct _MPI_ADAPTER_INFO typedef struct _CONFIG_PAGE_IO_UNIT_2 { - fCONFIG_PAGE_HEADER Header; - U32 Flags; - U32 BiosVersion; - MPI_ADAPTER_INFO AdapterOrder[4]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Flags; /* 04h */ + U32 BiosVersion; /* 08h */ + MPI_ADAPTER_INFO AdapterOrder[4]; /* 0Ch */ } fCONFIG_PAGE_IO_UNIT_2, MPI_POINTER PTR_CONFIG_PAGE_IO_UNIT_2, IOUnitPage2_t, MPI_POINTER pIOUnitPage2_t; @@ -340,34 +351,53 @@ typedef struct _CONFIG_PAGE_IO_UNIT_2 #define MPI_IOUNITPAGE2_FLAGS_DONT_HOOK_INT_40 (0x00000010) +typedef struct _CONFIG_PAGE_IO_UNIT_3 +{ + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 VolumeSettings; /* 04h */ + U8 InfoOffset0; /* 08h */ + U8 InfoSize0; /* 09h */ + U8 InfoOffset1; /* 0Ah */ + U8 InfoSize1; /* 0Bh */ + U8 InquirySize; /* 0Ch */ + U8 Reserved; /* 0Dh */ + U16 Reserved2; /* 0Eh */ + U8 InquiryData[56]; /* 10h */ +} fCONFIG_PAGE_IO_UNIT_3, MPI_POINTER PTR_CONFIG_PAGE_IO_UNIT_3, + IOUnitPage3_t, MPI_POINTER pIOUnitPage3_t; + +#define MPI_IOUNITPAGE3_PAGEVERSION (0x00) + + /****************************************************************************/ /* IOC Config Pages */ /****************************************************************************/ typedef struct _CONFIG_PAGE_IOC_0 { - fCONFIG_PAGE_HEADER Header; - U32 TotalNVStore; - U32 FreeNVStore; - U16 VendorID; - U16 DeviceID; - U8 RevisionID; - U8 Reserved[3]; - U32 ClassCode; - U16 SubsystemVendorID; - U16 SubsystemID; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 TotalNVStore; /* 04h */ + U32 FreeNVStore; /* 08h */ + U16 VendorID; /* 0Ch */ + U16 DeviceID; /* 0Eh */ + U8 RevisionID; /* 10h */ + U8 Reserved[3]; /* 11h */ + U32 ClassCode; /* 14h */ + U16 SubsystemVendorID; /* 18h */ + U16 SubsystemID; /* 1Ah */ } fCONFIG_PAGE_IOC_0, MPI_POINTER PTR_CONFIG_PAGE_IOC_0, IOCPage0_t, MPI_POINTER pIOCPage0_t; #define MPI_IOCPAGE0_PAGEVERSION (0x01) + typedef struct _CONFIG_PAGE_IOC_1 { - fCONFIG_PAGE_HEADER Header; - U32 Flags; - U32 CoalescingTimeout; - U8 CoalescingDepth; - U8 Reserved[3]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Flags; /* 04h */ + U32 CoalescingTimeout; /* 08h */ + U8 CoalescingDepth; /* 0Ch */ + U8 Reserved[3]; /* 0Dh */ } fCONFIG_PAGE_IOC_1, MPI_POINTER PTR_CONFIG_PAGE_IOC_1, IOCPage1_t, MPI_POINTER pIOCPage1_t; @@ -375,26 +405,27 @@ typedef struct _CONFIG_PAGE_IOC_1 #define MPI_IOCPAGE1_REPLY_COALESCING (0x00000001) + typedef struct _CONFIG_PAGE_IOC_2_RAID_VOL { - U8 VolumeTargetID; - U8 VolumeBus; - U16 Reserved; - U8 VolumeVersionMinor; - U8 VolumeVersionMajor; - U8 VolumeRaidType; - U8 Reserved1; + U8 VolumeTargetID; /* 00h */ + U8 VolumeBus; /* 01h */ + U16 Reserved; /* 02h */ + U8 VolumeVersionMinor; /* 04h */ + U8 VolumeVersionMajor; /* 05h */ + U8 VolumeRaidType; /* 06h */ + U8 Reserved1; /* 07h */ } fCONFIG_PAGE_IOC_2_RAID_VOL, MPI_POINTER PTR_CONFIG_PAGE_IOC_2_RAID_VOL, ConfigPageIoc2RaidVol_t, MPI_POINTER pConfigPageIoc2RaidVol_t; typedef struct _CONFIG_PAGE_IOC_2 { - fCONFIG_PAGE_HEADER Header; - U32 CapabilitiesFlags; - U8 NumActiveVolumes; - U8 MaxVolumes; - U16 Reserved; - fCONFIG_PAGE_IOC_2_RAID_VOL RaidVolume[1]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 CapabilitiesFlags; /* 04h */ + U8 NumActiveVolumes; /* 08h */ + U8 MaxVolumes; /* 09h */ + U16 Reserved; /* 0Ah */ + fCONFIG_PAGE_IOC_2_RAID_VOL RaidVolume[1]; /* 0Ch */ } fCONFIG_PAGE_IOC_2, MPI_POINTER PTR_CONFIG_PAGE_IOC_2, IOCPage2_t, MPI_POINTER pIOCPage2_t; @@ -423,9 +454,9 @@ typedef struct _CONFIG_PAGE_IOC_2 typedef struct _CONFIG_PAGE_SCSI_PORT_0 { - fCONFIG_PAGE_HEADER Header; - U32 Capabilities; - U32 PhysicalInterface; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Capabilities; /* 04h */ + U32 PhysicalInterface; /* 08h */ } fCONFIG_PAGE_SCSI_PORT_0, MPI_POINTER PTR_CONFIG_PAGE_SCSI_PORT_0, SCSIPortPage0_t, MPI_POINTER pSCSIPortPage0_t; @@ -445,10 +476,11 @@ typedef struct _CONFIG_PAGE_SCSI_PORT_0 #define MPI_SCSIPORTPAGE0_PHY_SIGNAL_SE (0x02) #define MPI_SCSIPORTPAGE0_PHY_SIGNAL_LVD (0x03) + typedef struct _CONFIG_PAGE_SCSI_PORT_1 { - fCONFIG_PAGE_HEADER Header; - U32 Configuration; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Configuration; /* 04h */ } fCONFIG_PAGE_SCSI_PORT_1, MPI_POINTER PTR_CONFIG_PAGE_SCSI_PORT_1, SCSIPortPage1_t, MPI_POINTER pSCSIPortPage1_t; @@ -457,20 +489,21 @@ typedef struct _CONFIG_PAGE_SCSI_PORT_1 #define MPI_SCSIPORTPAGE1_CFG_PORT_SCSI_ID_MASK (0x000000FF) #define MPI_SCSIPORTPAGE1_CFG_PORT_RESPONSE_ID_MASK (0xFFFF0000) + typedef struct _MPI_DEVICE_INFO { - U8 Timeout; - U8 SyncFactor; - U16 DeviceFlags; + U8 Timeout; /* 00h */ + U8 SyncFactor; /* 01h */ + U16 DeviceFlags; /* 02h */ } MPI_DEVICE_INFO, MPI_POINTER PTR_MPI_DEVICE_INFO, MpiDeviceInfo_t, MPI_POINTER pMpiDeviceInfo_t; typedef struct _CONFIG_PAGE_SCSI_PORT_2 { - fCONFIG_PAGE_HEADER Header; - U32 PortFlags; - U32 PortSettings; - MPI_DEVICE_INFO DeviceSettings[16]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 PortFlags; /* 04h */ + U32 PortSettings; /* 08h */ + MPI_DEVICE_INFO DeviceSettings[16]; /* 0Ch */ } fCONFIG_PAGE_SCSI_PORT_2, MPI_POINTER PTR_CONFIG_PAGE_SCSI_PORT_2, SCSIPortPage2_t, MPI_POINTER pSCSIPortPage2_t; @@ -492,15 +525,15 @@ typedef struct _CONFIG_PAGE_SCSI_PORT_2 #define MPI_SCSIPORTPAGE2_PORT_SPINUP_DELAY_MASK (0x00000F00) #define MPI_SCSIPORTPAGE2_PORT_MASK_NEGO_MASTER_SETTINGS (0x00003000) #define MPI_SCSIPORTPAGE2_PORT_NEGO_MASTER_SETTINGS (0x00000000) -#define MPI_SCSIPORTPAGE2_PORT_NONE_MASTER_SETTINGS (0x00000001) -#define MPI_SCSIPORTPAGE2_PORT_ALL_MASTER_SETTINGS (0x00000003) +#define MPI_SCSIPORTPAGE2_PORT_NONE_MASTER_SETTINGS (0x00001000) +#define MPI_SCSIPORTPAGE2_PORT_ALL_MASTER_SETTINGS (0x00003000) -#define MPI_SCSIPORTPAGE2_DEVICE_DISCONNECT_ENABLE (0x00000001) -#define MPI_SCSIPORTPAGE2_DEVICE_ID_SCAN_ENABLE (0x00000002) -#define MPI_SCSIPORTPAGE2_DEVICE_LUN_SCAN_ENABLE (0x00000004) -#define MPI_SCSIPORTPAGE2_DEVICE_TAG_QUEUE_ENABLE (0x00000008) -#define MPI_SCSIPORTPAGE2_DEVICE_WIDE_DISABLE (0x00000010) -#define MPI_SCSIPORTPAGE2_DEVICE_BOOT_CHOICE (0x00000020) +#define MPI_SCSIPORTPAGE2_DEVICE_DISCONNECT_ENABLE (0x0001) +#define MPI_SCSIPORTPAGE2_DEVICE_ID_SCAN_ENABLE (0x0002) +#define MPI_SCSIPORTPAGE2_DEVICE_LUN_SCAN_ENABLE (0x0004) +#define MPI_SCSIPORTPAGE2_DEVICE_TAG_QUEUE_ENABLE (0x0008) +#define MPI_SCSIPORTPAGE2_DEVICE_WIDE_DISABLE (0x0010) +#define MPI_SCSIPORTPAGE2_DEVICE_BOOT_CHOICE (0x0020) /****************************************************************************/ @@ -509,9 +542,9 @@ typedef struct _CONFIG_PAGE_SCSI_PORT_2 typedef struct _CONFIG_PAGE_SCSI_DEVICE_0 { - fCONFIG_PAGE_HEADER Header; - U32 NegotiatedParameters; - U32 Information; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 NegotiatedParameters; /* 04h */ + U32 Information; /* 08h */ } fCONFIG_PAGE_SCSI_DEVICE_0, MPI_POINTER PTR_CONFIG_PAGE_SCSI_DEVICE_0, SCSIDevicePage0_t, MPI_POINTER pSCSIDevicePage0_t; @@ -528,16 +561,17 @@ typedef struct _CONFIG_PAGE_SCSI_DEVICE_0 #define MPI_SCSIDEVPAGE0_INFO_PARAMS_NEGOTIATED (0x00000001) + typedef struct _CONFIG_PAGE_SCSI_DEVICE_1 { - fCONFIG_PAGE_HEADER Header; - U32 RequestedParameters; - U32 DomainValidation; - U32 Configuration; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 RequestedParameters; /* 04h */ + U32 Reserved; /* 08h */ + U32 Configuration; /* 0Ch */ } fCONFIG_PAGE_SCSI_DEVICE_1, MPI_POINTER PTR_CONFIG_PAGE_SCSI_DEVICE_1, SCSIDevicePage1_t, MPI_POINTER pSCSIDevicePage1_t; -#define MPI_SCSIDEVPAGE1_PAGEVERSION (0x01) +#define MPI_SCSIDEVPAGE1_PAGEVERSION (0x02) #define MPI_SCSIDEVPAGE1_RP_IU (0x00000001) #define MPI_SCSIDEVPAGE1_RP_DT (0x00000002) @@ -553,29 +587,71 @@ typedef struct _CONFIG_PAGE_SCSI_DEVICE_1 #define MPI_SCSIDEVPAGE1_CONF_PPR_ALLOWED (0x00000001) + +typedef struct _CONFIG_PAGE_SCSI_DEVICE_2 +{ + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 DomainValidation; /* 04h */ + U32 ParityPipeSelect; /* 08h */ + U32 DataPipeSelect; /* 0Ch */ +} fCONFIG_PAGE_SCSI_DEVICE_2, MPI_POINTER PTR_CONFIG_PAGE_SCSI_DEVICE_2, + SCSIDevicePage2_t, MPI_POINTER pSCSIDevicePage2_t; + +#define MPI_SCSIDEVPAGE2_PAGEVERSION (0x00) + +#define MPI_SCSIDEVPAGE2_DV_ISI_ENABLE (0x00000010) +#define MPI_SCSIDEVPAGE2_DV_SECONDARY_DRIVER_ENABLE (0x00000020) +#define MPI_SCSIDEVPAGE2_DV_SLEW_RATE_CTRL (0x00000380) +#define MPI_SCSIDEVPAGE2_DV_PRIM_DRIVE_STR_CTRL (0x00001C00) +#define MPI_SCSIDEVPAGE2_DV_SECOND_DRIVE_STR_CTRL (0x0000E000) +#define MPI_SCSIDEVPAGE2_DV_XCLKH_ST (0x10000000) +#define MPI_SCSIDEVPAGE2_DV_XCLKS_ST (0x20000000) +#define MPI_SCSIDEVPAGE2_DV_XCLKH_DT (0x40000000) +#define MPI_SCSIDEVPAGE2_DV_XCLKS_DT (0x80000000) + +#define MPI_SCSIDEVPAGE2_PPS_PPS_MASK (0x00000003) + +#define MPI_SCSIDEVPAGE2_DPS_BIT_0_PL_SELECT_MASK (0x00000003) +#define MPI_SCSIDEVPAGE2_DPS_BIT_1_PL_SELECT_MASK (0x0000000C) +#define MPI_SCSIDEVPAGE2_DPS_BIT_2_PL_SELECT_MASK (0x00000030) +#define MPI_SCSIDEVPAGE2_DPS_BIT_3_PL_SELECT_MASK (0x000000C0) +#define MPI_SCSIDEVPAGE2_DPS_BIT_4_PL_SELECT_MASK (0x00000300) +#define MPI_SCSIDEVPAGE2_DPS_BIT_5_PL_SELECT_MASK (0x00000C00) +#define MPI_SCSIDEVPAGE2_DPS_BIT_6_PL_SELECT_MASK (0x00003000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_7_PL_SELECT_MASK (0x0000C000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_8_PL_SELECT_MASK (0x00030000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_9_PL_SELECT_MASK (0x000C0000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_10_PL_SELECT_MASK (0x00300000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_11_PL_SELECT_MASK (0x00C00000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_12_PL_SELECT_MASK (0x03000000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_13_PL_SELECT_MASK (0x0C000000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_14_PL_SELECT_MASK (0x30000000) +#define MPI_SCSIDEVPAGE2_DPS_BIT_15_PL_SELECT_MASK (0xC0000000) + + /****************************************************************************/ /* FC Port Config Pages */ /****************************************************************************/ typedef struct _CONFIG_PAGE_FC_PORT_0 { - fCONFIG_PAGE_HEADER Header; - U32 Flags; - U8 MPIPortNumber; - U8 LinkType; - U8 PortState; - U8 Reserved; - U32 PortIdentifier; - U64 WWNN; - U64 WWPN; - U32 SupportedServiceClass; - U32 SupportedSpeeds; - U32 CurrentSpeed; - U32 MaxFrameSize; - U64 FabricWWNN; - U64 FabricWWPN; - U32 DiscoveredPortsCount; - U32 MaxInitiators; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Flags; /* 04h */ + U8 MPIPortNumber; /* 08h */ + U8 LinkType; /* 09h */ + U8 PortState; /* 0Ah */ + U8 Reserved; /* 0Bh */ + U32 PortIdentifier; /* 0Ch */ + U64 WWNN; /* 10h */ + U64 WWPN; /* 18h */ + U32 SupportedServiceClass; /* 20h */ + U32 SupportedSpeeds; /* 24h */ + U32 CurrentSpeed; /* 28h */ + U32 MaxFrameSize; /* 2Ch */ + U64 FabricWWNN; /* 30h */ + U64 FabricWWPN; /* 38h */ + U32 DiscoveredPortsCount; /* 40h */ + U32 MaxInitiators; /* 44h */ } fCONFIG_PAGE_FC_PORT_0, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_0, FCPortPage0_t, MPI_POINTER pFCPortPage0_t; @@ -591,12 +667,12 @@ typedef struct _CONFIG_PAGE_FC_PORT_0 #define MPI_FCPORTPAGE0_FLAGS_ALIAS_WWN_SUPPORTED (0x00000020) #define MPI_FCPORTPAGE0_FLAGS_FABRIC_WWN_VALID (0x00000030) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_TYPE_MASK (0x00000700) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_POINT_TO_POINT (0x00000000) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_PRIVATE_LOOP (0x00000100) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_FABRIC_DIRECT (0x00000200) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_PUBLIC_LOOP (0x00000300) -#define MPI_FCPORTPAGE0_FLAGS_ATTACH_NO_INIT (0x00000700) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_TYPE_MASK (0x00000F00) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_NO_INIT (0x00000000) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_POINT_TO_POINT (0x00000100) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_PRIVATE_LOOP (0x00000200) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_FABRIC_DIRECT (0x00000400) +#define MPI_FCPORTPAGE0_FLAGS_ATTACH_PUBLIC_LOOP (0x00000800) #define MPI_FCPORTPAGE0_LTYPE_RESERVED (0x00) #define MPI_FCPORTPAGE0_LTYPE_OTHER (0x01) @@ -639,14 +715,14 @@ typedef struct _CONFIG_PAGE_FC_PORT_0 typedef struct _CONFIG_PAGE_FC_PORT_1 { - fCONFIG_PAGE_HEADER Header; - U32 Flags; - U64 NoSEEPROMWWNN; - U64 NoSEEPROMWWPN; - U8 HardALPA; - U8 LinkConfig; - U8 TopologyConfig; - U8 Reserved; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Flags; /* 04h */ + U64 NoSEEPROMWWNN; /* 08h */ + U64 NoSEEPROMWWPN; /* 10h */ + U8 HardALPA; /* 18h */ + U8 LinkConfig; /* 19h */ + U8 TopologyConfig; /* 1Ah */ + U8 Reserved; /* 1Bh */ } fCONFIG_PAGE_FC_PORT_1, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_1, FCPortPage1_t, MPI_POINTER pFCPortPage1_t; @@ -679,23 +755,36 @@ typedef struct _CONFIG_PAGE_FC_PORT_1 typedef struct _CONFIG_PAGE_FC_PORT_2 { - fCONFIG_PAGE_HEADER Header; - U8 NumberActive; - U8 ALPA[126]; - U8 Reserved; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U8 NumberActive; /* 04h */ + U8 ALPA[126]; /* 05h */ + U8 Reserved; /* 83h */ } fCONFIG_PAGE_FC_PORT_2, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_2, FCPortPage2_t, MPI_POINTER pFCPortPage2_t; #define MPI_FCPORTPAGE2_PAGEVERSION (0x00) +typedef struct _WWN_FORMAT +{ + U64 WWNN; /* 00h */ + U64 WWPN; /* 08h */ +} WWN_FORMAT, MPI_POINTER PTR_WWN_FORMAT, + WWNFormat, MPI_POINTER pWWNFormat; + +typedef union _FC_PORT_PERSISTENT_PHYSICAL_ID +{ + WWN_FORMAT WWN; + U32 Did; +} FC_PORT_PERSISTENT_PHYSICAL_ID, MPI_POINTER PTR_FC_PORT_PERSISTENT_PHYSICAL_ID, + PersistentPhysicalId_t, MPI_POINTER pPersistentPhysicalId_t; + typedef struct _FC_PORT_PERSISTENT { - U64 WWNN; - U64 WWPN; - U8 TargetID; - U8 Bus; - U16 Flags; + FC_PORT_PERSISTENT_PHYSICAL_ID PhysicalIdentifier; /* 00h */ + U8 TargetID; /* 10h */ + U8 Bus; /* 11h */ + U16 Flags; /* 12h */ } FC_PORT_PERSISTENT, MPI_POINTER PTR_FC_PORT_PERSISTENT, PersistentData_t, MPI_POINTER pPersistentData_t; @@ -704,22 +793,23 @@ typedef struct _FC_PORT_PERSISTENT #define MPI_PERSISTENT_FLAGS_SCAN_ID (0x0002) #define MPI_PERSISTENT_FLAGS_SCAN_LUNS (0x0004) #define MPI_PERSISTENT_FLAGS_BOOT_DEVICE (0x0008) +#define MPI_PERSISTENT_FLAGS_BY_DID (0x0080) typedef struct _CONFIG_PAGE_FC_PORT_3 { - fCONFIG_PAGE_HEADER Header; - FC_PORT_PERSISTENT Entry[1]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + FC_PORT_PERSISTENT Entry[1]; /* 04h */ } fCONFIG_PAGE_FC_PORT_3, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_3, FCPortPage3_t, MPI_POINTER pFCPortPage3_t; -#define MPI_FCPORTPAGE3_PAGEVERSION (0x00) +#define MPI_FCPORTPAGE3_PAGEVERSION (0x01) typedef struct _CONFIG_PAGE_FC_PORT_4 { - fCONFIG_PAGE_HEADER Header; - U32 PortFlags; - U32 PortSettings; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 PortFlags; /* 04h */ + U32 PortSettings; /* 08h */ } fCONFIG_PAGE_FC_PORT_4, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_4, FCPortPage4_t, MPI_POINTER pFCPortPage4_t; @@ -738,18 +828,18 @@ typedef struct _CONFIG_PAGE_FC_PORT_4 typedef struct _CONFIG_PAGE_FC_PORT_5_ALIAS_INFO { - U8 Flags; - U8 AliasAlpa; - U16 Reserved; - U64 AliasWWNN; - U64 AliasWWPN; + U8 Flags; /* 00h */ + U8 AliasAlpa; /* 01h */ + U16 Reserved; /* 02h */ + U64 AliasWWNN; /* 04h */ + U64 AliasWWPN; /* 0Ch */ } fCONFIG_PAGE_FC_PORT_5_ALIAS_INFO, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_5_ALIAS_INFO, FcPortPage5AliasInfo_t, MPI_POINTER pFcPortPage5AliasInfo_t; typedef struct _CONFIG_PAGE_FC_PORT_5 { - fCONFIG_PAGE_HEADER Header; - fCONFIG_PAGE_FC_PORT_5_ALIAS_INFO AliasInfo[1]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + fCONFIG_PAGE_FC_PORT_5_ALIAS_INFO AliasInfo[1]; /* 04h */ } fCONFIG_PAGE_FC_PORT_5, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_5, FCPortPage5_t, MPI_POINTER pFCPortPage5_t; @@ -761,24 +851,24 @@ typedef struct _CONFIG_PAGE_FC_PORT_5 typedef struct _CONFIG_PAGE_FC_PORT_6 { - fCONFIG_PAGE_HEADER Header; - U32 Reserved; - U64 TimeSinceReset; - U64 TxFrames; - U64 RxFrames; - U64 TxWords; - U64 RxWords; - U64 LipCount; - U64 NosCount; - U64 ErrorFrames; - U64 DumpedFrames; - U64 LinkFailureCount; - U64 LossOfSyncCount; - U64 LossOfSignalCount; - U64 PrimativeSeqErrCount; - U64 InvalidTxWordCount; - U64 InvalidCrcCount; - U64 FcpInitiatorIoCount; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Reserved; /* 04h */ + U64 TimeSinceReset; /* 08h */ + U64 TxFrames; /* 10h */ + U64 RxFrames; /* 18h */ + U64 TxWords; /* 20h */ + U64 RxWords; /* 28h */ + U64 LipCount; /* 30h */ + U64 NosCount; /* 38h */ + U64 ErrorFrames; /* 40h */ + U64 DumpedFrames; /* 48h */ + U64 LinkFailureCount; /* 50h */ + U64 LossOfSyncCount; /* 58h */ + U64 LossOfSignalCount; /* 60h */ + U64 PrimativeSeqErrCount; /* 68h */ + U64 InvalidTxWordCount; /* 70h */ + U64 InvalidCrcCount; /* 78h */ + U64 FcpInitiatorIoCount; /* 80h */ } fCONFIG_PAGE_FC_PORT_6, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_6, FCPortPage6_t, MPI_POINTER pFCPortPage6_t; @@ -787,35 +877,65 @@ typedef struct _CONFIG_PAGE_FC_PORT_6 typedef struct _CONFIG_PAGE_FC_PORT_7 { - fCONFIG_PAGE_HEADER Header; - U32 Reserved; - U8 PortSymbolicName[256]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Reserved; /* 04h */ + U8 PortSymbolicName[256]; /* 08h */ } fCONFIG_PAGE_FC_PORT_7, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_7, FCPortPage7_t, MPI_POINTER pFCPortPage7_t; #define MPI_FCPORTPAGE7_PAGEVERSION (0x00) +typedef struct _CONFIG_PAGE_FC_PORT_8 +{ + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 BitVector[8]; /* 04h */ +} fCONFIG_PAGE_FC_PORT_8, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_8, + FCPortPage8_t, MPI_POINTER pFCPortPage8_t; + +#define MPI_FCPORTPAGE8_PAGEVERSION (0x00) + + +typedef struct _CONFIG_PAGE_FC_PORT_9 +{ + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 Reserved; /* 04h */ + U64 GlobalWWPN; /* 08h */ + U64 GlobalWWNN; /* 10h */ + U32 UnitType; /* 18h */ + U32 PhysicalPortNumber; /* 1Ch */ + U32 NumAttachedNodes; /* 20h */ + U16 IPVersion; /* 24h */ + U16 UDPPortNumber; /* 26h */ + U8 IPAddress[16]; /* 28h */ + U16 Reserved1; /* 38h */ + U16 TopologyDiscoveryFlags; /* 3Ah */ +} fCONFIG_PAGE_FC_PORT_9, MPI_POINTER PTR_CONFIG_PAGE_FC_PORT_9, + FCPortPage9_t, MPI_POINTER pFCPortPage9_t; + +#define MPI_FCPORTPAGE9_PAGEVERSION (0x00) + + /****************************************************************************/ /* FC Device Config Pages */ /****************************************************************************/ typedef struct _CONFIG_PAGE_FC_DEVICE_0 { - fCONFIG_PAGE_HEADER Header; - U64 WWNN; - U64 WWPN; - U32 PortIdentifier; - U8 Protocol; - U8 Flags; - U16 BBCredit; - U16 MaxRxFrameSize; - U8 Reserved1; - U8 PortNumber; - U8 FcPhLowestVersion; - U8 FcPhHighestVersion; - U8 CurrentTargetID; - U8 CurrentBus; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U64 WWNN; /* 04h */ + U64 WWPN; /* 0Ch */ + U32 PortIdentifier; /* 14h */ + U8 Protocol; /* 18h */ + U8 Flags; /* 19h */ + U16 BBCredit; /* 1Ah */ + U16 MaxRxFrameSize; /* 1Ch */ + U8 Reserved1; /* 1Eh */ + U8 PortNumber; /* 1Fh */ + U8 FcPhLowestVersion; /* 20h */ + U8 FcPhHighestVersion; /* 21h */ + U8 CurrentTargetID; /* 22h */ + U8 CurrentBus; /* 23h */ } fCONFIG_PAGE_FC_DEVICE_0, MPI_POINTER PTR_CONFIG_PAGE_FC_DEVICE_0, FCDevicePage0_t, MPI_POINTER pFCDevicePage0_t; @@ -841,70 +961,75 @@ typedef struct _CONFIG_PAGE_FC_DEVICE_0 /* RAID Volume Config Pages */ /****************************************************************************/ -typedef struct _RAIDVOL2_EM_PHYS_ID -{ - U8 TargetID; - U8 Bus; - U8 IocNumber; - U8 PhysDiskNumber; - U8 Reserved[8]; - U8 PhysicalDiskIdentifier[16]; - U8 ProductId[16]; - U8 InfoOffset0; - U8 InfoSize0; - U8 InfoOffset1; - U8 InfoSize1; - U8 Info[32]; -} RAIDVOL2_EM_PHYS_ID, MPI_POINTER PTR_RAIDVOL2_EM_PHYS_ID, - RaidVol2EmPhysicalID_t, MPI_POINTER pRaidVol2EmPhysicalID_t; - -typedef struct _RAIDVOL2_EM_DISK_INFO -{ - U32 DiskStatus; - U32 DeviceSettings; - U16 ErrorCount; - U16 Reserved; - U8 ErrorCdbByte; - U8 ErrorSenseKey; - U8 ErrorASC; - U8 ErrorASCQ; - U16 SmartCount; - U8 SmartASC; - U8 SmartASCQ; -} RAIDVOL2_EM_DISK_INFO, MPI_POINTER PTR_RAIDVOL2_EM_DISK_INFO, - RaidVol2EmDiskInfo_t, MPI_POINTER pRaidVol2EmDiskInfo_t; - -/* RAID Volume 2 EM Physical Disk DiskStatus flags */ - -#define MPI_RAIDVOLPAGE2_PHYS_DISK_PRIMARY (0x00000001) -#define MPI_RAIDVOLPAGE2_PHYS_DISK_SECONDARY (0x00000002) -#define MPI_RAIDVOLPAGE2_PHYS_DISK_HOT_SPARE (0x00000004) -#define MPI_RAIDVOLPAGE2_PHYS_DISK_OUT_OF_SYNC (0x00000008) -#define MPI_RAIDVOLPAGE2_PHYS_DISK_OFFLINE (0x00000010) -#define MPI_RAIDVOLPAGE2_PHYS_DISK_NOT_RESPONDING (0x00000020) - -typedef struct _RAIDVOL2_EM_PHYSICAL_DISK -{ - RAIDVOL2_EM_PHYS_ID Id; - RAIDVOL2_EM_DISK_INFO Info; -} RAIDVOL2_EM_PHYSICAL_DISK, MPI_POINTER PTR_RAIDVOL2_EM_PHYSICAL_DISK, - RaidVol2EmPhysicalDisk_t, MPI_POINTER pRaidVol2EmPhysicalDisk_t; +typedef struct _RAIDVOL2_IM_PHYS_ID +{ + U8 TargetID; /* 00h */ + U8 Bus; /* 01h */ + U8 IocNumber; /* 02h */ + U8 PhysDiskNumber; /* 03h */ + U8 Reserved[8]; /* 04h */ + U8 PhysicalDiskIdentifier[16]; /* 0Ch */ + U8 VendorId[8]; /* 1Ch */ + U8 ProductId[16]; /* 24h */ + U8 ProductRevLevel[4]; /* 34h */ + U32 Reserved1; /* 38h */ + U8 Info[32]; /* 3Ch */ +} RAIDVOL2_IM_PHYS_ID, MPI_POINTER PTR_RAIDVOL2_IM_PHYS_ID, + RaidVol2ImPhysicalID_t, MPI_POINTER pRaidVol2ImPhysicalID_t; + +typedef struct _RAIDVOL2_IM_DISK_INFO +{ + U32 DiskStatus; /* 00h */ + U32 DeviceSettings; /* 04h */ + U16 ErrorCount; /* 08h */ + U16 Reserved; /* 0Ah */ + U8 ErrorCdbByte; /* 0Ch */ + U8 ErrorSenseKey; /* 0Dh */ + U8 ErrorASC; /* 0Eh */ + U8 ErrorASCQ; /* 0Fh */ + U16 SmartCount; /* 10h */ + U8 SmartASC; /* 12h */ + U8 SmartASCQ; /* 13h */ +} RAIDVOL2_IM_DISK_INFO, MPI_POINTER PTR_RAIDVOL2_IM_DISK_INFO, + RaidVol2ImDiskInfo_t, MPI_POINTER pRaidVol2ImDiskInfo_t; + +/* RAID Volume 2 IM Physical Disk DiskStatus flags */ + +#define MPI_RVP2_PHYS_DISK_PRIMARY (0x00000001) +#define MPI_RVP2_PHYS_DISK_SECONDARY (0x00000002) +#define MPI_RVP2_PHYS_DISK_HOT_SPARE (0x00000004) +#define MPI_RVP2_PHYS_DISK_OUT_OF_SYNC (0x00000008) +#define MPI_RVP2_PHYS_DISK_STATUS_MASK (0x00000F00) +#define MPI_RVP2_PHYS_DISK_STATUS_ONLINE (0x00000000) +#define MPI_RVP2_PHYS_DISK_STATUS_MISSING (0x00000100) +#define MPI_RVP2_PHYS_DISK_STATUS_NOT_COMPATIBLE (0x00000200) +#define MPI_RVP2_PHYS_DISK_STATUS_FAILED (0x00000300) +#define MPI_RVP2_PHYS_DISK_STATUS_INITIALIZING (0x00000400) +#define MPI_RVP2_PHYS_DISK_STATUS_OFFLINE_REQUESTED (0x00000500) +#define MPI_RVP2_PHYS_DISK_STATUS_OTHER_OFFLINE (0x00000F00) + + +typedef struct _RAIDVOL2_IM_PHYSICAL_DISK +{ + RAIDVOL2_IM_PHYS_ID Id; /* 00h */ + RAIDVOL2_IM_DISK_INFO Info; /* 5Ch */ +} RAIDVOL2_IM_PHYSICAL_DISK, MPI_POINTER PTR_RAIDVOL2_IM_PHYSICAL_DISK, + RaidVol2ImPhysicalDisk_t, MPI_POINTER pRaidVol2ImPhysicalDisk_t; #define MPI_RAIDVOLPAGE2_MAX_DISKS (3) typedef struct _CONFIG_PAGE_RAID_VOL_2 { - fCONFIG_PAGE_HEADER Header; - U32 VolumeStatus; - U32 VolumeSettings; - U32 Reserved; - U64 MaxLba; - U32 BlockSize; - U8 InquirySize; - U8 NumPhysicalDisks; - U16 Reserved1; - U8 InquiryData[56]; - RAIDVOL2_EM_PHYSICAL_DISK EMPhysicalDisk[MPI_RAIDVOLPAGE2_MAX_DISKS]; + fCONFIG_PAGE_HEADER Header; /* 00h */ + U32 VolumeStatus; /* 04h */ + U32 VolumeSettings; /* 08h */ + U32 Reserved; /* 0Ch */ + U64 MaxLba; /* 10h */ + U32 BlockSize; /* 18h */ + U8 Reserved1; /* 1Ch */ + U8 NumPhysicalDisks; /* 1Dh */ + U16 Reserved2; /* 1Eh */ + RAIDVOL2_IM_PHYSICAL_DISK IMPhysicalDisk[MPI_RAIDVOLPAGE2_MAX_DISKS]; } fCONFIG_PAGE_RAID_VOL_2, MPI_POINTER PTR_CONFIG_PAGE_RAID_VOL_2, RaidVolumePage2_t, MPI_POINTER pRaidVolumePage2_t; @@ -922,6 +1047,7 @@ typedef struct _CONFIG_PAGE_RAID_VOL_2 #define MPI_RAIDVOLPAGE2_SETTING_WRITE_CACHING_ENABLE (0x00000001) #define MPI_RAIDVOLPAGE2_SETTING_OFFLINE_ON_SMART (0x00000002) #define MPI_RAIDVOLPAGE2_SETTING_AUTO_CONFIGURE (0x00000004) +#define MPI_RAIDVOLPAGE2_SETTING_USE_DEFAULTS (0x80000000) /****************************************************************************/ @@ -930,10 +1056,10 @@ typedef struct _CONFIG_PAGE_RAID_VOL_2 typedef struct _CONFIG_PAGE_LAN_0 { - ConfigPageHeader_t Header; - U16 TxRxModes; - U16 Reserved; - U32 PacketPrePad; + ConfigPageHeader_t Header; /* 00h */ + U16 TxRxModes; /* 04h */ + U16 Reserved; /* 06h */ + U32 PacketPrePad; /* 08h */ } fCONFIG_PAGE_LAN_0, MPI_POINTER PTR_CONFIG_PAGE_LAN_0, LANPage0_t, MPI_POINTER pLANPage0_t; @@ -945,20 +1071,20 @@ typedef struct _CONFIG_PAGE_LAN_0 typedef struct _CONFIG_PAGE_LAN_1 { - ConfigPageHeader_t Header; - U16 Reserved; - U8 CurrentDeviceState; - U8 Reserved1; - U32 MinPacketSize; - U32 MaxPacketSize; - U32 HardwareAddressLow; - U32 HardwareAddressHigh; - U32 MaxWireSpeedLow; - U32 MaxWireSpeedHigh; - U32 BucketsRemaining; - U32 MaxReplySize; - U32 NegWireSpeedHigh; - U32 NegWireSpeedLow; + ConfigPageHeader_t Header; /* 00h */ + U16 Reserved; /* 04h */ + U8 CurrentDeviceState; /* 06h */ + U8 Reserved1; /* 07h */ + U32 MinPacketSize; /* 08h */ + U32 MaxPacketSize; /* 0Ch */ + U32 HardwareAddressLow; /* 10h */ + U32 HardwareAddressHigh; /* 14h */ + U32 MaxWireSpeedLow; /* 18h */ + U32 MaxWireSpeedHigh; /* 1Ch */ + U32 BucketsRemaining; /* 20h */ + U32 MaxReplySize; /* 24h */ + U32 NegWireSpeedHigh; /* 28h */ + U32 NegWireSpeedLow; /* 2Ch */ } fCONFIG_PAGE_LAN_1, MPI_POINTER PTR_CONFIG_PAGE_LAN_1, LANPage1_t, MPI_POINTER pLANPage1_t; diff --git a/drivers/message/fusion/lsi/mpi_fc.h b/drivers/message/fusion/lsi/mpi_fc.h index 73d17d2217ba..042953b4a756 100644 --- a/drivers/message/fusion/lsi/mpi_fc.h +++ b/drivers/message/fusion/lsi/mpi_fc.h @@ -6,7 +6,7 @@ * Title: MPI Fibre Channel messages and structures * Creation Date: June 12, 2000 * - * MPI Version: 01.01.05 + * MPI Version: 01.01.07 * * Version History * --------------- @@ -27,6 +27,11 @@ * FC_ABORT_TYPE_EXLINKSEND_REQUEST for FcAbort request. * Added MPI_FC_PRIM_SEND_FLAGS_STOP_SEND. * 02-20-01 01.01.05 Started using MPI_POINTER. + * 03-27-01 01.01.06 Added Flags field to MSG_LINK_SERVICE_BUFFER_POST_REPLY + * and defined MPI_LS_BUF_POST_REPLY_FLAG_NO_RSP_NEEDED. + * Added MPI_FC_PRIM_SEND_FLAGS_RESET_LINK define. + * Added structure offset comments. + * 04-09-01 01.01.07 Added RspLength field to MSG_LINK_SERVICE_RSP_REQUEST. * -------------------------------------------------------------------------- */ @@ -136,7 +141,7 @@ typedef struct _MSG_LINK_SERVICE_BUFFER_POST_REPLY typedef struct _MSG_LINK_SERVICE_RSP_REQUEST { U8 RspFlags; /* 00h */ - U8 Reserved; /* 01h */ + U8 RspLength; /* 01h */ U8 ChainOffset; /* 02h */ U8 Function; /* 03h */ U16 Reserved1; /* 04h */ @@ -224,14 +229,14 @@ typedef struct _MSG_EXLINK_SERVICE_SEND_REPLY typedef struct _MSG_FC_ABORT_REQUEST { - U8 AbortFlags; /* 00h */ - U8 AbortType; /* 01h */ - U8 ChainOffset; /* 02h */ - U8 Function; /* 03h */ - U16 Reserved1; /* 04h */ - U8 Reserved2; /* 06h */ - U8 MsgFlags; /* 07h */ - U32 MsgContext; /* 08h */ + U8 AbortFlags; /* 00h */ + U8 AbortType; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ U32 TransactionContextToAbort; /* 0Ch */ } MSG_FC_ABORT_REQUEST, MPI_POINTER PTR_MSG_FC_ABORT_REQUEST, FcAbortRequest_t, MPI_POINTER pFcAbortRequest_t; @@ -323,6 +328,7 @@ typedef struct _MSG_FC_PRIMITIVE_SEND_REQUEST FcPrimitiveSendRequest_t, MPI_POINTER pFcPrimitiveSendRequest_t; #define MPI_FC_PRIM_SEND_FLAGS_PORT_MASK (0x01) +#define MPI_FC_PRIM_SEND_FLAGS_RESET_LINK (0x04) #define MPI_FC_PRIM_SEND_FLAGS_STOP_SEND (0x08) #define MPI_FC_PRIM_SEND_FLAGS_SEND_ONCE (0x10) #define MPI_FC_PRIM_SEND_FLAGS_SEND_AROUND (0x20) diff --git a/drivers/message/fusion/lsi/mpi_history.txt b/drivers/message/fusion/lsi/mpi_history.txt index 5ac3e0622f52..0deb7721e936 100644 --- a/drivers/message/fusion/lsi/mpi_history.txt +++ b/drivers/message/fusion/lsi/mpi_history.txt @@ -6,22 +6,22 @@ Copyright (c) 2000-2001 LSI Logic Corporation. --------------------------------------- - Header Set Release Version: 01.01.08 - Header Set Release Date: 02-27-01 + Header Set Release Version: 01.01.10 + Header Set Release Date: 04-09-01 --------------------------------------- Filename Current version Prior version ---------- --------------- ------------- - mpi.h 01.01.06 01.01.05 - mpi_ioc.h 01.01.05 01.01.04 - mpi_cnfg.h 01.01.09 01.01.08 - mpi_init.h 01.01.03 01.01.03 - mpi_targ.h 01.01.03 01.01.03 - mpi_fc.h 01.01.05 01.01.05 - mpi_lan.h 01.01.02 01.01.02 - mpi_raid.h 01.01.01 none + mpi.h 01.01.07 01.01.06 + mpi_ioc.h 01.01.07 01.01.06 + mpi_cnfg.h 01.01.11 01.01.10 + mpi_init.h 01.01.05 01.01.04 + mpi_targ.h 01.01.04 01.01.04 + mpi_fc.h 01.01.07 01.01.06 + mpi_lan.h 01.01.03 01.01.03 + mpi_raid.h 01.01.02 01.01.02 mpi_type.h 01.01.02 01.01.02 - mpi_history.txt 01.01.08 01.01.07 + mpi_history.txt 01.01.09 01.01.09 * Date Version Description @@ -51,6 +51,8 @@ mpi.h * Obsoleted MPI_IOCSTATUS_TARGET_FC_ defines. * 02-27-01 01.01.06 Removed MPI_HOST_INDEX_REGISTER define. * Added function codes for RAID. + * 04-09-01 01.01.07 Added alternate define for MPI_DOORBELL_ACTIVE, + * MPI_DOORBELL_USED, to better match the spec. * -------------------------------------------------------------------------- mpi_ioc.h @@ -76,6 +78,9 @@ mpi_ioc.h * 02-20-01 01.01.04 Started using MPI_POINTER. * 02-27-01 01.01.05 Added event for RAID status change and its event data. * Added IocNumber field to MSG_IOC_FACTS_REPLY. + * 03-27-01 01.01.06 Added defines for ProductId field of MPI_FW_HEADER. + * Added structure offset comments. + * 04-09-01 01.01.07 Added structure EVENT_DATA_EVENT_CHANGE. * -------------------------------------------------------------------------- mpi_cnfg.h @@ -125,6 +130,18 @@ mpi_cnfg.h * MPI_CONFIG_PAGETYPE_RAID_VOLUME. * Added definitions and structures for IOC Page 2 and * RAID Volume Page 2. + * 03-27-01 01.01.10 Added CONFIG_PAGE_FC_PORT_8 and CONFIG_PAGE_FC_PORT_9. + * CONFIG_PAGE_FC_PORT_3 now supports persistent by DID. + * Added VendorId and ProductRevLevel fields to + * RAIDVOL2_IM_PHYS_ID struct. + * Modified values for MPI_FCPORTPAGE0_FLAGS_ATTACH_ + * defines to make them compatible to MPI version 1.0. + * Added structure offset comments. + * 04-09-01 01.01.11 Added some new defines for the PageAddress field and + * removed some obsolete ones. + * Added IO Unit Page 3. + * Modified defines for Scsi Port Page 2. + * Modified RAID Volume Pages. * -------------------------------------------------------------------------- mpi_init.h @@ -135,6 +152,8 @@ mpi_init.h * 11-02-00 01.01.01 Original release for post 1.0 work * 12-04-00 01.01.02 Added MPI_SCSIIO_CONTROL_NO_DISCONNECT. * 02-20-01 01.01.03 Started using MPI_POINTER. + * 03-27-01 01.01.04 Added structure offset comments. + * 04-10-01 01.01.05 Added new MsgFlag for MSG_SCSI_TASK_MGMT. * -------------------------------------------------------------------------- mpi_targ.h @@ -150,6 +169,7 @@ mpi_targ.h * 02-20-01 01.01.03 Started using MPI_POINTER. * Added structures for MPI_TARGET_SCSI_SPI_CMD_BUFFER and * MPI_TARGET_FCP_CMD_BUFFER. + * 03-27-01 01.01.04 Added structure offset comments. * -------------------------------------------------------------------------- mpi_fc.h @@ -167,6 +187,11 @@ mpi_fc.h * FC_ABORT_TYPE_EXLINKSEND_REQUEST for FcAbort request. * Added MPI_FC_PRIM_SEND_FLAGS_STOP_SEND. * 02-20-01 01.01.05 Started using MPI_POINTER. + * 03-27-01 01.01.06 Added Flags field to MSG_LINK_SERVICE_BUFFER_POST_REPLY + * and defined MPI_LS_BUF_POST_REPLY_FLAG_NO_RSP_NEEDED. + * Added MPI_FC_PRIM_SEND_FLAGS_RESET_LINK define. + * Added structure offset comments. + * 04-09-01 01.01.07 Added RspLength field to MSG_LINK_SERVICE_RSP_REQUEST. * -------------------------------------------------------------------------- mpi_lan.h @@ -183,10 +208,12 @@ mpi_lan.h * to lan private header file * 11-02-00 01.01.01 Original release for post 1.0 work * 02-20-01 01.01.02 Started using MPI_POINTER. + * 03-27-01 01.01.03 Added structure offset comments. * -------------------------------------------------------------------------- mpi_raid.h * 02-27-01 01.01.01 Original release for this file. + * 03-27-01 01.01.02 Added structure offset comments. * -------------------------------------------------------------------------- mpi_type.h @@ -198,17 +225,29 @@ mpi_type.h mpi_history.txt Parts list history -Filename 01.01.08 01.01.07 01.01.06 01.01.05 01.01.04 ----------- -------- -------- -------- -------- -------- -mpi.h 01.01.06 01.01.05 01.01.04 01.01.04 01.01.03 -mpi_ioc.h 01.01.05 01.01.04 01.01.03 01.01.03 01.01.03 -mpi_cnfg.h 01.01.09 01.01.08 01.01.07 01.01.06 01.01.05 -mpi_init.h 01.01.03 01.01.03 01.01.02 01.01.02 01.01.02 -mpi_targ.h 01.01.03 01.01.03 01.01.02 01.01.02 01.01.02 -mpi_fc.h 01.01.05 01.01.05 01.01.04 01.01.04 01.01.03 -mpi_lan.h 01.01.02 01.01.02 01.01.01 01.01.01 01.01.01 -mpi_raid.h 01.01.01 -mpi_type.h 01.01.02 01.01.02 01.01.01 01.01.01 01.01.01 +Filename 01.01.10 +---------- -------- +mpi.h 01.01.07 +mpi_ioc.h 01.01.07 +mpi_cnfg.h 01.01.11 +mpi_init.h 01.01.05 +mpi_targ.h 01.01.04 +mpi_fc.h 01.01.07 +mpi_lan.h 01.01.03 +mpi_raid.h 01.01.02 +mpi_type.h 01.01.02 + +Filename 01.01.09 01.01.08 01.01.07 01.01.06 01.01.05 01.01.04 +---------- -------- -------- -------- -------- -------- -------- +mpi.h 01.01.06 01.01.06 01.01.05 01.01.04 01.01.04 01.01.03 +mpi_ioc.h 01.01.06 01.01.05 01.01.04 01.01.03 01.01.03 01.01.03 +mpi_cnfg.h 01.01.10 01.01.09 01.01.08 01.01.07 01.01.06 01.01.05 +mpi_init.h 01.01.04 01.01.03 01.01.03 01.01.02 01.01.02 01.01.02 +mpi_targ.h 01.01.04 01.01.03 01.01.03 01.01.02 01.01.02 01.01.02 +mpi_fc.h 01.01.06 01.01.05 01.01.05 01.01.04 01.01.04 01.01.03 +mpi_lan.h 01.01.03 01.01.02 01.01.02 01.01.01 01.01.01 01.01.01 +mpi_raid.h 01.01.02 01.01.01 +mpi_type.h 01.01.02 01.01.02 01.01.02 01.01.01 01.01.01 01.01.01 Filename 01.01.03 01.01.02 01.01.01 01.00.07 01.00.06 01.00.05 ---------- -------- -------- -------- -------- -------- -------- diff --git a/drivers/message/fusion/lsi/mpi_init.h b/drivers/message/fusion/lsi/mpi_init.h index 4f3c8dc705c5..5d871e4fd11d 100644 --- a/drivers/message/fusion/lsi/mpi_init.h +++ b/drivers/message/fusion/lsi/mpi_init.h @@ -6,7 +6,7 @@ * Title: MPI initiator mode messages and structures * Creation Date: June 8, 2000 * - * MPI Version: 01.01.03 + * MPI Version: 01.01.05 * * Version History * --------------- @@ -20,6 +20,8 @@ * 11-02-00 01.01.01 Original release for post 1.0 work. * 12-04-00 01.01.02 Added MPI_SCSIIO_CONTROL_NO_DISCONNECT. * 02-20-01 01.01.03 Started using MPI_POINTER. + * 03-27-01 01.01.04 Added structure offset comments. + * 04-10-01 01.01.05 Added new MsgFlag for MSG_SCSI_TASK_MGMT. * -------------------------------------------------------------------------- */ @@ -39,21 +41,21 @@ typedef struct _MSG_SCSI_IO_REQUEST { - U8 TargetID; - U8 Bus; - U8 ChainOffset; - U8 Function; - U8 CDBLength; - U8 SenseBufferLength; - U8 Reserved; - U8 MsgFlags; - U32 MsgContext; - U8 LUN[8]; - U32 Control; - U8 CDB[16]; - U32 DataLength; - U32 SenseBufferLowAddr; - SGE_IO_UNION SGL; + U8 TargetID; /* 00h */ + U8 Bus; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 CDBLength; /* 04h */ + U8 SenseBufferLength; /* 05h */ + U8 Reserved; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 LUN[8]; /* 0Ch */ + U32 Control; /* 14h */ + U8 CDB[16]; /* 18h */ + U32 DataLength; /* 28h */ + U32 SenseBufferLowAddr; /* 2Ch */ + SGE_IO_UNION SGL; /* 30h */ } MSG_SCSI_IO_REQUEST, MPI_POINTER PTR_MSG_SCSI_IO_REQUEST, SCSIIORequest_t, MPI_POINTER pSCSIIORequest_t; @@ -108,22 +110,22 @@ typedef struct _MSG_SCSI_IO_REQUEST /* SCSIIO reply structure */ typedef struct _MSG_SCSI_IO_REPLY { - U8 TargetID; - U8 Bus; - U8 MsgLength; - U8 Function; - U8 CDBLength; - U8 SenseBufferLength; - U8 Reserved; - U8 MsgFlags; - U32 MsgContext; - U8 SCSIStatus; - U8 SCSIState; - U16 IOCStatus; - U32 IOCLogInfo; - U32 TransferCount; - U32 SenseCount; - U32 ResponseInfo; + U8 TargetID; /* 00h */ + U8 Bus; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 CDBLength; /* 04h */ + U8 SenseBufferLength; /* 05h */ + U8 Reserved; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 SCSIStatus; /* 0Ch */ + U8 SCSIState; /* 0Dh */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 TransferCount; /* 14h */ + U32 SenseCount; /* 18h */ + U32 ResponseInfo; /* 1Ch */ } MSG_SCSI_IO_REPLY, MPI_POINTER PTR_MSG_SCSI_IO_REPLY, SCSIIOReply_t, MPI_POINTER pSCSIIOReply_t; @@ -168,47 +170,49 @@ typedef struct _MSG_SCSI_IO_REPLY typedef struct _MSG_SCSI_TASK_MGMT { - U8 TargetID; - U8 Bus; - U8 ChainOffset; - U8 Function; - U8 Reserved; - U8 TaskType; - U8 Reserved1; - U8 MsgFlags; - U32 MsgContext; - U8 LUN[8]; - U32 Reserved2[7]; - U32 TaskMsgContext; + U8 TargetID; /* 00h */ + U8 Bus; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved; /* 04h */ + U8 TaskType; /* 05h */ + U8 Reserved1; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 LUN[8]; /* 0Ch */ + U32 Reserved2[7]; /* 14h */ + U32 TaskMsgContext; /* 30h */ } MSG_SCSI_TASK_MGMT, MPI_POINTER PTR_SCSI_TASK_MGMT, SCSITaskMgmt_t, MPI_POINTER pSCSITaskMgmt_t; /* TaskType values */ -#define MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK (0x00000001) -#define MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET (0x00000002) -#define MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET (0x00000003) -#define MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS (0x00000004) +#define MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK (0x01) +#define MPI_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET (0x02) +#define MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET (0x03) +#define MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS (0x04) /* MsgFlags bits */ -#define MPI_SCSITASKMGMT_MSGFLAGS_LIP_RESET_OPTION (0x00000002) +#define MPI_SCSITASKMGMT_MSGFLAGS_TARGET_RESET_OPTION (0x00) +#define MPI_SCSITASKMGMT_MSGFLAGS_LIP_RESET_OPTION (0x02) +#define MPI_SCSITASKMGMT_MSGFLAGS_LIPRESET_RESET_OPTION (0x04) /* SCSI Task Management Reply */ typedef struct _MSG_SCSI_TASK_MGMT_REPLY { - U8 TargetID; - U8 Bus; - U8 MsgLength; - U8 Function; - U8 Reserved; - U8 TaskType; - U8 Reserved1; - U8 MsgFlags; - U32 MsgContext; - U8 Reserved2[2]; - U16 IOCStatus; - U32 IOCLogInfo; - U32 TerminationCount; + U8 TargetID; /* 00h */ + U8 Bus; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved; /* 04h */ + U8 TaskType; /* 05h */ + U8 Reserved1; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 Reserved2[2]; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 TerminationCount; /* 14h */ } MSG_SCSI_TASK_MGMT_REPLY, MPI_POINTER PTR_MSG_SCSI_TASK_MGMT_REPLY, SCSITaskMgmtReply_t, MPI_POINTER pSCSITaskMgmtReply_t; diff --git a/drivers/message/fusion/lsi/mpi_ioc.h b/drivers/message/fusion/lsi/mpi_ioc.h index 0411671dc9a9..d910811bc0ff 100644 --- a/drivers/message/fusion/lsi/mpi_ioc.h +++ b/drivers/message/fusion/lsi/mpi_ioc.h @@ -3,10 +3,10 @@ * * * Name: MPI_IOC.H - * Title: MPI IOC, Port, Event, FW Load, and ToolBox messages + * Title: MPI IOC, Port, Event, FW Download, and FW Upload messages * Creation Date: August 11, 2000 * - * MPI Version: 01.01.05 + * MPI Version: 01.01.07 * * Version History * --------------- @@ -35,6 +35,9 @@ * 02-20-01 01.01.04 Started using MPI_POINTER. * 02-27-01 01.01.05 Added event for RAID status change and its event data. * Added IocNumber field to MSG_IOC_FACTS_REPLY. + * 03-27-01 01.01.06 Added defines for ProductId field of MPI_FW_HEADER. + * Added structure offset comments. + * 04-09-01 01.01.07 Added structure EVENT_DATA_EVENT_CHANGE. * -------------------------------------------------------------------------- */ @@ -54,36 +57,36 @@ typedef struct _MSG_IOC_INIT { - U8 WhoInit; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U8 Flags; - U8 MaxDevices; - U8 MaxBuses; - U8 MsgFlags; - U32 MsgContext; - U16 ReplyFrameSize; - U8 Reserved1[2]; - U32 HostMfaHighAddr; - U32 SenseBufferHighAddr; + U8 WhoInit; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Flags; /* 04h */ + U8 MaxDevices; /* 05h */ + U8 MaxBuses; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 ReplyFrameSize; /* 0Ch */ + U8 Reserved1[2]; /* 0Eh */ + U32 HostMfaHighAddr; /* 10h */ + U32 SenseBufferHighAddr; /* 14h */ } MSG_IOC_INIT, MPI_POINTER PTR_MSG_IOC_INIT, IOCInit_t, MPI_POINTER pIOCInit_t; typedef struct _MSG_IOC_INIT_REPLY { - U8 WhoInit; - U8 Reserved; - U8 MsgLength; - U8 Function; - U8 Flags; - U8 MaxDevices; - U8 MaxBuses; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; + U8 WhoInit; /* 00h */ + U8 Reserved; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Flags; /* 04h */ + U8 MaxDevices; /* 05h */ + U8 MaxBuses; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_IOC_INIT_REPLY, MPI_POINTER PTR_MSG_IOC_INIT_REPLY, IOCInitReply_t, MPI_POINTER pIOCInitReply_t; @@ -103,12 +106,12 @@ typedef struct _MSG_IOC_INIT_REPLY typedef struct _MSG_IOC_FACTS { - U8 Reserved[2]; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; + U8 Reserved[2]; /* 00h */ + U8 ChainOffset; /* 01h */ + U8 Function; /* 02h */ + U8 Reserved1[3]; /* 03h */ + U8 MsgFlags; /* 04h */ + U32 MsgContext; /* 08h */ } MSG_IOC_FACTS, MPI_POINTER PTR_IOC_FACTS, IOCFacts_t, MPI_POINTER pIOCFacts_t; @@ -116,34 +119,34 @@ typedef struct _MSG_IOC_FACTS typedef struct _MSG_IOC_FACTS_REPLY { - U16 MsgVersion; - U8 MsgLength; - U8 Function; - U16 Reserved; - U8 IOCNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; - U8 MaxChainDepth; - U8 WhoInit; - U8 BlockSize; - U8 Flags; - U16 ReplyQueueDepth; - U16 RequestFrameSize; - U16 FWVersion; - U16 ProductID; - U32 CurrentHostMfaHighAddr; - U16 GlobalCredits; - U8 NumberOfPorts; - U8 EventState; - U32 CurrentSenseBufferHighAddr; - U16 CurReplyFrameSize; - U8 MaxDevices; - U8 MaxBuses; - U32 FWImageSize; - U32 DataImageSize; + U16 MsgVersion; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved; /* 04h */ + U8 IOCNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U8 MaxChainDepth; /* 14h */ + U8 WhoInit; /* 15h */ + U8 BlockSize; /* 16h */ + U8 Flags; /* 17h */ + U16 ReplyQueueDepth; /* 18h */ + U16 RequestFrameSize; /* 1Ah */ + U16 FWVersion; /* 1Ch */ + U16 ProductID; /* 1Eh */ + U32 CurrentHostMfaHighAddr; /* 20h */ + U16 GlobalCredits; /* 24h */ + U8 NumberOfPorts; /* 26h */ + U8 EventState; /* 27h */ + U32 CurrentSenseBufferHighAddr; /* 28h */ + U16 CurReplyFrameSize; /* 2Ch */ + U8 MaxDevices; /* 2Eh */ + U8 MaxBuses; /* 2Fh */ + U32 FWImageSize; /* 30h */ + U32 DataImageSize; /* 34h */ } MSG_IOC_FACTS_REPLY, MPI_POINTER PTR_MSG_IOC_FACTS_REPLY, IOCFactsReply_t, MPI_POINTER pIOCFactsReply_t; @@ -170,38 +173,38 @@ typedef struct _MSG_IOC_FACTS_REPLY typedef struct _MSG_PORT_FACTS { - U8 Reserved[2]; - U8 ChainOffset; - U8 Function; - U8 Reserved1[2]; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; + U8 Reserved[2]; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[2]; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ } MSG_PORT_FACTS, MPI_POINTER PTR_MSG_PORT_FACTS, PortFacts_t, MPI_POINTER pPortFacts_t; typedef struct _MSG_PORT_FACTS_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved1; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; - U8 Reserved3; - U8 PortType; - U16 MaxDevices; - U16 PortSCSIID; - U16 ProtocolFlags; - U16 MaxPostedCmdBuffers; - U16 MaxPersistentIDs; - U16 MaxLanBuckets; - U16 Reserved4; - U32 Reserved5; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U8 Reserved3; /* 14h */ + U8 PortType; /* 15h */ + U16 MaxDevices; /* 16h */ + U16 PortSCSIID; /* 18h */ + U16 ProtocolFlags; /* 1Ah */ + U16 MaxPostedCmdBuffers; /* 1Ch */ + U16 MaxPersistentIDs; /* 1Eh */ + U16 MaxLanBuckets; /* 20h */ + U16 Reserved4; /* 22h */ + U32 Reserved5; /* 24h */ } MSG_PORT_FACTS_REPLY, MPI_POINTER PTR_MSG_PORT_FACTS_REPLY, PortFactsReply_t, MPI_POINTER pPortFactsReply_t; @@ -226,28 +229,28 @@ typedef struct _MSG_PORT_FACTS_REPLY typedef struct _MSG_PORT_ENABLE { - U8 Reserved[2]; - U8 ChainOffset; - U8 Function; - U8 Reserved1[2]; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; + U8 Reserved[2]; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[2]; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ } MSG_PORT_ENABLE, MPI_POINTER PTR_MSG_PORT_ENABLE, PortEnable_t, MPI_POINTER pPortEnable_t; typedef struct _MSG_PORT_ENABLE_REPLY { - U8 Reserved[2]; - U8 MsgLength; - U8 Function; - U8 Reserved1[2]; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; + U8 Reserved[2]; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[2]; /* 04h */ + U8 PortNumber; /* 05h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_PORT_ENABLE_REPLY, MPI_POINTER PTR_MSG_PORT_ENABLE_REPLY, PortEnableReply_t, MPI_POINTER pPortEnableReply_t; @@ -264,13 +267,13 @@ typedef struct _MSG_PORT_ENABLE_REPLY typedef struct _MSG_EVENT_NOTIFY { - U8 Switch; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; + U8 Switch; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ } MSG_EVENT_NOTIFY, MPI_POINTER PTR_MSG_EVENT_NOTIFY, EventNotification_t, MPI_POINTER pEventNotification_t; @@ -278,19 +281,19 @@ typedef struct _MSG_EVENT_NOTIFY typedef struct _MSG_EVENT_NOTIFY_REPLY { - U16 EventDataLength; - U8 MsgLength; - U8 Function; - U8 Reserved1[2]; - U8 AckRequired; - U8 MsgFlags; - U32 MsgContext; - U8 Reserved2[2]; - U16 IOCStatus; - U32 IOCLogInfo; - U32 Event; - U32 EventContext; - U32 Data[1]; + U16 EventDataLength; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[2]; /* 04h */ + U8 AckRequired; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 Reserved2[2]; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 Event; /* 14h */ + U32 EventContext; /* 18h */ + U32 Data[1]; /* 1Ch */ } MSG_EVENT_NOTIFY_REPLY, MPI_POINTER PTR_MSG_EVENT_NOTIFY_REPLY, EventNotificationReply_t, MPI_POINTER pEventNotificationReply_t; @@ -298,28 +301,28 @@ typedef struct _MSG_EVENT_NOTIFY_REPLY typedef struct _MSG_EVENT_ACK { - U8 Reserved[2]; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U32 Event; - U32 EventContext; + U8 Reserved[2]; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U32 Event; /* 0Ch */ + U32 EventContext; /* 10h */ } MSG_EVENT_ACK, MPI_POINTER PTR_MSG_EVENT_ACK, EventAck_t, MPI_POINTER pEventAck_t; typedef struct _MSG_EVENT_ACK_REPLY { - U8 Reserved[2]; - U8 MsgLength; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; + U8 Reserved[2]; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_EVENT_ACK_REPLY, MPI_POINTER PTR_MSG_EVENT_ACK_REPLY, EventAckReply_t, MPI_POINTER pEventAckReply_t; @@ -349,13 +352,23 @@ typedef struct _MSG_EVENT_ACK_REPLY #define MPI_EVENT_NOTIFICATION_ACK_NOT_REQUIRED (0x00) #define MPI_EVENT_NOTIFICATION_ACK_REQUIRED (0x01) -/* SCSI Event data for Port, Bus and Device forms) */ +/* EventChange Event data */ + +typedef struct _EVENT_DATA_EVENT_CHANGE +{ + U8 EventState; /* 00h */ + U8 Reserved; /* 01h */ + U16 Reserved1; /* 02h */ +} EVENT_DATA_EVENT_CHANGE, MPI_POINTER PTR_EVENT_DATA_EVENT_CHANGE, + EventDataEventChange_t, MPI_POINTER pEventDataEventChange_t; + +/* SCSI Event data for Port, Bus and Device forms */ typedef struct _EVENT_DATA_SCSI { - U8 TargetID; - U8 BusPort; - U16 Reserved; + U8 TargetID; /* 00h */ + U8 BusPort; /* 01h */ + U16 Reserved; /* 02h */ } EVENT_DATA_SCSI, MPI_POINTER PTR_EVENT_DATA_SCSI, EventDataScsi_t, MPI_POINTER pEventDataScsi_t; @@ -363,12 +376,12 @@ typedef struct _EVENT_DATA_SCSI typedef struct _EVENT_DATA_LINK_STATUS { - U8 State; - U8 Reserved; - U16 Reserved1; - U8 Reserved2; - U8 Port; - U16 Reserved3; + U8 State; /* 00h */ + U8 Reserved; /* 01h */ + U16 Reserved1; /* 02h */ + U8 Reserved2; /* 04h */ + U8 Port; /* 05h */ + U16 Reserved3; /* 06h */ } EVENT_DATA_LINK_STATUS, MPI_POINTER PTR_EVENT_DATA_LINK_STATUS, EventDataLinkStatus_t, MPI_POINTER pEventDataLinkStatus_t; @@ -379,13 +392,13 @@ typedef struct _EVENT_DATA_LINK_STATUS typedef struct _EVENT_DATA_LOOP_STATE { - U8 Character4; - U8 Character3; - U8 Type; - U8 Reserved; - U8 Reserved1; - U8 Port; - U16 Reserved2; + U8 Character4; /* 00h */ + U8 Character3; /* 01h */ + U8 Type; /* 02h */ + U8 Reserved; /* 03h */ + U8 Reserved1; /* 04h */ + U8 Port; /* 05h */ + U16 Reserved2; /* 06h */ } EVENT_DATA_LOOP_STATE, MPI_POINTER PTR_EVENT_DATA_LOOP_STATE, EventDataLoopState_t, MPI_POINTER pEventDataLoopState_t; @@ -397,10 +410,10 @@ typedef struct _EVENT_DATA_LOOP_STATE typedef struct _EVENT_DATA_LOGOUT { - U32 NPortID; - U8 Reserved; - U8 Port; - U16 Reserved1; + U32 NPortID; /* 00h */ + U8 Reserved; /* 04h */ + U8 Port; /* 05h */ + U16 Reserved1; /* 06h */ } EVENT_DATA_LOGOUT, MPI_POINTER PTR_EVENT_DATA_LOGOUT, EventDataLogout_t, MPI_POINTER pEventDataLogout_t; @@ -408,13 +421,13 @@ typedef struct _EVENT_DATA_LOGOUT typedef struct _EVENT_DATA_RAID_STATUS_CHANGE { - U8 VolumeTargetID; - U8 VolumeBus; - U8 ReasonCode; - U8 PhysDiskNum; - U8 ASC; - U8 ASCQ; - U16 Reserved; + U8 VolumeTargetID; /* 00h */ + U8 VolumeBus; /* 01h */ + U8 ReasonCode; /* 02h */ + U8 PhysDiskNum; /* 03h */ + U8 ASC; /* 04h */ + U8 ASCQ; /* 05h */ + U16 Reserved; /* 06h */ } EVENT_DATA_RAID_STATUS_CHANGE, MPI_POINTER PTR_EVENT_DATA_RAID_STATUS_CHANGE, MpiEventDataRaidStatusChange_t, MPI_POINTER pMpiEventDataRaidStatusChange_t; @@ -441,14 +454,14 @@ typedef struct _EVENT_DATA_RAID_STATUS_CHANGE typedef struct _MSG_FW_DOWNLOAD { - U8 ImageType; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - SGE_MPI_UNION SGL; + U8 ImageType; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + SGE_MPI_UNION SGL; /* 0Ch */ } MSG_FW_DOWNLOAD, MPI_POINTER PTR_MSG_FW_DOWNLOAD, FWDownload_t, MPI_POINTER pFWDownload_t; @@ -459,29 +472,29 @@ typedef struct _MSG_FW_DOWNLOAD typedef struct _FWDownloadTCSGE { - U8 Reserved; - U8 ContextSize; - U8 DetailsLength; - U8 Flags; - U32 Reserved1; - U32 ImageOffset; - U32 ImageSize; + U8 Reserved; /* 00h */ + U8 ContextSize; /* 01h */ + U8 DetailsLength; /* 02h */ + U8 Flags; /* 03h */ + U32 Reserved1; /* 04h */ + U32 ImageOffset; /* 08h */ + U32 ImageSize; /* 0Ch */ } FW_DOWNLOAD_TCSGE, MPI_POINTER PTR_FW_DOWNLOAD_TCSGE, FWDownloadTCSGE_t, MPI_POINTER pFWDownloadTCSGE_t; /* Firmware Download reply */ typedef struct _MSG_FW_DOWNLOAD_REPLY { - U8 ImageType; - U8 Reserved; - U8 MsgLength; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; + U8 ImageType; /* 00h */ + U8 Reserved; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_FW_DOWNLOAD_REPLY, MPI_POINTER PTR_MSG_FW_DOWNLOAD_REPLY, FWDownloadReply_t, MPI_POINTER pFWDownloadReply_t; @@ -492,14 +505,14 @@ typedef struct _MSG_FW_DOWNLOAD_REPLY typedef struct _MSG_FW_UPLOAD { - U8 ImageType; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - SGE_MPI_UNION SGL; + U8 ImageType; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + SGE_MPI_UNION SGL; /* 0Ch */ } MSG_FW_UPLOAD, MPI_POINTER PTR_MSG_FW_UPLOAD, FWUpload_t, MPI_POINTER pFWUpload_t; @@ -510,74 +523,88 @@ typedef struct _MSG_FW_UPLOAD typedef struct _FWUploadTCSGE { - U8 Reserved; - U8 ContextSize; - U8 DetailsLength; - U8 Flags; - U32 Reserved1; - U32 ImageOffset; - U32 ImageSize; + U8 Reserved; /* 00h */ + U8 ContextSize; /* 01h */ + U8 DetailsLength; /* 02h */ + U8 Flags; /* 03h */ + U32 Reserved1; /* 04h */ + U32 ImageOffset; /* 08h */ + U32 ImageSize; /* 0Ch */ } FW_UPLOAD_TCSGE, MPI_POINTER PTR_FW_UPLOAD_TCSGE, FWUploadTCSGE_t, MPI_POINTER pFWUploadTCSGE_t; /* Firmware Upload reply */ typedef struct _MSG_FW_UPLOAD_REPLY { - U8 ImageType; - U8 Reserved; - U8 MsgLength; - U8 Function; - U8 Reserved1[3]; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; - U32 ActualImageSize; + U8 ImageType; /* 00h */ + U8 Reserved; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved1[3]; /* 04h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 ActualImageSize; /* 14h */ } MSG_FW_UPLOAD_REPLY, MPI_POINTER PTR_MSG_FW_UPLOAD_REPLY, FWUploadReply_t, MPI_POINTER pFWUploadReply_t; typedef struct _MPI_FW_HEADER { - U32 ArmBranchInstruction0; - U32 Signature0; - U32 Signature1; - U32 Signature2; - U32 ArmBranchInstruction1; - U32 ArmBranchInstruction2; - U32 Reserved; - U32 Checksum; - U16 VendorId; - U16 ProductId; - U16 FwVersion; - U16 Reserved1; - U32 SeqCodeVersion; - U32 ImageSize; - U32 Reserved2; - U32 LoadStartAddress; - U32 IopResetVectorValue; - U32 IopResetRegAddr; - U32 VersionNameWhat; - U8 VersionName[32]; - U32 VendorNameWhat; - U8 VendorName[32]; + U32 ArmBranchInstruction0; /* 00h */ + U32 Signature0; /* 04h */ + U32 Signature1; /* 08h */ + U32 Signature2; /* 0Ch */ + U32 ArmBranchInstruction1; /* 10h */ + U32 ArmBranchInstruction2; /* 14h */ + U32 Reserved; /* 18h */ + U32 Checksum; /* 1Ch */ + U16 VendorId; /* 20h */ + U16 ProductId; /* 22h */ + U16 FwVersion; /* 24h */ + U16 Reserved1; /* 26h */ + U32 SeqCodeVersion; /* 28h */ + U32 ImageSize; /* 2Ch */ + U32 Reserved2; /* 30h */ + U32 LoadStartAddress; /* 34h */ + U32 IopResetVectorValue; /* 38h */ + U32 IopResetRegAddr; /* 3Ch */ + U32 VersionNameWhat; /* 40h */ + U8 VersionName[32]; /* 44h */ + U32 VendorNameWhat; /* 64h */ + U8 VendorName[32]; /* 68h */ } MPI_FW_HEADER, MPI_POINTER PTR_MPI_FW_HEADER, MpiFwHeader_t, MPI_POINTER pMpiFwHeader_t; -#define MPI_FW_HEADER_WHAT_SIGNATURE (0x29232840) +#define MPI_FW_HEADER_WHAT_SIGNATURE (0x29232840) + +/* defines for using the ProductId field */ +#define MPI_FW_HEADER_PID_TYPE_MASK (0xF000) +#define MPI_FW_HEADER_PID_TYPE_SCSI (0x0000) +#define MPI_FW_HEADER_PID_TYPE_FC (0x1000) + +#define MPI_FW_HEADER_PID_FW_VENDOR_MASK (0x0F00) +#define MPI_FW_HEADER_PID_FW_VENDOR_LSI (0x0000) + +#define MPI_FW_HEADER_PID_FAMILY_MASK (0x000F) +#define MPI_FW_HEADER_PID_FAMILY_1030_SCSI (0x0000) +#define MPI_FW_HEADER_PID_FAMILY_909_FC (0x0000) +#define MPI_FW_HEADER_PID_FAMILY_919_FC (0x0001) +#define MPI_FW_HEADER_PID_FAMILY_919X_FC (0x0002) typedef struct _MPI_DATA_HEADER { - U32 Signature; - U16 FunctionNumber; - U16 Length; - U32 Checksum; - U32 LoadStartAddress; + U32 Signature; /* 00h */ + U16 FunctionNumber; /* 04h */ + U16 Length; /* 06h */ + U32 Checksum; /* 08h */ + U32 LoadStartAddress; /* 0Ch */ } MPI_DATA_HEADER, MPI_POINTER PTR_MPI_DATA_HEADER, MpiDataHeader_t, MPI_POINTER pMpiDataHeader_t; -#define MPI_DATA_HEADER_SIGNATURE (0x43504147) +#define MPI_DATA_HEADER_SIGNATURE (0x43504147) #endif diff --git a/drivers/message/fusion/lsi/mpi_lan.h b/drivers/message/fusion/lsi/mpi_lan.h index 86d15dc25996..f5a3bb0bf3d6 100644 --- a/drivers/message/fusion/lsi/mpi_lan.h +++ b/drivers/message/fusion/lsi/mpi_lan.h @@ -6,7 +6,7 @@ * Title: MPI LAN messages and structures * Creation Date: June 30, 2000 * - * MPI Version: 01.01.02 + * MPI Version: 01.01.03 * * Version History * --------------- @@ -26,6 +26,7 @@ * to lan private header file * 11-02-00 01.01.01 Original release for post 1.0 work * 02-20-01 01.01.02 Started using MPI_POINTER. + * 03-27-01 01.01.03 Added structure offset comments. * -------------------------------------------------------------------------- */ @@ -43,32 +44,32 @@ typedef struct _MSG_LAN_SEND_REQUEST { - U16 Reserved; - U8 ChainOffset; - U8 Function; - U16 Reserved2; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - SGE_MPI_UNION SG_List[1]; + U16 Reserved; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved2; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + SGE_MPI_UNION SG_List[1]; /* 0Ch */ } MSG_LAN_SEND_REQUEST, MPI_POINTER PTR_MSG_LAN_SEND_REQUEST, LANSendRequest_t, MPI_POINTER pLANSendRequest_t; typedef struct _MSG_LAN_SEND_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U8 Reserved2; - U8 NumberOfContexts; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 BufferContext; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved2; /* 04h */ + U8 NumberOfContexts; /* 05h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 BufferContext; /* 14h */ } MSG_LAN_SEND_REPLY, MPI_POINTER PTR_MSG_LAN_SEND_REPLY, LANSendReply_t, MPI_POINTER pLANSendReply_t; @@ -77,36 +78,36 @@ typedef struct _MSG_LAN_SEND_REPLY typedef struct _MSG_LAN_RECEIVE_POST_REQUEST { - U16 Reserved; - U8 ChainOffset; - U8 Function; - U16 Reserved2; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U32 BucketCount; - SGE_MPI_UNION SG_List[1]; + U16 Reserved; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved2; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U32 BucketCount; /* 0Ch */ + SGE_MPI_UNION SG_List[1]; /* 10h */ } MSG_LAN_RECEIVE_POST_REQUEST, MPI_POINTER PTR_MSG_LAN_RECEIVE_POST_REQUEST, LANReceivePostRequest_t, MPI_POINTER pLANReceivePostRequest_t; typedef struct _MSG_LAN_RECEIVE_POST_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U8 Reserved2; - U8 NumberOfContexts; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 BucketsRemaining; - U32 PacketOffset; - U32 PacketLength; - U32 BucketContext[1]; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 Reserved2; /* 04h */ + U8 NumberOfContexts; /* 05h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 BucketsRemaining; /* 14h */ + U32 PacketOffset; /* 18h */ + U32 PacketLength; /* 1Ch */ + U32 BucketContext[1]; /* 20h */ } MSG_LAN_RECEIVE_POST_REPLY, MPI_POINTER PTR_MSG_LAN_RECEIVE_POST_REPLY, LANReceivePostReply_t, MPI_POINTER pLANReceivePostReply_t; @@ -115,29 +116,29 @@ typedef struct _MSG_LAN_RECEIVE_POST_REPLY typedef struct _MSG_LAN_RESET_REQUEST { - U16 Reserved; - U8 ChainOffset; - U8 Function; - U16 Reserved2; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; + U16 Reserved; /* 00h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved2; /* 04h */ + U8 PortNumber; /* 05h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ } MSG_LAN_RESET_REQUEST, MPI_POINTER PTR_MSG_LAN_RESET_REQUEST, LANResetRequest_t, MPI_POINTER pLANResetRequest_t; typedef struct _MSG_LAN_RESET_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved2; - U8 PortNumber; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved2; /* 04h */ + U8 PortNumber; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_LAN_RESET_REPLY, MPI_POINTER PTR_MSG_LAN_RESET_REPLY, LANResetReply_t, MPI_POINTER pLANResetReply_t; @@ -200,5 +201,11 @@ typedef struct _MSG_LAN_RESET_REPLY #define MPI_LAN_DEVICE_STATE_OPERATIONAL (0x01) +/****************************************************************************/ +/* LAN Loopback defines */ +/****************************************************************************/ + +#define MPI_LAN_TX_MODES_ENABLE_LOOPBACK_SUPPRESSION (0x01) + #endif diff --git a/drivers/message/fusion/lsi/mpi_targ.h b/drivers/message/fusion/lsi/mpi_targ.h index 8b0d74a2b64c..1f24a957f5c7 100644 --- a/drivers/message/fusion/lsi/mpi_targ.h +++ b/drivers/message/fusion/lsi/mpi_targ.h @@ -6,7 +6,7 @@ * Title: MPI Target mode messages and structures * Creation Date: June 22, 2000 * - * MPI Version: 01.01.03 + * MPI Version: 01.01.04 * * Version History * --------------- @@ -25,6 +25,7 @@ * 02-20-01 01.01.03 Started using MPI_POINTER. * Added structures for MPI_TARGET_SCSI_SPI_CMD_BUFFER and * MPI_TARGET_FCP_CMD_BUFFER. + * 03-27-01 01.01.04 Added structure offset comments. * -------------------------------------------------------------------------- */ @@ -40,9 +41,9 @@ typedef struct _CMD_BUFFER_DESCRIPTOR { - U16 IoIndex; - U16 Reserved; - union + U16 IoIndex; /* 00h */ + U16 Reserved; /* 02h */ + union /* 04h */ { U32 PhysicalAddress32; U64 PhysicalAddress64; @@ -57,16 +58,16 @@ typedef struct _CMD_BUFFER_DESCRIPTOR typedef struct _MSG_TARGET_CMD_BUFFER_POST_REQUEST { - U8 BufferPostFlags; - U8 BufferCount; - U8 ChainOffset; - U8 Function; - U8 BufferLength; - U8 Reserved; - U8 Reserved1; - U8 MsgFlags; - U32 MsgContext; - CMD_BUFFER_DESCRIPTOR Buffer[1]; + U8 BufferPostFlags; /* 00h */ + U8 BufferCount; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U8 BufferLength; /* 04h */ + U8 Reserved; /* 05h */ + U8 Reserved1; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + CMD_BUFFER_DESCRIPTOR Buffer[1]; /* 0Ch */ } MSG_TARGET_CMD_BUFFER_POST_REQUEST, MPI_POINTER PTR_MSG_TARGET_CMD_BUFFER_POST_REQUEST, TargetCmdBufferPostRequest_t, MPI_POINTER pTargetCmdBufferPostRequest_t; @@ -81,36 +82,36 @@ typedef struct _MSG_TARGET_CMD_BUFFER_POST_REQUEST typedef struct _MSG_TARGET_CMD_BUFFER_POST_REPLY { - U8 BufferPostFlags; - U8 BufferCount; - U8 MsgLength; - U8 Function; - U8 BufferLength; - U8 Reserved; - U8 Reserved1; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved2; - U16 IOCStatus; - U32 IOCLogInfo; + U8 BufferPostFlags; /* 00h */ + U8 BufferCount; /* 01h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U8 BufferLength; /* 04h */ + U8 Reserved; /* 05h */ + U8 Reserved1; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved2; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ } MSG_TARGET_CMD_BUFFER_POST_REPLY, MPI_POINTER PTR_MSG_TARGET_CMD_BUFFER_POST_REPLY, TargetCmdBufferPostReply_t, MPI_POINTER pTargetCmdBufferPostReply_t; typedef struct _MSG_PRIORITY_CMD_RECEIVED_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved1; - U8 Reserved2; - U8 MsgFlags; - U32 MsgContext; - U8 PriorityReason; - U8 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 ReplyWord; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U8 PriorityReason; /* 0Ch */ + U8 Reserved3; /* 0Dh */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 ReplyWord; /* 14h */ } MSG_PRIORITY_CMD_RECEIVED_REPLY, MPI_POINTER PTR_MSG_PRIORITY_CMD_RECEIVED_REPLY, PriorityCommandReceivedReply_t, MPI_POINTER pPriorityCommandReceivedReply_t; @@ -121,17 +122,17 @@ typedef struct _MSG_PRIORITY_CMD_RECEIVED_REPLY typedef struct _MSG_TARGET_CMD_BUFFER_POST_ERROR_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved1; - U8 Reserved2; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 ReplyWord; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 ReplyWord; /* 14h */ } MSG_TARGET_CMD_BUFFER_POST_ERROR_REPLY, MPI_POINTER PTR_MSG_TARGET_CMD_BUFFER_POST_ERROR_REPLY, TargetCmdBufferPostErrorReply_t, MPI_POINTER pTargetCmdBufferPostErrorReply_t; @@ -139,10 +140,10 @@ typedef struct _MSG_TARGET_CMD_BUFFER_POST_ERROR_REPLY typedef struct _MPI_TARGET_FCP_CMD_BUFFER { - U8 FcpLun[8]; - U8 FcpCntl[4]; - U8 FcpCdb[16]; - U32 FcpDl; + U8 FcpLun[8]; /* 00h */ + U8 FcpCntl[4]; /* 08h */ + U8 FcpCdb[16]; /* 0Ch */ + U32 FcpDl; /* 1Ch */ } MPI_TARGET_FCP_CMD_BUFFER, MPI_POINTER PTR_MPI_TARGET_FCP_CMD_BUFFER, MpiTargetFcpCmdBuffer, MPI_POINTER pMpiTargetFcpCmdBuffer; @@ -150,17 +151,17 @@ typedef struct _MPI_TARGET_FCP_CMD_BUFFER typedef struct _MPI_TARGET_SCSI_SPI_CMD_BUFFER { /* SPI L_Q information unit */ - U8 L_QType; - U8 Reserved; - U16 Tag; - U8 LogicalUnitNumber[8]; - U32 DataLength; + U8 L_QType; /* 00h */ + U8 Reserved; /* 01h */ + U16 Tag; /* 02h */ + U8 LogicalUnitNumber[8]; /* 04h */ + U32 DataLength; /* 0Ch */ /* SPI command information unit */ - U8 ReservedFirstByteOfCommandIU; - U8 TaskAttribute; - U8 TaskManagementFlags; - U8 AdditionalCDBLength; - U8 CDB[16]; + U8 ReservedFirstByteOfCommandIU; /* 10h */ + U8 TaskAttribute; /* 11h */ + U8 TaskManagementFlags; /* 12h */ + U8 AdditionalCDBLength; /* 13h */ + U8 CDB[16]; /* 14h */ } MPI_TARGET_SCSI_SPI_CMD_BUFFER, MPI_POINTER PTR_MPI_TARGET_SCSI_SPI_CMD_BUFFER, MpiTargetScsiSpiCmdBuffer, MPI_POINTER pMpiTargetScsiSpiCmdBuffer; @@ -172,19 +173,19 @@ typedef struct _MPI_TARGET_SCSI_SPI_CMD_BUFFER typedef struct _MSG_TARGET_ASSIST_REQUEST { - U8 StatusCode; - U8 TargetAssistFlags; - U8 ChainOffset; - U8 Function; - U16 QueueTag; - U8 Reserved; - U8 MsgFlags; - U32 MsgContext; - U32 ReplyWord; - U8 LUN[8]; - U32 RelativeOffset; - U32 DataLength; - SGE_IO_UNION SGL[1]; + U8 StatusCode; /* 00h */ + U8 TargetAssistFlags; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 QueueTag; /* 04h */ + U8 Reserved; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U32 ReplyWord; /* 0Ch */ + U8 LUN[8]; /* 10h */ + U32 RelativeOffset; /* 18h */ + U32 DataLength; /* 1Ch */ + SGE_IO_UNION SGL[1]; /* 20h */ } MSG_TARGET_ASSIST_REQUEST, MPI_POINTER PTR_MSG_TARGET_ASSIST_REQUEST, TargetAssistRequest_t, MPI_POINTER pTargetAssistRequest_t; @@ -196,18 +197,18 @@ typedef struct _MSG_TARGET_ASSIST_REQUEST typedef struct _MSG_TARGET_ERROR_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved1; - U8 Reserved2; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 ReplyWord; - U32 TransferCount; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 ReplyWord; /* 14h */ + U32 TransferCount; /* 18h */ } MSG_TARGET_ERROR_REPLY, MPI_POINTER PTR_MSG_TARGET_ERROR_REPLY, TargetErrorReply_t, MPI_POINTER pTargetErrorReply_t; @@ -218,17 +219,17 @@ typedef struct _MSG_TARGET_ERROR_REPLY typedef struct _MSG_TARGET_STATUS_SEND_REQUEST { - U8 StatusCode; - U8 StatusFlags; - U8 ChainOffset; - U8 Function; - U16 QueueTag; - U8 Reserved; - U8 MsgFlags; - U32 MsgContext; - U32 ReplyWord; - U8 LUN[8]; - SGE_SIMPLE_UNION StatusDataSGE; + U8 StatusCode; /* 00h */ + U8 StatusFlags; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 QueueTag; /* 04h */ + U8 Reserved; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U32 ReplyWord; /* 0Ch */ + U8 LUN[8]; /* 10h */ + SGE_SIMPLE_UNION StatusDataSGE; /* 18h */ } MSG_TARGET_STATUS_SEND_REQUEST, MPI_POINTER PTR_MSG_TARGET_STATUS_SEND_REQUEST, TargetStatusSendRequest_t, MPI_POINTER pTargetStatusSendRequest_t; @@ -242,16 +243,16 @@ typedef struct _MSG_TARGET_STATUS_SEND_REQUEST typedef struct _MSG_TARGET_MODE_ABORT_REQUEST { - U8 AbortType; - U8 Reserved; - U8 ChainOffset; - U8 Function; - U16 Reserved1; - U8 Reserved2; - U8 MsgFlags; - U32 MsgContext; - U32 ReplyWord; - U32 MsgContextToAbort; + U8 AbortType; /* 00h */ + U8 Reserved; /* 01h */ + U8 ChainOffset; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U32 ReplyWord; /* 0Ch */ + U32 MsgContextToAbort; /* 10h */ } MSG_TARGET_MODE_ABORT, MPI_POINTER PTR_MSG_TARGET_MODE_ABORT, TargetModeAbort_t, MPI_POINTER pTargetModeAbort_t; @@ -264,17 +265,17 @@ typedef struct _MSG_TARGET_MODE_ABORT_REQUEST typedef struct _MSG_TARGET_MODE_ABORT_REPLY { - U16 Reserved; - U8 MsgLength; - U8 Function; - U16 Reserved1; - U8 Reserved2; - U8 MsgFlags; - U32 MsgContext; - U16 Reserved3; - U16 IOCStatus; - U32 IOCLogInfo; - U32 AbortCount; + U16 Reserved; /* 00h */ + U8 MsgLength; /* 02h */ + U8 Function; /* 03h */ + U16 Reserved1; /* 04h */ + U8 Reserved2; /* 06h */ + U8 MsgFlags; /* 07h */ + U32 MsgContext; /* 08h */ + U16 Reserved3; /* 0Ch */ + U16 IOCStatus; /* 0Eh */ + U32 IOCLogInfo; /* 10h */ + U32 AbortCount; /* 14h */ } MSG_TARGET_MODE_ABORT_REPLY, MPI_POINTER PTR_MSG_TARGET_MODE_ABORT_REPLY, TargetModeAbortReply_t, MPI_POINTER pTargetModeAbortReply_t; diff --git a/drivers/message/fusion/mptbase.c b/drivers/message/fusion/mptbase.c index 0ada7fe6e632..0e3cd3fb4ee3 100644 --- a/drivers/message/fusion/mptbase.c +++ b/drivers/message/fusion/mptbase.c @@ -42,7 +42,7 @@ * Originally By: Steven J. Ralston * (mailto:Steve.Ralston@lsil.com) * - * $Id: mptbase.c,v 1.47 2001/03/22 10:32:23 sralston Exp $ + * $Id: mptbase.c,v 1.53.4.1 2001/08/24 20:07:05 sralston Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -130,6 +130,8 @@ void *mpt_v_ASCQ_TablePtr = NULL; const char **mpt_ScsiOpcodesPtr = NULL; int mpt_ASCQ_TableSz = 0; +#define WHOINIT_UNKNOWN 0xAA + /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* * Private data... @@ -143,6 +145,8 @@ static MPT_CALLBACK MptCallbacks[MPT_MAX_PROTOCOL_DRIVERS]; static int MptDriverClass[MPT_MAX_PROTOCOL_DRIVERS]; /* Event handler lookup table */ static MPT_EVHANDLER MptEvHandlers[MPT_MAX_PROTOCOL_DRIVERS]; + /* Reset handler lookup table */ +static MPT_RESETHANDLER MptResetHandlers[MPT_MAX_PROTOCOL_DRIVERS]; static int FusionInitCalled = 0; static int mpt_base_index = -1; @@ -154,25 +158,27 @@ static int mpt_base_index = -1; static void mpt_interrupt(int irq, void *bus_id, struct pt_regs *r); static int mpt_base_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply); +static int mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason); static int mpt_adapter_install(struct pci_dev *pdev); static void mpt_detect_929_bound_ports(MPT_ADAPTER *this, struct pci_dev *pdev); -static void mpt_adapter_disable(MPT_ADAPTER *ioc); +static void mpt_adapter_disable(MPT_ADAPTER *ioc, int freeup); static void mpt_adapter_dispose(MPT_ADAPTER *ioc); static void MptDisplayIocCapabilities(MPT_ADAPTER *ioc); +static int MakeIocReady(MPT_ADAPTER *ioc, int force); static u32 GetIocState(MPT_ADAPTER *ioc, int cooked); static int GetIocFacts(MPT_ADAPTER *ioc); -static int GetPortFacts(MPT_ADAPTER *ioc); +static int GetPortFacts(MPT_ADAPTER *ioc, int portnum); static int SendIocInit(MPT_ADAPTER *ioc); static int SendPortEnable(MPT_ADAPTER *ioc, int portnum); -static int mpt_fc9x9_reset(MPT_ADAPTER *ioc); -static int KickStart(MPT_ADAPTER *ioc); +static int mpt_fc9x9_reset(MPT_ADAPTER *ioc, int ignore); +static int KickStart(MPT_ADAPTER *ioc, int ignore); static int SendIocReset(MPT_ADAPTER *ioc, u8 reset_type); static int PrimeIocFifos(MPT_ADAPTER *ioc); -static int HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply); -static int WaitForDoorbellAck(MPT_ADAPTER *ioc); -static int WaitForDoorbellInt(MPT_ADAPTER *ioc); -static int WaitForDoorbellReply(MPT_ADAPTER *ioc); +static int HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply, int maxwait); +static int WaitForDoorbellAck(MPT_ADAPTER *ioc, int howlong); +static int WaitForDoorbellInt(MPT_ADAPTER *ioc, int howlong); +static int WaitForDoorbellReply(MPT_ADAPTER *ioc, int howlong); static int GetLanConfigPages(MPT_ADAPTER *ioc); static int SendEventNotification(MPT_ADAPTER *ioc, u8 EvSwitch); static int SendEventAck(MPT_ADAPTER *ioc, EventNotificationReply_t *evnp); @@ -192,6 +198,7 @@ static void mpt_sp_log_info(MPT_ADAPTER *ioc, u32 log_info); static struct proc_dir_entry *procmpt_root_dir = NULL; int fusion_init(void); +static void fusion_exit(void); /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* 20000207 -sralston @@ -586,6 +593,45 @@ mpt_event_deregister(int cb_idx) /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /** + * mpt_reset_register - Register protocol-specific IOC reset handler. + * @cb_idx: previously registered (via mpt_register) callback handle + * @reset_func: reset function + * + * This routine can be called by one or more protocol-specific drivers + * if/when they choose to be notified of IOC resets. + * + * Returns 0 for success. + */ +int +mpt_reset_register(int cb_idx, MPT_RESETHANDLER reset_func) +{ + if (cb_idx < 1 || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS) + return -1; + + MptResetHandlers[cb_idx] = reset_func; + return 0; +} + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/** + * mpt_reset_deregister - Deregister protocol-specific IOC reset handler. + * @cb_idx: previously registered callback handle + * + * Each protocol-specific driver should call this routine + * when it does not (or can no longer) handle IOC reset handling, + * or when it's module is unloaded. + */ +void +mpt_reset_deregister(int cb_idx) +{ + if (cb_idx < 1 || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS) + return; + + MptResetHandlers[cb_idx] = NULL; +} + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/** * mpt_get_msg_frame - Obtain a MPT request frame from the pool (of 1024) * allocated per MPT adapter. * @handle: Handle of registered MPT protocol driver @@ -723,13 +769,29 @@ mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 *req) iocp = mpt_adapters[iocid]; if (iocp != NULL) { - u8 *req_as_bytes; - int i; + u8 *req_as_bytes; + u32 ioc_raw_state; + int i; + + /* YIKES! We already know something is amiss. + * Do upfront check on IOC state. + */ + ioc_raw_state = GetIocState(iocp, 0); + if ((ioc_raw_state & MPI_DOORBELL_ACTIVE) || + ((ioc_raw_state & MPI_IOC_STATE_MASK) != MPI_IOC_STATE_OPERATIONAL)) { + printk(KERN_WARNING MYNAM ": %s: Bad IOC state (%08x) WARNING!\n", + iocp->name, ioc_raw_state); + if ((r = mpt_do_ioc_recovery(iocp, MPT_HOSTEVENT_IOC_RECOVER)) != 0) { + printk(KERN_WARNING MYNAM ": WARNING - (%d) Cannot recover %s\n", + r, iocp->name); + return r; + } + } /* - * Emulate what mpt_put_msg_frame() does /wrt to sanity - * setting cb_idx/req_idx. But ONLY if this request - * is in proper (pre-alloc'd) request buffer range... + * Emulate what mpt_put_msg_frame() does /wrt to sanity + * setting cb_idx/req_idx. But ONLY if this request + * is in proper (pre-alloc'd) request buffer range... */ i = MFPTR_2_MPT_INDEX(iocp,(MPT_FRAME_HDR*)req); if (reqBytes >= 12 && i >= 0 && i < iocp->req_depth) { @@ -738,17 +800,15 @@ mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 *req) mf->u.frame.hwhdr.msgctxu.fld.cb_idx = handle; } - /* Make sure there are no doorbells */ + /* Make sure there are no doorbells */ CHIPREG_WRITE32(&iocp->chip->IntStatus, 0); CHIPREG_WRITE32(&iocp->chip->Doorbell, ((MPI_FUNCTION_HANDSHAKE<<MPI_DOORBELL_FUNCTION_SHIFT) | ((reqBytes/4)<<MPI_DOORBELL_ADD_DWORDS_SHIFT))); - /* Wait for IOC doorbell int */ - if ((i = WaitForDoorbellInt(iocp)) < 0) { - /* FIXME! Recovery action(s)? */ - /*i = unresponsive_ioc(i);*/ + /* Wait for IOC doorbell int */ + if ((i = WaitForDoorbellInt(iocp, 2)) < 0) { return i; } @@ -757,10 +817,11 @@ mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 *req) CHIPREG_WRITE32(&iocp->chip->IntStatus, 0); - if ((r = WaitForDoorbellAck(iocp)) < 0) + if ((r = WaitForDoorbellAck(iocp, 1)) < 0) { return -2; + } - /* Send request via doorbell handshake */ + /* Send request via doorbell handshake */ req_as_bytes = (u8 *) req; for (i = 0; i < reqBytes/4; i++) { u32 word; @@ -770,15 +831,19 @@ mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 *req) (req_as_bytes[(i*4) + 2] << 16) | (req_as_bytes[(i*4) + 3] << 24)); CHIPREG_WRITE32(&iocp->chip->Doorbell, word); - if ((r = WaitForDoorbellAck(iocp)) < 0) { + if ((r = WaitForDoorbellAck(iocp, 1)) < 0) { r = -3; break; } } - /* Make sure there are no doorbells */ - CHIPREG_WRITE32(&iocp->chip->IntStatus, 0); + if ((r = WaitForDoorbellInt(iocp, 2)) >= 0) + r = 0; + else + r = -4; + /* Make sure there are no doorbells */ + CHIPREG_WRITE32(&iocp->chip->IntStatus, 0); } return r; @@ -849,9 +914,8 @@ mpt_pci_scan(void) if ((pdev->device != MPI_MANUFACTPAGE_DEVICEID_FC909) && (pdev->device != MPI_MANUFACTPAGE_DEVICEID_FC929) && -#if 0 - /* FIXME! FC919 */ (pdev->device != MPI_MANUFACTPAGE_DEVICEID_FC919) && +#if 0 /* FIXME! C103x family */ (pdev->device != MPI_MANUFACTPAGE_DEVID_53C1030) && (pdev->device != MPI_MANUFACTPAGE_DEVID_53C1030_ZC) && @@ -897,8 +961,10 @@ mpt_pci_scan(void) printk(KERN_INFO MYNAM ": %d MPT adapter%s found, %d installed.\n", found, (found==1) ? "" : "s", count); - if (count == 0) + if (!found || !count) { + fusion_exit(); return -ENODEV; + } #ifdef CONFIG_PROC_FS if (procmpt_create() != 0) @@ -962,12 +1028,9 @@ mpt_adapter_install(struct pci_dev *pdev) unsigned long port; u32 msize; u32 psize; - u32 ioc_state; int i; int r = -ENODEV; - int cntdn; int len; - int statefault = 0; ioc = kmalloc(sizeof(MPT_ADAPTER), GFP_KERNEL); if (ioc == NULL) { @@ -980,7 +1043,7 @@ mpt_adapter_install(struct pci_dev *pdev) ioc->pcidev = pdev; - /* Find lookup slot. GRRRR... */ + /* Find lookup slot. */ for (i=0; i < MPT_MAX_ADAPTERS; i++) { if (mpt_adapters[i] == NULL) { ioc->id = i; /* Assign adapter unique id (lookup) */ @@ -997,11 +1060,11 @@ mpt_adapter_install(struct pci_dev *pdev) port = psize = 0; for (i=0; i < DEVICE_COUNT_RESOURCE; i++) { if (pdev->PCI_BASEADDR_FLAGS(i) & PCI_BASE_ADDRESS_SPACE_IO) { - /* Get I/O space! */ + /* Get I/O space! */ port = pdev->PCI_BASEADDR_START(i); psize = PCI_BASEADDR_SIZE(pdev,i); } else { - /* Get memmap */ + /* Get memmap */ mem_phys = pdev->PCI_BASEADDR_START(i); msize = PCI_BASEADDR_SIZE(pdev,i); break; @@ -1021,7 +1084,7 @@ mpt_adapter_install(struct pci_dev *pdev) mem = NULL; if (! PortIo) { - /* Get logical ptr for PciMem0 space */ + /* Get logical ptr for PciMem0 space */ /*mem = ioremap(mem_phys, msize);*/ mem = ioremap(mem_phys, 0x100); if (mem == NULL) { @@ -1051,11 +1114,11 @@ mpt_adapter_install(struct pci_dev *pdev) ioc->chip_type = FC929; ioc->prod_name = "LSIFC929"; } -#if 0 else if (pdev->device == MPI_MANUFACTPAGE_DEVICEID_FC919) { - ioc->chip_type = C1030; + ioc->chip_type = FC919; ioc->prod_name = "LSIFC919"; } +#if 0 else if (pdev->device == MPI_MANUFACTPAGE_DEVICEID_53C1030) { ioc->chip_type = C1030; ioc->prod_name = "LSI53C1030"; @@ -1070,10 +1133,10 @@ mpt_adapter_install(struct pci_dev *pdev) Q_INIT(&ioc->FreeQ, MPT_FRAME_HDR); spin_lock_init(&ioc->FreeQlock); - /* Disable all! */ + /* Disable all! */ CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF); - CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); ioc->active = 0; + CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); ioc->pci_irq = -1; if (pdev->irq) { @@ -1094,7 +1157,7 @@ mpt_adapter_install(struct pci_dev *pdev) dprintk((KERN_INFO MYNAM ": %s installed at interrupt %d\n", ioc->name, pdev->irq)); } - /* tack onto tail of our MPT adapter list */ + /* tack onto tail of our MPT adapter list */ Q_ADD_TAIL(&MptAdapters, ioc, MPT_ADAPTER); /* Set lookup ptr. */ @@ -1106,115 +1169,168 @@ mpt_adapter_install(struct pci_dev *pdev) if (ioc->chip_type == FC929) mpt_detect_929_bound_ports(ioc, pdev); - /* Get current [raw] IOC state */ - ioc_state = GetIocState(ioc, 0); - dhsprintk((KERN_INFO MYNAM ": %s initial [raw] state=%08x\n", ioc->name, ioc_state)); + if ((r = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_BRINGUP)) != 0) { + printk(KERN_WARNING MYNAM ": WARNING - %s did not initialize properly! (%d)\n", + ioc->name, r); + } - /* - * Check to see if IOC got left/stuck in doorbell handshake - * grip of death. If so, hard reset the IOC. - */ - if (ioc_state & MPI_DOORBELL_ACTIVE) { - statefault = 1; - printk(KERN_WARNING MYNAM ": %s: Uh-oh, unexpected doorbell active!\n", + return r; +} + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/** + * mpt_do_ioc_recovery - Initialize or recover MPT adapter. + * @ioc: Pointer to MPT adapter structure + * @reason: Event word / reason + * + * This routine performs all the steps necessary to bring the IOC + * to a OPERATIONAL state. + * + * This routine also pre-fetches the LAN MAC address of a Fibre Channel + * MPT adapter. + * + * Returns 0 for success. + */ +static int +mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason) +{ + int hard_reset_done = 0; + int alt_ioc_ready = 0; + int hard; + int r; + int i; + int handlers; + + printk(KERN_INFO MYNAM ": Initiating %s %s\n", + ioc->name, reason==MPT_HOSTEVENT_IOC_BRINGUP ? "bringup" : "recovery"); + + /* Disable reply interrupts */ + CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF); + ioc->active = 0; + /* NOTE: Access to IOC's request FreeQ is now blocked! */ + +// FIXME? Cleanup all IOC requests here! (or below?) +// But watch out for event associated request? + + hard = HardReset; + if (ioc->alt_ioc && (reason == MPT_HOSTEVENT_IOC_BRINGUP)) + hard = 0; + + if ((hard_reset_done = MakeIocReady(ioc, hard)) < 0) { + printk(KERN_WARNING MYNAM ": %s NOT READY WARNING!\n", ioc->name); + return -1; } - /* - * Check to see if IOC is in FAULT state. - * If so, hard reset the IOC. - */ - if ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_FAULT) { - statefault = 2; - printk(KERN_WARNING MYNAM ": %s: Uh-oh, IOC is in FAULT state!!!\n", - ioc->name); - printk(KERN_WARNING " FAULT code = %04xh\n", - ioc_state & MPI_DOORBELL_DATA_MASK); +// NEW! +#if 0 // Kiss-of-death!?! + if (ioc->alt_ioc) { +// Grrr... Hold off any alt-IOC interrupts (and events) while +// handshaking to <this> IOC, needed because? + /* Disable alt-IOC's reply interrupts for a bit ... */ + alt_ioc_intmask = CHIPREG_READ32(&ioc->alt_ioc->chip->IntMask); + CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, 0xFFFFFFFF); + ioc->alt_ioc->active = 0; + /* NOTE: Access to alt-IOC's request FreeQ is now blocked! */ } +#endif - if (HardReset || statefault) { - if ((r = KickStart(ioc)) != 0) { - r = -ENODEV; - goto ioc_up_fail; - } + if (hard_reset_done && ioc->alt_ioc) { + if ((r = MakeIocReady(ioc->alt_ioc, 0)) == 0) + alt_ioc_ready = 1; + else + printk(KERN_WARNING MYNAM ": alt-%s: (%d) Not ready WARNING!\n", + ioc->alt_ioc->name, r); + } + + if (reason == MPT_HOSTEVENT_IOC_BRINGUP) { + /* Get IOC facts! */ + if ((r = GetIocFacts(ioc)) != 0) + return -2; + MptDisplayIocCapabilities(ioc); } /* - * Loop here waiting for IOC to come READY. + * Call each currently registered protocol IOC reset handler + * with pre-reset indication. + * NOTE: If we're doing _IOC_BRINGUP, there can be no + * MptResetHandlers[] registered yet. */ - i = 0; - cntdn = HZ * 10; - while ((ioc_state = GetIocState(ioc, 1)) != MPI_IOC_STATE_READY) { - if (ioc_state == MPI_IOC_STATE_OPERATIONAL) { - /* - * BIOS or previous driver load left IOC in OP state. - * Reset messaging FIFOs. - */ - dprintk((KERN_WARNING MYNAM ": %s: Sending IOC msg unit reset!\n", ioc->name)); - if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET)) != 0) { - printk(KERN_ERR MYNAM ": %s: ERROR - IOC msg unit reset failed!\n", ioc->name); - r = -ENODEV; - goto ioc_up_fail; - } - } else if (ioc_state == MPI_IOC_STATE_RESET) { - /* - * Something is wrong. Try to get IOC back - * to a known state. - */ - dprintk((KERN_WARNING MYNAM ": %s: Sending IO unit reset!\n", ioc->name)); - if ((r = SendIocReset(ioc, MPI_FUNCTION_IO_UNIT_RESET)) != 0) { - printk(KERN_ERR MYNAM ": %s: ERROR - IO unit reset failed!\n", ioc->name); - r = -ENODEV; - goto ioc_up_fail; + if (hard_reset_done) { + r = handlers = 0; + for (i=MPT_MAX_PROTOCOL_DRIVERS-1; i; i--) { + if (MptResetHandlers[i]) { + dprintk((KERN_INFO MYNAM ": %s: Calling IOC pre_reset handler #%d\n", + ioc->name, i)); + r += (*(MptResetHandlers[i]))(ioc, MPT_IOC_PRE_RESET); + handlers++; + + if (alt_ioc_ready) { + dprintk((KERN_INFO MYNAM ": %s: Calling alt-IOC pre_reset handler #%d\n", + ioc->alt_ioc->name, i)); + r += (*(MptResetHandlers[i]))(ioc->alt_ioc, MPT_IOC_PRE_RESET); + handlers++; + } } } + /* FIXME? Examine results here? */ + } - i++; cntdn--; - if (!cntdn) { - printk(KERN_ERR MYNAM ": %s: ERROR - Wait IOC_READY state timeout(%d)!\n", - ioc->name, (i+5)/HZ); - r = -ETIME; - goto ioc_up_fail; - } + // May need to check/upload firmware & data here! - current->state = TASK_INTERRUPTIBLE; - schedule_timeout(1); + if ((r = SendIocInit(ioc)) != 0) + return -3; +// NEW! + if (alt_ioc_ready) { + if ((r = SendIocInit(ioc->alt_ioc)) != 0) { + alt_ioc_ready = 0; + printk(KERN_WARNING MYNAM ": alt-%s: (%d) init failure WARNING!\n", + ioc->alt_ioc->name, r); + } } - if (statefault) { - printk(KERN_WARNING MYNAM ": %s: Whew! Recovered from %s\n", - ioc->name, statefault==1 ? "stuck handshake" : "IOC FAULT"); + /* + * Call each currently registered protocol IOC reset handler + * with post-reset indication. + * NOTE: If we're doing _IOC_BRINGUP, there can be no + * MptResetHandlers[] registered yet. + */ + if (hard_reset_done) { + r = handlers = 0; + for (i=MPT_MAX_PROTOCOL_DRIVERS-1; i; i--) { + if (MptResetHandlers[i]) { + dprintk((KERN_INFO MYNAM ": %s: Calling IOC post_reset handler #%d\n", + ioc->name, i)); + r += (*(MptResetHandlers[i]))(ioc, MPT_IOC_POST_RESET); + handlers++; + + if (alt_ioc_ready) { + dprintk((KERN_INFO MYNAM ": %s: Calling alt-IOC post_reset handler #%d\n", + ioc->alt_ioc->name, i)); + r += (*(MptResetHandlers[i]))(ioc->alt_ioc, MPT_IOC_POST_RESET); + handlers++; + } + } + } + /* FIXME? Examine results here? */ } - /* Enable! (reply interrupt) */ - CHIPREG_WRITE32(&ioc->chip->IntMask, ~(MPI_HIM_RIM)); - ioc->active = 1; - - /* Get IOC facts! (first time, ioc->facts0 and ioc->pfacts0) */ - if ((r = GetIocFacts(ioc)) != 0) - goto ioc_up_fail; - - /* Does IocFacts.EventState need any looking at / attention here? */ - - if ((r = SendIocInit(ioc)) != 0) - goto ioc_up_fail; - /* - * Prime reply & request queues! - * (mucho alloc's) + * Prime reply & request queues! + * (mucho alloc's) */ if ((r = PrimeIocFifos(ioc)) != 0) - goto ioc_up_fail; - - /* Get IOC facts again! (2nd time, ioc->factsN and ioc->pfactsN) */ - if ((r = GetIocFacts(ioc)) != 0) - goto ioc_up_fail; - - /* Does IocFacts.EventState need any looking at / attention here? */ + return -4; +// NEW! + if (alt_ioc_ready && ((r = PrimeIocFifos(ioc->alt_ioc)) != 0)) { + printk(KERN_WARNING MYNAM ": alt-%s: (%d) FIFO mgmt alloc WARNING!\n", + ioc->alt_ioc->name, r); + } - MptDisplayIocCapabilities(ioc); +// FIXME! Cleanup all IOC (and alt-IOC?) requests here! - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { + if ((ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) && + (ioc->lan_cnfg_page0.Header.PageLength == 0)) { /* * Pre-fetch the ports LAN MAC address! * (LANPage1_t stuff) @@ -1229,19 +1345,34 @@ mpt_adapter_install(struct pci_dev *pdev) #endif } + /* Enable! (reply interrupt) */ + CHIPREG_WRITE32(&ioc->chip->IntMask, ~(MPI_HIM_RIM)); + ioc->active = 1; + +// NEW! +#if 0 // Kiss-of-death!?! + if (alt_ioc_ready && (r==0)) { + /* (re)Enable alt-IOC! (reply interrupt) */ + dprintk((KERN_INFO MYNAM ": alt-%s reply irq re-enabled\n", + ioc->alt_ioc->name)); + CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, ~(MPI_HIM_RIM)); + ioc->alt_ioc->active = 1; + } +#endif + /* NEW! 20010120 -sralston * Enable MPT base driver management of EventNotification * and EventAck handling. */ - (void) SendEventNotification(ioc, 1); /* 1=Enable EventNotification */ + if (!ioc->facts.EventState) + (void) SendEventNotification(ioc, 1); /* 1=Enable EventNotification */ +// NEW! +// FIXME!?! +// if (ioc->alt_ioc && alt_ioc_ready && !ioc->alt_ioc->facts.EventState) { +// (void) SendEventNotification(ioc->alt_ioc, 1); /* 1=Enable EventNotification */ +// } return 0; - -ioc_up_fail: - //Q_DEL_ITEM(ioc); - //mpt_adapter_dispose(ioc); - mpt_adapter_disable(ioc); - return r; } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ @@ -1297,20 +1428,25 @@ mpt_detect_929_bound_ports(MPT_ADAPTER *ioc, struct pci_dev *pdev) /* * mpt_adapter_disable - Disable misbehaving MPT adapter. * @this: Pointer to MPT adapter structure + * @free: Free up alloc'd reply, request, etc. */ static void -mpt_adapter_disable(MPT_ADAPTER *this) +mpt_adapter_disable(MPT_ADAPTER *this, int freeup) { if (this != NULL) { int sz; + /* Disable the FW */ + if (SendIocReset(this, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET) != 0) + (void) KickStart(this, 1); + /* Disable adapter interrupts! */ CHIPREG_WRITE32(&this->chip->IntMask, 0xFFFFFFFF); + this->active = 0; /* Clear any lingering interrupt */ CHIPREG_WRITE32(&this->chip->IntStatus, 0); - this->active = 0; - if (this->reply_alloc != NULL) { + if (freeup && this->reply_alloc != NULL) { sz = (this->reply_sz * this->reply_depth) + 128; pci_free_consistent(this->pcidev, sz, this->reply_alloc, this->reply_alloc_dma); @@ -1319,7 +1455,7 @@ mpt_adapter_disable(MPT_ADAPTER *this) this->alloc_total -= sz; } - if (this->req_alloc != NULL) { + if (freeup && this->req_alloc != NULL) { sz = (this->req_sz * this->req_depth) + 128; /* * Rounding UP to nearest 4-kB boundary here... @@ -1332,7 +1468,7 @@ mpt_adapter_disable(MPT_ADAPTER *this) this->alloc_total -= sz; } - if (this->sense_buf_pool != NULL) { + if (freeup && this->sense_buf_pool != NULL) { sz = (this->req_depth * 256); pci_free_consistent(this->pcidev, sz, this->sense_buf_pool, this->sense_buf_pool_dma); @@ -1359,7 +1495,7 @@ mpt_adapter_dispose(MPT_ADAPTER *this) sz_first = this->alloc_total; - mpt_adapter_disable(this); + mpt_adapter_disable(this, 1); if (this->pci_irq != -1) { free_irq(this->pci_irq, this); @@ -1401,17 +1537,17 @@ MptDisplayIocCapabilities(MPT_ADAPTER *ioc) printk("%s: ", ioc->prod_name+3); printk("Capabilities={"); - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR) { + if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR) { printk("Initiator"); i++; } - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) { + if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) { printk("%sTarget", i ? "," : ""); i++; } - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { + if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { printk("%sLAN", i ? "," : ""); i++; } @@ -1420,7 +1556,7 @@ MptDisplayIocCapabilities(MPT_ADAPTER *ioc) /* * This would probably evoke more questions than it's worth */ - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) { + if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) { printk("%sLogBusAddr", i ? "," : ""); i++; } @@ -1431,6 +1567,113 @@ MptDisplayIocCapabilities(MPT_ADAPTER *ioc) /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* + * MakeIocReady - Get IOC to a READY state, using KickStart if needed. + * @ioc: Pointer to MPT_ADAPTER structure + * @kick: Force hard KickStart of IOC + * + * Returns 0 for already-READY, 1 for hard reset success, + * else negative for failure. + */ +static int +MakeIocReady(MPT_ADAPTER *ioc, int force) +{ + u32 ioc_state; + int statefault = 0; + int cntdn; + int hard_reset_done = 0; + int r; + int i; + + /* Get current [raw] IOC state */ + ioc_state = GetIocState(ioc, 0); + dhsprintk((KERN_INFO MYNAM "::MakeIocReady, %s [raw] state=%08x\n", ioc->name, ioc_state)); + + /* + * Check to see if IOC got left/stuck in doorbell handshake + * grip of death. If so, hard reset the IOC. + */ + if (ioc_state & MPI_DOORBELL_ACTIVE) { + statefault = 1; + printk(KERN_WARNING MYNAM ": %s: Uh-oh, unexpected doorbell active!\n", + ioc->name); + } + + /* Is it already READY? */ + if (!statefault && (ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_READY) + return 0; + + /* + * Check to see if IOC is in FAULT state. + */ + if ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_FAULT) { + statefault = 2; + printk(KERN_WARNING MYNAM ": %s: Uh-oh, IOC is in FAULT state!!!\n", + ioc->name); + printk(KERN_WARNING " FAULT code = %04xh\n", + ioc_state & MPI_DOORBELL_DATA_MASK); + } + + /* + * Hmmm... Did it get left operational? + */ + if ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_OPERATIONAL) { + statefault = 3; + dprintk((KERN_WARNING MYNAM ": %s: Hmmm... IOC operational unexpected\n", + ioc->name)); + } + + hard_reset_done = KickStart(ioc, statefault||force); + if (hard_reset_done < 0) + return -1; + + /* + * Loop here waiting for IOC to come READY. + */ + i = 0; + cntdn = HZ * 15; + while ((ioc_state = GetIocState(ioc, 1)) != MPI_IOC_STATE_READY) { + if (ioc_state == MPI_IOC_STATE_OPERATIONAL) { + /* + * BIOS or previous driver load left IOC in OP state. + * Reset messaging FIFOs. + */ + if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET)) != 0) { + printk(KERN_ERR MYNAM ": %s: ERROR - IOC msg unit reset failed!\n", ioc->name); + return -2; + } + } else if (ioc_state == MPI_IOC_STATE_RESET) { + /* + * Something is wrong. Try to get IOC back + * to a known state. + */ + if ((r = SendIocReset(ioc, MPI_FUNCTION_IO_UNIT_RESET)) != 0) { + printk(KERN_ERR MYNAM ": %s: ERROR - IO unit reset failed!\n", ioc->name); + return -3; + } + } + + i++; cntdn--; + if (!cntdn) { + printk(KERN_ERR MYNAM ": %s: ERROR - Wait IOC_READY state timeout(%d)!\n", + ioc->name, (i+5)/HZ); + return -ETIME; + } + + current->state = TASK_INTERRUPTIBLE; + schedule_timeout(1); + } + + if (statefault < 3) { + printk(KERN_WARNING MYNAM ": %s: Whew! Recovered from %s\n", + ioc->name, + statefault==1 ? "stuck handshake" : "IOC FAULT"); + } + + return hard_reset_done; +} + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/* * GetIocState - Get the current state of a MPT adapter. * @ioc: Pointer to MPT_ADAPTER structure * @cooked: Request raw or cooked IOC state @@ -1471,7 +1714,7 @@ GetIocFacts(MPT_ADAPTER *ioc) int reply_sz; u32 status; - /* IOC *must* NOT be in RESET state! */ + /* IOC *must* NOT be in RESET state! */ if (ioc->last_state == MPI_IOC_STATE_RESET) { printk(KERN_ERR MYNAM ": ERROR - Can't get IOCFacts, %s NOT READY! (%08x)\n", ioc->name, @@ -1479,44 +1722,45 @@ GetIocFacts(MPT_ADAPTER *ioc) return -44; } - facts = &ioc->facts0; - /* Nth (2,3,...) time thru? (been here, done that?) */ - if (ioc->facts0.Function == MPI_FUNCTION_IOC_FACTS) { - facts = &ioc->factsN; - } + facts = &ioc->facts; - /* Destination (reply area)... */ + /* Destination (reply area)... */ reply_sz = sizeof(*facts); memset(facts, 0, reply_sz); - /* Request area (get_facts on the stack right now!) */ + /* Request area (get_facts on the stack right now!) */ req_sz = sizeof(get_facts); memset(&get_facts, 0, req_sz); get_facts.Function = MPI_FUNCTION_IOC_FACTS; - /* Assert: All other get_facts fields are zero! */ + /* Assert: All other get_facts fields are zero! */ - dprintk((KERN_INFO MYNAM ": %s: Sending IocFacts%s request\n", - ioc->name, facts == &ioc->facts0 ? "0" : "N" )); + dprintk((KERN_INFO MYNAM ": %s: Sending get IocFacts request\n", ioc->name)); /* No non-zero fields in the get_facts request are greater than * 1 byte in size, so we can just fire it off as is. */ r = HandShakeReqAndReply(ioc, req_sz, (u32*)&get_facts, - reply_sz, (u16*)facts); + reply_sz, (u16*)facts, 3); if (r != 0) return r; /* - * Now byte swap the necessary fields before any further - * inspection of reply contents. + * Now byte swap (GRRR) the necessary fields before any further + * inspection of reply contents. * - * But need to do some sanity checks on MsgLength (byte) field - * to make sure we don't zero IOC's req_sz! + * But need to do some sanity checks on MsgLength (byte) field + * to make sure we don't zero IOC's req_sz! */ /* Did we get a valid reply? */ if (facts->MsgLength > offsetof(IOCFactsReply_t, RequestFrameSize)/sizeof(u32)) { + /* + * If not been here, done that, save off first WhoInit value + */ + if (ioc->FirstWhoInit == WHOINIT_UNKNOWN) + ioc->FirstWhoInit = facts->WhoInit; + facts->MsgVersion = le16_to_cpu(facts->MsgVersion); facts->MsgContext = le32_to_cpu(facts->MsgContext); facts->IOCStatus = le16_to_cpu(facts->IOCStatus); @@ -1537,9 +1781,9 @@ GetIocFacts(MPT_ADAPTER *ioc) le16_to_cpu(facts->CurReplyFrameSize); /* - * Handle NEW (!) IOCFactsReply fields in MPI-1.01.xx - * Older MPI-1.00.xx struct had 13 dwords, and enlarged - * to 14 in MPI-1.01.0x. + * Handle NEW (!) IOCFactsReply fields in MPI-1.01.xx + * Older MPI-1.00.xx struct had 13 dwords, and enlarged + * to 14 in MPI-1.01.0x. */ if (facts->MsgLength >= sizeof(IOCFactsReply_t)/sizeof(u32) && facts->MsgVersion > 0x0100) { facts->FWImageSize = le32_to_cpu(facts->FWImageSize); @@ -1548,7 +1792,7 @@ GetIocFacts(MPT_ADAPTER *ioc) if (facts->RequestFrameSize) { /* - * Set values for this IOC's REQUEST queue size & depth... + * Set values for this IOC's REQUEST queue size & depth... */ ioc->req_sz = MIN(MPT_REQ_SIZE, facts->RequestFrameSize * 4); @@ -1582,8 +1826,8 @@ GetIocFacts(MPT_ADAPTER *ioc) dprintk((KERN_INFO MYNAM ": %s: req_sz =%3d, req_depth =%4d\n", ioc->name, ioc->req_sz, ioc->req_depth)); - /* Get port facts! */ - if ( (r = GetPortFacts(ioc)) != 0 ) + /* Get port facts! */ + if ( (r = GetPortFacts(ioc, 0)) != 0 ) return r; } else { printk(KERN_ERR MYNAM ": %s: ERROR - Invalid IOC facts reply!\n", @@ -1598,11 +1842,12 @@ GetIocFacts(MPT_ADAPTER *ioc) /* * GetPortFacts - Send PortFacts request to MPT adapter. * @ioc: Pointer to MPT_ADAPTER structure + * @portnum: Port number * * Returns 0 for success, non-zero for failure. */ static int -GetPortFacts(MPT_ADAPTER *ioc) +GetPortFacts(MPT_ADAPTER *ioc, int portnum) { PortFacts_t get_pfacts; PortFactsReply_t *pfacts; @@ -1610,7 +1855,7 @@ GetPortFacts(MPT_ADAPTER *ioc) int req_sz; int reply_sz; - /* IOC *must* NOT be in RESET state! */ + /* IOC *must* NOT be in RESET state! */ if (ioc->last_state == MPI_IOC_STATE_RESET) { printk(KERN_ERR MYNAM ": ERROR - Can't get PortFacts, %s NOT READY! (%08x)\n", ioc->name, @@ -1618,31 +1863,28 @@ GetPortFacts(MPT_ADAPTER *ioc) return -4; } - pfacts = &ioc->pfacts0; - /* Nth (2,3,...) time thru? (been here, done that?) */ - if (ioc->pfacts0.Function == MPI_FUNCTION_PORT_FACTS) { - pfacts = &ioc->pfactsN; - } + pfacts = &ioc->pfacts[portnum]; - /* Destination (reply area)... */ + /* Destination (reply area)... */ reply_sz = sizeof(*pfacts); memset(pfacts, 0, reply_sz); - /* Request area (get_pfacts on the stack right now!) */ + /* Request area (get_pfacts on the stack right now!) */ req_sz = sizeof(get_pfacts); memset(&get_pfacts, 0, req_sz); get_pfacts.Function = MPI_FUNCTION_PORT_FACTS; - /* Assert: All other get_pfacts fields are zero! */ + get_pfacts.PortNumber = portnum; + /* Assert: All other get_pfacts fields are zero! */ - dprintk((KERN_INFO MYNAM ": %s: Sending PortFacts%s request\n", - ioc->name, pfacts == &ioc->pfacts0 ? "0" : "N" )); + dprintk((KERN_INFO MYNAM ": %s: Sending get PortFacts(%d) request\n", + ioc->name, portnum)); /* No non-zero fields in the get_pfacts request are greater than * 1 byte in size, so we can just fire it off as is. */ i = HandShakeReqAndReply(ioc, req_sz, (u32*)&get_pfacts, - reply_sz, (u16*)pfacts); + reply_sz, (u16*)pfacts, 3); if (i != 0) return i; @@ -1702,7 +1944,7 @@ SendIocInit(MPT_ADAPTER *ioc) dprintk((KERN_INFO MYNAM ": %s: Sending IOCInit (req @ %p)\n", ioc->name, &ioc_init)); r = HandShakeReqAndReply(ioc, sizeof(IOCInit_t), (u32*)&ioc_init, - sizeof(MPIDefaultReply_t), (u16*)&init_reply); + sizeof(MPIDefaultReply_t), (u16*)&init_reply, 10); if (r != 0) return r; @@ -1775,7 +2017,7 @@ SendPortEnable(MPT_ADAPTER *ioc, int portnum) ioc->name, portnum, &port_enable)); i = HandShakeReqAndReply(ioc, req_sz, (u32*)&port_enable, - reply_sz, (u16*)&reply_buf); + reply_sz, (u16*)&reply_buf, 65); if (i != 0) return i; @@ -1790,24 +2032,28 @@ SendPortEnable(MPT_ADAPTER *ioc, int portnum) /* * KickStart - Perform hard reset of MPT adapter. * @ioc: Pointer to MPT_ADAPTER structure + * @force: Force hard reset * * This routine places MPT adapter in diagnostic mode via the * WriteSequence register, and then performs a hard reset of adapter * via the Diagnostic register. * - * Returns 0 for success, non-zero for failure. + * Returns 0 for soft reset success, 1 for hard reset success, + * else a negative value for failure. */ static int -KickStart(MPT_ADAPTER *ioc) +KickStart(MPT_ADAPTER *ioc, int force) { - int r; + int hard_reset_done = 0; u32 ioc_state; int cnt = 0; dprintk((KERN_WARNING MYNAM ": KickStarting %s!\n", ioc->name)); - if (ioc->chip_type == FC909) { - r = mpt_fc9x9_reset(ioc); + hard_reset_done = mpt_fc9x9_reset(ioc, force); +#if 0 + if (ioc->chip_type == FC909 || ioc->chip-type == FC919) { + hard_reset_done = mpt_fc9x9_reset(ioc, force); } else if (ioc->chip_type == FC929) { unsigned long delta; @@ -1815,15 +2061,12 @@ KickStart(MPT_ADAPTER *ioc) dprintk((KERN_INFO MYNAM ": %s: 929 KickStart, last=%ld, delta = %ld\n", ioc->name, ioc->last_kickstart, delta)); if ((ioc->sod_reset == 0) || (delta >= 10*HZ)) - r = mpt_fc9x9_reset(ioc); + hard_reset_done = mpt_fc9x9_reset(ioc, ignore); else { dprintk((KERN_INFO MYNAM ": %s: Skipping KickStart (delta=%ld)!\n", ioc->name, delta)); return 0; } - /* TODO! Add FC919! - } else if (ioc->chip_type == FC919) { - */ /* TODO! Add C1030! } else if (ioc->chip_type == C1030) { */ @@ -1832,9 +2075,10 @@ KickStart(MPT_ADAPTER *ioc) ioc->name, ioc->chip_type); return -5; } +#endif - if (r != 0) - return -r; + if (hard_reset_done < 0) + return hard_reset_done; dprintk((KERN_INFO MYNAM ": %s: Diagnostic reset successful\n", ioc->name)); @@ -1843,7 +2087,7 @@ KickStart(MPT_ADAPTER *ioc) if ((ioc_state = GetIocState(ioc, 1)) == MPI_IOC_STATE_READY) { dprintk((KERN_INFO MYNAM ": %s: KickStart successful! (cnt=%d)\n", ioc->name, cnt)); - return 0; + return hard_reset_done; } /* udelay(10000) ? */ current->state = TASK_INTERRUPTIBLE; @@ -1867,52 +2111,112 @@ KickStart(MPT_ADAPTER *ioc) * Returns 0 for success, non-zero for failure. */ static int -mpt_fc9x9_reset(MPT_ADAPTER *ioc) +mpt_fc9x9_reset(MPT_ADAPTER *ioc, int ignore) { - u32 diagval; + u32 diag0val; + int hard_reset_done = 0; /* Use "Diagnostic reset" method! (only thing available!) */ - /* - * Extra read to handle 909 B.0 chip problem with reset - * logic not finishing the RAM access before hard reset hits. - * (? comment taken from NT SYMMPI source) - */ - (void) CHIPREG_READ32(&ioc->chip->Fubar); + diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic); +#ifdef MPT_DEBUG +{ + u32 diag1val = 0; + if (ioc->alt_ioc) + diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic); + dprintk((KERN_INFO MYNAM ": %s: DBG1: diag0=%08x, diag1=%08x\n", + ioc->name, diag0val, diag1val)); +} +#endif + if (diag0val & MPI_DIAG_DRWE) { + dprintk((KERN_INFO MYNAM ": %s: DiagWriteEn bit already set\n", + ioc->name)); + } else { + /* Write magic sequence to WriteSequence register */ + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE); + dprintk((KERN_INFO MYNAM ": %s: Wrote magic DiagWriteEn sequence [spot#1]\n", + ioc->name)); + } - /* - * Write magic sequence to WriteSequence register. - * But, send 0x0F first to insure a reset to the beginning of the sequence. - */ - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_KEY_VALUE_MASK); - - /* Now write magic sequence */ - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE); - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE); - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE); - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE); - CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE); - dprintk((KERN_INFO MYNAM ": %s: Wrote magic DiagWriteEn sequence\n", - ioc->name)); + diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic); +#ifdef MPT_DEBUG +{ + u32 diag1val = 0; + if (ioc->alt_ioc) + diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic); + dprintk((KERN_INFO MYNAM ": %s: DbG2: diag0=%08x, diag1=%08x\n", + ioc->name, diag0val, diag1val)); +} +#endif + if (!ignore && (diag0val & MPI_DIAG_RESET_HISTORY)) { + dprintk((KERN_INFO MYNAM ": %s: Skipping due to ResetHistory bit set!\n", + ioc->name)); + } else { + /* + * Now hit the reset bit in the Diagnostic register + * (THE BIG HAMMER!) + */ + CHIPREG_WRITE32(&ioc->chip->Diagnostic, MPI_DIAG_RESET_ADAPTER); + hard_reset_done = 1; + dprintk((KERN_INFO MYNAM ": %s: Diagnostic reset performed\n", + ioc->name)); - /* Now hit the reset bit in the Diagnostic register */ - CHIPREG_WRITE32(&ioc->chip->Diagnostic, MPI_DIAG_RESET_ADAPTER); + /* want udelay(100) */ + current->state = TASK_INTERRUPTIBLE; + schedule_timeout(1); - udelay(100); + /* Write magic sequence to WriteSequence register */ + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE); + CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE); + dprintk((KERN_INFO MYNAM ": %s: Wrote magic DiagWriteEn sequence [spot#2]\n", + ioc->name)); + } - if ((diagval = CHIPREG_READ32(&ioc->chip->Diagnostic)) & - (MPI_DIAG_FLASH_BAD_SIG | MPI_DIAG_DISABLE_ARM)) { - printk(KERN_ERR MYNAM ": %s: ERROR - Diagnostic reset FAILED!\n", + /* Clear RESET_HISTORY bit! */ + CHIPREG_WRITE32(&ioc->chip->Diagnostic, 0x0); + + diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic); +#ifdef MPT_DEBUG +{ + u32 diag1val = 0; + if (ioc->alt_ioc) + diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic); + dprintk((KERN_INFO MYNAM ": %s: DbG3: diag0=%08x, diag1=%08x\n", + ioc->name, diag0val, diag1val)); +} +#endif + if (diag0val & MPI_DIAG_RESET_HISTORY) { + printk(KERN_WARNING MYNAM ": %s: WARNING - ResetHistory bit failed to clear!\n", ioc->name); - return -9; } - /* TODO! - * Cleanup all event stuff for this IOC; - * re-issue EventNotification request if needed. + diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic); +#ifdef MPT_DEBUG +{ + u32 diag1val = 0; + if (ioc->alt_ioc) + diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic); + dprintk((KERN_INFO MYNAM ": %s: DbG4: diag0=%08x, diag1=%08x\n", + ioc->name, diag0val, diag1val)); +} +#endif + if (diag0val & (MPI_DIAG_FLASH_BAD_SIG | MPI_DIAG_RESET_ADAPTER | MPI_DIAG_DISABLE_ARM)) { + printk(KERN_ERR MYNAM ": %s: ERROR - Diagnostic reset FAILED! (%02xh)\n", + ioc->name, diag0val); + return -3; + } + + /* + * Reset flag that says we've enabled event notification */ - if (ioc->factsN.Function) - ioc->factsN.EventState = 0; + ioc->facts.EventState = 0; /* NEW! 20010220 -sralston * Try to avoid redundant resets of the 929. @@ -1924,7 +2228,7 @@ mpt_fc9x9_reset(MPT_ADAPTER *ioc) ioc->alt_ioc->last_kickstart = ioc->last_kickstart; } - return 0; + return hard_reset_done; } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ @@ -1943,18 +2247,18 @@ SendIocReset(MPT_ADAPTER *ioc, u8 reset_type) { int r; - printk(KERN_WARNING MYNAM ": %s: Sending IOC reset(0x%02x)!\n", - ioc->name, reset_type); + dprintk((KERN_WARNING MYNAM ": %s: Sending IOC reset(0x%02x)!\n", + ioc->name, reset_type)); CHIPREG_WRITE32(&ioc->chip->Doorbell, reset_type<<MPI_DOORBELL_FUNCTION_SHIFT); - if ((r = WaitForDoorbellAck(ioc)) < 0) + if ((r = WaitForDoorbellAck(ioc, 2)) < 0) return r; /* TODO! * Cleanup all event stuff for this IOC; re-issue EventNotification * request if needed. */ - if (ioc->factsN.Function) - ioc->factsN.EventState = 0; + if (ioc->facts.Function) + ioc->facts.EventState = 0; return 0; } @@ -2125,6 +2429,7 @@ out_fail: * @req: Pointer to MPT request frame * @replyBytes: Expected size of the reply in bytes * @u16reply: Pointer to area where reply should be written + * @maxwait: Max wait time for a reply (in seconds) * * NOTES: It is the callers responsibility to byte-swap fields in the * request which are greater than 1 byte in size. It is also the @@ -2134,7 +2439,7 @@ out_fail: * Returns 0 for success, non-zero for failure. */ static int -HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply) +HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u16 *u16reply, int maxwait) { MPIDefaultReply_t *mptReply; int failcnt = 0; @@ -2160,7 +2465,7 @@ HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u /* * Wait for IOC's doorbell handshake int */ - if ((t = WaitForDoorbellInt(ioc)) < 0) + if ((t = WaitForDoorbellInt(ioc, 2)) < 0) failcnt++; dhsprintk((KERN_INFO MYNAM ": %s: HandShake request start, WaitCnt=%d%s\n", @@ -2172,7 +2477,7 @@ HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u * our handshake request. */ CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); - if (!failcnt && (t = WaitForDoorbellAck(ioc)) < 0) + if (!failcnt && (t = WaitForDoorbellAck(ioc, 2)) < 0) failcnt++; if (!failcnt) { @@ -2190,7 +2495,7 @@ HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u (req_as_bytes[(i*4) + 3] << 24)); CHIPREG_WRITE32(&ioc->chip->Doorbell, word); - if ((t = WaitForDoorbellAck(ioc)) < 0) + if ((t = WaitForDoorbellAck(ioc, 2)) < 0) failcnt++; } @@ -2203,7 +2508,7 @@ HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u /* * Wait for completion of doorbell handshake reply from the IOC */ - if (!failcnt && (t = WaitForDoorbellReply(ioc)) < 0) + if (!failcnt && (t = WaitForDoorbellReply(ioc, maxwait)) < 0) failcnt++; /* @@ -2223,16 +2528,17 @@ HandShakeReqAndReply(MPT_ADAPTER *ioc, int reqBytes, u32 *req, int replyBytes, u * WaitForDoorbellAck - Wait for IOC to clear the IOP_DOORBELL_STATUS bit * in it's IntStatus register. * @ioc: Pointer to MPT_ADAPTER structure + * @howlong: How long to wait (in seconds) * - * This routine waits (up to ~30 seconds max) for IOC doorbell + * This routine waits (up to ~2 seconds max) for IOC doorbell * handshake ACKnowledge. * * Returns a negative value on failure, else wait loop count. */ static int -WaitForDoorbellAck(MPT_ADAPTER *ioc) +WaitForDoorbellAck(MPT_ADAPTER *ioc, int howlong) { - int cntdn = HZ * 30; /* ~30 seconds */ + int cntdn = HZ * howlong; int count = 0; u32 intstat; @@ -2261,15 +2567,16 @@ WaitForDoorbellAck(MPT_ADAPTER *ioc) * WaitForDoorbellInt - Wait for IOC to set the HIS_DOORBELL_INTERRUPT bit * in it's IntStatus register. * @ioc: Pointer to MPT_ADAPTER structure + * @howlong: How long to wait (in seconds) * - * This routine waits (up to ~30 seconds max) for IOC doorbell interrupt. + * This routine waits (up to ~2 seconds max) for IOC doorbell interrupt. * * Returns a negative value on failure, else wait loop count. */ static int -WaitForDoorbellInt(MPT_ADAPTER *ioc) +WaitForDoorbellInt(MPT_ADAPTER *ioc, int howlong) { - int cntdn = HZ * 30; /* ~30 seconds */ + int cntdn = HZ * howlong; int count = 0; u32 intstat; @@ -2297,6 +2604,7 @@ WaitForDoorbellInt(MPT_ADAPTER *ioc) /* * WaitForDoorbellReply - Wait for and capture a IOC handshake reply. * @ioc: Pointer to MPT_ADAPTER structure + * @howlong: How long to wait (in seconds) * * This routine polls the IOC for a handshake reply, 16 bits at a time. * Reply is cached to IOC private area large enough to hold a maximum @@ -2305,7 +2613,7 @@ WaitForDoorbellInt(MPT_ADAPTER *ioc) * Returns a negative value on failure, else size of reply in WORDS. */ static int -WaitForDoorbellReply(MPT_ADAPTER *ioc) +WaitForDoorbellReply(MPT_ADAPTER *ioc, int howlong) { int u16cnt = 0; int failcnt = 0; @@ -2319,11 +2627,18 @@ WaitForDoorbellReply(MPT_ADAPTER *ioc) /* * Get first two u16's so we can look at IOC's intended reply MsgLength */ - for (u16cnt=0; !failcnt && u16cnt < 2; u16cnt++) { - if ((t = WaitForDoorbellInt(ioc)) < 0) - failcnt++; - hs_reply[u16cnt] = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF); + u16cnt=0; + if ((t = WaitForDoorbellInt(ioc, howlong)) < 0) { + failcnt++; + } else { + hs_reply[u16cnt++] = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF); CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); + if ((t = WaitForDoorbellInt(ioc, 2)) < 0) + failcnt++; + else { + hs_reply[u16cnt++] = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF); + CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); + } } dhsprintk((KERN_INFO MYNAM ": %s: First handshake reply word=%08x%s\n", @@ -2335,7 +2650,7 @@ WaitForDoorbellReply(MPT_ADAPTER *ioc) * reply 16 bits at a time. */ for (u16cnt=2; !failcnt && u16cnt < (2 * mptReply->MsgLength); u16cnt++) { - if ((t = WaitForDoorbellInt(ioc)) < 0) + if ((t = WaitForDoorbellInt(ioc, 2)) < 0) failcnt++; hword = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF); /* don't overflow our IOC hs_reply[] buffer! */ @@ -2344,7 +2659,7 @@ WaitForDoorbellReply(MPT_ADAPTER *ioc) CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); } - if (!failcnt && (t = WaitForDoorbellInt(ioc)) < 0) + if (!failcnt && (t = WaitForDoorbellInt(ioc, 2)) < 0) failcnt++; CHIPREG_WRITE32(&ioc->chip->IntStatus, 0); @@ -2428,7 +2743,7 @@ GetLanConfigPages(MPT_ADAPTER *ioc) ioc->name)); i = HandShakeReqAndReply(ioc, req_sz, (u32*)&config_req, - reply_sz, (u16*)&config_reply); + reply_sz, (u16*)&config_reply, 3); pci_unmap_single(ioc->pcidev, page0_dma, data_sz, PCI_DMA_FROMDEVICE); if (i != 0) return i; @@ -2472,7 +2787,7 @@ GetLanConfigPages(MPT_ADAPTER *ioc) ioc->name)); i = HandShakeReqAndReply(ioc, req_sz, (u32*)&config_req, - reply_sz, (u16*)&config_reply); + reply_sz, (u16*)&config_reply, 3); pci_unmap_single(ioc->pcidev, page1_dma, data_sz, PCI_DMA_FROMDEVICE); if (i != 0) return i; @@ -2564,7 +2879,6 @@ SendEventAck(MPT_ADAPTER *ioc, EventNotificationReply_t *evnp) return len; \ } - /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* * procmpt_create - Create %MPT_PROCFS_MPTBASEDIR entries. @@ -2653,6 +2967,9 @@ procmpt_destroy(void) { MPT_ADAPTER *ioc; + if (!procmpt_root_dir) + return 0; + /* * BEWARE: If/when MPT_PROCFS_MPTBASEDIR changes from "mpt" * (single level) to multi level (e.g. "driver/message/fusion") @@ -2685,6 +3002,7 @@ procmpt_destroy(void) if (atomic_read((atomic_t *)&procmpt_root_dir->count) == 0) { remove_proc_entry(MPT_PROCFS_MPTBASEDIR, 0); + procmpt_root_dir = NULL; return 0; } @@ -2724,7 +3042,7 @@ procmpt_read_summary(char *page, char **start, off_t off, int count, int *eof, v // Too verbose! // mpt_print_ioc_facts(ioc, out, &more, 0); - mpt_print_ioc_summary(ioc, out, &more, 0); + mpt_print_ioc_summary(ioc, out, &more, 0, 1); out += more; if ((out-page) >= count) { @@ -2784,15 +3102,15 @@ procmpt_read_dbg(char *page, char **start, off_t off, int count, int *eof, void static void mpt_get_fw_exp_ver(char *buf, MPT_ADAPTER *ioc) { - if ((ioc->facts0.FWVersion & 0xF000) == 0xE000) + if ((ioc->facts.FWVersion & 0xF000) == 0xE000) sprintf(buf, " (Exp %02d%02d)", - (ioc->facts0.FWVersion & 0x0F00) >> 8, /* Month */ - ioc->facts0.FWVersion & 0x001F); /* Day */ + (ioc->facts.FWVersion & 0x0F00) >> 8, /* Month */ + ioc->facts.FWVersion & 0x001F); /* Day */ else buf[0] ='\0'; /* insider hack! */ - if (ioc->facts0.FWVersion & 0x0080) { + if (ioc->facts.FWVersion & 0x0080) { strcat(buf, " [MDBG]"); } } @@ -2804,17 +3122,17 @@ mpt_get_fw_exp_ver(char *buf, MPT_ADAPTER *ioc) * @buffer: Pointer to buffer where IOC summary info should be written * @size: Pointer to number of bytes we wrote (set by this routine) * @len: Offset at which to start writing in buffer + * @showlan: Display LAN stuff? * * This routine writes (english readable) ASCII text, which represents * a summary of IOC information, to a buffer. */ void -mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buffer, int *size, int len) +mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buffer, int *size, int len, int showlan) { char expVer[32]; int y; - mpt_get_fw_exp_ver(expVer, ioc); /* @@ -2824,17 +3142,20 @@ mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buffer, int *size, int len) ioc->name, ioc->prod_name, MPT_FW_REV_MAGIC_ID_STRING, /* "FwRev=" or somesuch */ - ioc->facts0.FWVersion, + ioc->facts.FWVersion, expVer, - ioc->facts0.NumberOfPorts, + ioc->facts.NumberOfPorts, ioc->req_depth); - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { + if (showlan && (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN)) { u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow; y += sprintf(buffer+len+y, ", LanAddr=%02X:%02X:%02X:%02X:%02X:%02X", a[5], a[4], a[3], a[2], a[1], a[0]); } + if (ioc->pci_irq < 100) + y += sprintf(buffer+len+y, ", IRQ=%d", ioc->pci_irq); + if (!ioc->active) y += sprintf(buffer+len+y, " (disabled)"); @@ -2861,32 +3182,34 @@ mpt_print_ioc_facts(MPT_ADAPTER *ioc, char *buffer, int *size, int len) char iocName[16]; int sz; int y; - + int p; mpt_get_fw_exp_ver(expVer, ioc); strcpy(iocName, ioc->name); y = sprintf(buffer+len, "%s:\n", iocName); - y += sprintf(buffer+len+y, " ProductID = 0x%04x\n", ioc->facts0.ProductID); - y += sprintf(buffer+len+y, " PortNumber = %d (of %d)\n", - ioc->pfacts0.PortNumber+1, - ioc->facts0.NumberOfPorts); - if (ioc->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { - u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow; - y += sprintf(buffer+len+y, " LanAddr = 0x%02x:%02x:%02x:%02x:%02x:%02x\n", - a[5], a[4], a[3], a[2], a[1], a[0]); + y += sprintf(buffer+len+y, " ProductID = 0x%04x\n", ioc->facts.ProductID); + for (p=0; p < ioc->facts.NumberOfPorts; p++) { + y += sprintf(buffer+len+y, " PortNumber = %d (of %d)\n", + p+1, + ioc->facts.NumberOfPorts); + if (ioc->pfacts[p].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { + u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow; + y += sprintf(buffer+len+y, " LanAddr = 0x%02x:%02x:%02x:%02x:%02x:%02x\n", + a[5], a[4], a[3], a[2], a[1], a[0]); + } } - y += sprintf(buffer+len+y, " FWVersion = 0x%04x%s\n", ioc->facts0.FWVersion, expVer); - y += sprintf(buffer+len+y, " MsgVersion = 0x%04x\n", ioc->facts0.MsgVersion); - y += sprintf(buffer+len+y, " WhoInit = 0x%02x\n", ioc->facts0.WhoInit); - y += sprintf(buffer+len+y, " EventState = 0x%02x\n", ioc->facts0.EventState); + y += sprintf(buffer+len+y, " FWVersion = 0x%04x%s\n", ioc->facts.FWVersion, expVer); + y += sprintf(buffer+len+y, " MsgVersion = 0x%04x\n", ioc->facts.MsgVersion); + y += sprintf(buffer+len+y, " FirstWhoInit = 0x%02x\n", ioc->FirstWhoInit); + y += sprintf(buffer+len+y, " EventState = 0x%02x\n", ioc->facts.EventState); y += sprintf(buffer+len+y, " CurrentHostMfaHighAddr = 0x%08x\n", - ioc->facts0.CurrentHostMfaHighAddr); + ioc->facts.CurrentHostMfaHighAddr); y += sprintf(buffer+len+y, " CurrentSenseBufferHighAddr = 0x%08x\n", - ioc->facts0.CurrentSenseBufferHighAddr); - y += sprintf(buffer+len+y, " MaxChainDepth = 0x%02x frames\n", ioc->facts0.MaxChainDepth); - y += sprintf(buffer+len+y, " MinBlockSize = 0x%02x bytes\n", 4*ioc->facts0.BlockSize); + ioc->facts.CurrentSenseBufferHighAddr); + y += sprintf(buffer+len+y, " MaxChainDepth = 0x%02x frames\n", ioc->facts.MaxChainDepth); + y += sprintf(buffer+len+y, " MinBlockSize = 0x%02x bytes\n", 4*ioc->facts.BlockSize); y += sprintf(buffer+len+y, " RequestFrames @ 0x%p (Dma @ 0x%08x)\n", ioc->req_alloc, ioc->req_alloc_dma); @@ -2898,8 +3221,8 @@ mpt_print_ioc_facts(MPT_ADAPTER *ioc, char *buffer, int *size, int len) y += sprintf(buffer+len+y, " {CurReqSz=%d} x {CurReqDepth=%d} = %d bytes ^= 0x%x\n", ioc->req_sz, ioc->req_depth, ioc->req_sz*ioc->req_depth, sz); y += sprintf(buffer+len+y, " {MaxReqSz=%d} {MaxReqDepth=%d}\n", - 4*ioc->facts0.RequestFrameSize, - ioc->facts0.GlobalCredits); + 4*ioc->facts.RequestFrameSize, + ioc->facts.GlobalCredits); y += sprintf(buffer+len+y, " ReplyFrames @ 0x%p (Dma @ 0x%08x)\n", ioc->reply_alloc, ioc->reply_alloc_dma); @@ -2907,8 +3230,8 @@ mpt_print_ioc_facts(MPT_ADAPTER *ioc, char *buffer, int *size, int len) y += sprintf(buffer+len+y, " {CurRepSz=%d} x {CurRepDepth=%d} = %d bytes ^= 0x%x\n", ioc->reply_sz, ioc->reply_depth, ioc->reply_sz*ioc->reply_depth, sz); y += sprintf(buffer+len+y, " {MaxRepSz=%d} {MaxRepDepth=%d}\n", - ioc->factsN.CurReplyFrameSize, - ioc->facts0.ReplyQueueDepth); + ioc->facts.CurReplyFrameSize, + ioc->facts.ReplyQueueDepth); *size = y; } @@ -3045,8 +3368,8 @@ ProcessEventNotification(MPT_ADAPTER *ioc, EventNotificationReply_t *pEventReply /* CHECKME! What if evState unexpectedly says OFF (0)? */ /* Update EventState field in cached IocFacts */ - if (ioc->factsN.Function) { - ioc->factsN.EventState = evState; + if (ioc->facts.Function) { + ioc->facts.EventState = evState; } } break; @@ -3182,6 +3505,9 @@ mpt_fc_log_info(MPT_ADAPTER *ioc, u32 log_info) case MPI_IOCLOGINFO_FC_LINK_LINK_NOT_ESTABLISHED: desc = "Not synchronized to signal or still negotiating (possible cable problem)"; break; + case MPI_IOCLOGINFO_FC_LINK_CRC_ERROR: + desc = "CRC check detected error on received frame"; + break; } printk(KERN_INFO MYNAM ": %s: LogInfo(0x%08x): SubCl={%s}", @@ -3259,6 +3585,8 @@ EXPORT_SYMBOL(mpt_register); EXPORT_SYMBOL(mpt_deregister); EXPORT_SYMBOL(mpt_event_register); EXPORT_SYMBOL(mpt_event_deregister); +EXPORT_SYMBOL(mpt_reset_register); +EXPORT_SYMBOL(mpt_reset_deregister); EXPORT_SYMBOL(mpt_get_msg_frame); EXPORT_SYMBOL(mpt_put_msg_frame); EXPORT_SYMBOL(mpt_free_msg_frame); @@ -3299,6 +3627,7 @@ int __init fusion_init(void) MptCallbacks[i] = NULL; MptDriverClass[i] = MPTUNKNOWN_DRIVER; MptEvHandlers[i] = NULL; + MptResetHandlers[i] = NULL; } /* NEW! 20010120 -sralston @@ -3323,23 +3652,9 @@ int __init fusion_init(void) static void fusion_exit(void) { MPT_ADAPTER *this; - int i; dprintk((KERN_INFO MYNAM ": fusion_exit() called!\n")); - /* - * Paranoia; disable interrupts on all MPT adapters. - */ - for (i=0; i<MPT_MAX_ADAPTERS; i++) { - if ((this = mpt_adapters[i]) != NULL) { - /* Disable adapter interrupts! */ - CHIPREG_WRITE32(&this->chip->IntMask, 0xFFFFFFFF); - /* Clear any lingering interrupt */ - CHIPREG_WRITE32(&this->chip->IntStatus, 0); - this->active = 0; - } - } - /* Whups? 20010120 -sralston * Moved this *above* removal of all MptAdapters! */ diff --git a/drivers/message/fusion/mptbase.h b/drivers/message/fusion/mptbase.h index 68fc7acff022..d19402a58f15 100644 --- a/drivers/message/fusion/mptbase.h +++ b/drivers/message/fusion/mptbase.h @@ -12,7 +12,7 @@ * Originally By: Steven J. Ralston * (mailto:Steve.Ralston@lsil.com) * - * $Id: mptbase.h,v 1.38 2001/03/22 10:54:30 sralston Exp $ + * $Id: mptbase.h,v 1.46.2.2.2.1 2001/08/24 20:07:05 sralston Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -63,8 +63,8 @@ #include "lsi/mpi_init.h" /* SCSI Host (initiator) protocol support */ #include "lsi/mpi_lan.h" /* LAN over FC protocol support */ -//#include "lsi/mpi_fc.h" /* Fibre Channel (lowlevel) support */ -//#include "lsi/mpi_targ.h" /* SCSI/FCP Target protcol support */ +#include "lsi/mpi_fc.h" /* Fibre Channel (lowlevel) support */ +#include "lsi/mpi_targ.h" /* SCSI/FCP Target protcol support */ #include "lsi/fc_log.h" /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ @@ -77,9 +77,8 @@ #define COPYRIGHT "Copyright (c) 1999-2001 " MODULEAUTHOR #endif -#define MPT_LINUX_VERSION_COMMON "1.00.11" -#define MPT_LINUX_VERSION_EXP "0.09.66-EXP" -#define MPT_LINUX_PACKAGE_NAME "@(#)mptlinux-1.00.11" +#define MPT_LINUX_VERSION_COMMON "1.02.01" +#define MPT_LINUX_PACKAGE_NAME "@(#)mptlinux-1.02.01" #define WHAT_MAGIC_STRING "@" "(" "#" ")" #define show_mptmod_ver(s,ver) \ @@ -91,6 +90,7 @@ */ #define MPT_MAX_ADAPTERS 16 #define MPT_MAX_PROTOCOL_DRIVERS 8 +#define MPT_MAX_FC_DEVICES 255 #define MPT_MISCDEV_BASENAME "mptctl" #define MPT_MISCDEV_PATHNAME "/dev/" MPT_MISCDEV_BASENAME @@ -262,8 +262,6 @@ typedef struct _MPT_ADAPTER struct _MPT_ADAPTER *back; int id; /* Unique adapter id {0,1,2,...} */ int pci_irq; - IOCFactsReply_t facts0; - IOCFactsReply_t factsN; char name[32]; /* "iocN" */ char *prod_name; /* "LSIFC9x9" */ u32 mem_phys; /* == f4020000 (mmap) */ @@ -275,10 +273,6 @@ typedef struct _MPT_ADAPTER int active; int sod_reset; unsigned long last_kickstart; - PortFactsReply_t pfacts0; - PortFactsReply_t pfactsN; - LANPage0_t lan_cnfg_page0; - LANPage1_t lan_cnfg_page1; u8 *reply_alloc; /* Reply frames alloc ptr */ dma_addr_t reply_alloc_dma; MPT_FRAME_HDR *reply_frames; /* Reply frames - rounded up! */ @@ -292,24 +286,30 @@ typedef struct _MPT_ADAPTER dma_addr_t req_frames_dma; int req_depth; int req_sz; - spinlock_t FreeQlock; MPT_Q_TRACKER FreeQ; + spinlock_t FreeQlock; /* Pool of SCSI sense buffers for commands coming from * the SCSI mid-layer. We have one 256 byte sense buffer * for each REQ entry. */ u8 *sense_buf_pool; dma_addr_t sense_buf_pool_dma; - int hs_reply_idx; - u32 hs_req[MPT_MAX_FRAME_SIZE/sizeof(u32)]; - u16 hs_reply[MPT_MAX_FRAME_SIZE/sizeof(u16)]; struct pci_dev *pcidev; - struct _MPT_ADAPTER *alt_ioc; /* atomic_t userCnt; */ u8 *memmap; int mtrr_reg; struct Scsi_Host *sh; struct proc_dir_entry *ioc_dentry; + struct _MPT_ADAPTER *alt_ioc; + int hs_reply_idx; + u32 hs_req[MPT_MAX_FRAME_SIZE/sizeof(u32)]; + u16 hs_reply[MPT_MAX_FRAME_SIZE/sizeof(u16)]; + IOCFactsReply_t facts; + PortFactsReply_t pfacts[2]; + LANPage0_t lan_cnfg_page0; + LANPage1_t lan_cnfg_page1; + u8 FirstWhoInit; + u8 pad1[3]; } MPT_ADAPTER; @@ -324,26 +324,25 @@ typedef struct _MPT_ADAPTER_TRACKER { * 0 = not Ok ... */ typedef int (*MPT_CALLBACK)(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply); + typedef int (*MPT_EVHANDLER)(MPT_ADAPTER *ioc, EventNotificationReply_t *evReply); +typedef int (*MPT_RESETHANDLER)(MPT_ADAPTER *ioc, int reset_phase); +/* reset_phase defs */ +#define MPT_IOC_PRE_RESET 0 +#define MPT_IOC_POST_RESET 1 /* - * Fibre Channel (SCSI) target device... + * Invent MPT host event (super-set of MPI Events) + * Fitted to 1030's 64-byte [max] request frame size */ -typedef struct _FC_TARGET { - struct _FC_TARGET *forw; - struct _FC_TARGET *back; - int bus_id; - int target_id; - int lun_exists[32]; - u8 inquiry_data[36]; - u8 last_sense[256]; -} FC_TARGET; - -typedef struct _FCDEV_TRACKER { - FC_TARGET *head; - FC_TARGET *tail; -} FCDEV_TRACKER; +typedef struct _MPT_HOST_EVENT { + EventNotificationReply_t MpiEvent; /* 8 32-bit words! */ + u32 pad[6]; + void *next; +} MPT_HOST_EVENT; +#define MPT_HOSTEVENT_IOC_BRINGUP 0x91 +#define MPT_HOSTEVENT_IOC_RECOVER 0x92 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -523,6 +522,8 @@ extern int mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass); extern void mpt_deregister(int cb_idx); extern int mpt_event_register(int cb_idx, MPT_EVHANDLER ev_cbfunc); extern void mpt_event_deregister(int cb_idx); +extern int mpt_reset_register(int cb_idx, MPT_RESETHANDLER reset_func); +extern void mpt_reset_deregister(int cb_idx); extern int mpt_register_ascqops_strings(/*ASCQ_Table_t*/void *ascqTable, int ascqtbl_sz, const char **opsTable); extern void mpt_deregister_ascqops_strings(void); extern MPT_FRAME_HDR *mpt_get_msg_frame(int handle, int iocid); @@ -532,7 +533,7 @@ extern int mpt_send_handshake_request(int handle, int iocid, int reqBytes, u32 extern int mpt_verify_adapter(int iocid, MPT_ADAPTER **iocpp); extern MPT_ADAPTER *mpt_adapter_find_first(void); extern MPT_ADAPTER *mpt_adapter_find_next(MPT_ADAPTER *prev); -extern void mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buf, int *size, int len); +extern void mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buf, int *size, int len, int showlan); extern void mpt_print_ioc_facts(MPT_ADAPTER *ioc, char *buf, int *size, int len); /* diff --git a/drivers/message/fusion/mptctl.c b/drivers/message/fusion/mptctl.c index a939104e8187..5809cee210cf 100644 --- a/drivers/message/fusion/mptctl.c +++ b/drivers/message/fusion/mptctl.c @@ -27,7 +27,7 @@ * Originally By: Steven J. Ralston, Noah Romer * (mailto:Steve.Ralston@lsil.com) * - * $Id: mptctl.c,v 1.23 2001/03/21 19:42:31 sralston Exp $ + * $Id: mptctl.c,v 1.25.4.1 2001/08/24 20:07:06 sralston Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -205,6 +205,22 @@ mptctl_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply) } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/* + * struct file_operations functionality. + * Members: + * llseek, write, read, ioctl, open, release + */ +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,9) +static loff_t +mptctl_llseek(struct file *file, loff_t offset, int origin) +{ + return -ESPIPE; +} +#define no_llseek mptctl_llseek +#endif + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ static ssize_t mptctl_write(struct file *file, const char *buf, size_t count, loff_t *ppos) { @@ -335,8 +351,8 @@ mpt_ioctl_do_fw_download(int ioc, char *ufwbuf, size_t fwlen) SGESimple32_t *sgl; SGESimple32_t *sgOut, *sgIn; dma_addr_t sgl_dma; - struct buflist *buflist; - struct buflist *bl; + struct buflist *buflist = NULL; + struct buflist *bl = NULL; int numfrags = 0; int maxfrags; int n = 0; @@ -421,7 +437,7 @@ mpt_ioctl_do_fw_download(int ioc, char *ufwbuf, size_t fwlen) sgIn = sgl; bl = buflist; for (i=0; i < numfrags; i++) { - nib = (sgIn->FlagsLength & 0xF0000000) >> 28; + nib = (le32_to_cpu(sgIn->FlagsLength) & 0xF0000000) >> 28; /* skip ignore/chain. */ if (nib == 0 || nib == 3) { ; @@ -654,7 +670,7 @@ free_and_fail: u8 *kptr; int len; - if ((sglbuf[i].FlagsLength >> 24) == 0x30) + if ((le32_to_cpu(sglbuf[i].FlagsLength) >> 24) == 0x30) continue; dma_addr = le32_to_cpu(sglbuf[i].Address); @@ -679,12 +695,12 @@ kfree_sgl(SGESimple32_t *sgl, dma_addr_t sgl_dma, struct buflist *buflist, MPT_A int dir; int n = 0; - if (sg->FlagsLength & 0x04000000) + if (le32_to_cpu(sg->FlagsLength) & 0x04000000) dir = PCI_DMA_TODEVICE; else dir = PCI_DMA_FROMDEVICE; - nib = (sg->FlagsLength & 0xF0000000) >> 28; + nib = (le32_to_cpu(sg->FlagsLength) & 0xF0000000) >> 28; while (! (nib & 0x4)) { /* eob */ /* skip ignore/chain. */ if (nib == 0 || nib == 3) { @@ -703,7 +719,7 @@ kfree_sgl(SGESimple32_t *sgl, dma_addr_t sgl_dma, struct buflist *buflist, MPT_A } sg++; bl++; - nib = (sg->FlagsLength & 0xF0000000) >> 28; + nib = (le32_to_cpu(sg->FlagsLength) & 0xF0000000) >> 28; } /* we're at eob! */ @@ -1081,10 +1097,14 @@ mpt_ioctl_scsi_cmd(unsigned long arg) /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ -static struct file_operations mptctl_fops = { #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,3,51) - owner: THIS_MODULE, +#define owner_THIS_MODULE owner: THIS_MODULE, +#else +#define owner_THIS_MODULE #endif + +static struct file_operations mptctl_fops = { + owner_THIS_MODULE llseek: no_llseek, read: mptctl_read, write: mptctl_write, @@ -1162,48 +1182,6 @@ sparc32_mptfwxfer_ioctl(unsigned int fd, unsigned int cmd, return ret; } -#if 0 /* { */ -static int -sparc32_mptfwxfer_ioctl(unsigned int fd, unsigned int cmd, - unsigned long arg, struct file *filp) -{ - struct mpt_fw_xfer32 kfw32; - struct mpt_fw_xfer kfw; - mm_segment_t old_fs; - int ret; - - dprintk((KERN_INFO MYNAM "::sparc32_mptfwxfer_ioctl() called\n")); - - if (copy_from_user(&kfw32, (char *)arg, sizeof(kfw32))) - return -EFAULT; - - /* Verify intended MPT adapter */ - iocnumX = kfw32.iocnum & 0xFF; - if (((iocnum = mpt_verify_adapter(iocnumX, &iocp)) < 0) || - (iocp == NULL)) { - printk(KERN_ERR MYNAM "::sparc32_mptfwxfer_ioctl @%d - ioc%d not found!\n", - __LINE__, iocnumX); - return -ENODEV; - } - - if ((ret = mptctl_syscall_down(iocp, nonblock)) != 0) - return ret; - - kfw.iocnum = iocnum; - kfw.fwlen = kfw32.fwlen; - kfw.bufp = (void *)(unsigned long)kfw32.bufp; - - old_fs = get_fs(); - set_fs(KERNEL_DS); - ret = sys_ioctl(fd, MPTFWDOWNLOAD, (unsigned long)&kfw); - set_fs(old_fs); - - up(&mptctl_syscall_sem_ioc[iocp->id]); - - return ret; -} -#endif /* #if 0 } */ - #endif /*} linux >= 2.3.x */ #endif /*} sparc */ @@ -1228,8 +1206,7 @@ int __init mptctl_init(void) if (++where && err) goto out_fail; err = register_ioctl32_conversion(MPTRWPERF_RESET, NULL); if (++where && err) goto out_fail; - err = register_ioctl32_conversion(MPTFWDOWNLOAD32, - sparc32_mptfwxfer_ioctl); + err = register_ioctl32_conversion(MPTFWDOWNLOAD32, sparc32_mptfwxfer_ioctl); if (++where && err) goto out_fail; #endif /*} linux >= 2.3.x */ #endif /*} sparc */ @@ -1247,7 +1224,7 @@ int __init mptctl_init(void) * Install our handler */ ++where; - if ((mptctl_id = mpt_register(mptctl_reply, MPTCTL_DRIVER)) < 0) { + if ((mptctl_id = mpt_register(mptctl_reply, MPTCTL_DRIVER)) <= 0) { printk(KERN_ERR MYNAM ": ERROR: Failed to register with Fusion MPT base driver\n"); misc_deregister(&mptctl_miscdev); err = -EBUSY; @@ -1275,6 +1252,16 @@ out_fail: /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ void mptctl_exit(void) { + +#if defined(__sparc__) && defined(__sparc_v9__) /*{*/ +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,3,0) /*{*/ + unregister_ioctl32_conversion(MPTRWPERF); + unregister_ioctl32_conversion(MPTRWPERF_CHK); + unregister_ioctl32_conversion(MPTRWPERF_RESET); + unregister_ioctl32_conversion(MPTFWDOWNLOAD32); +#endif /*} linux >= 2.3.x */ +#endif /*} sparc */ + misc_deregister(&mptctl_miscdev); printk(KERN_INFO MYNAM ": /dev/%s @ (major,minor=%d,%d)\n", mptctl_miscdev.name, MISC_MAJOR, mptctl_miscdev.minor); diff --git a/drivers/message/fusion/mptlan.c b/drivers/message/fusion/mptlan.c index f619f2f12588..542ac00eb1e5 100644 --- a/drivers/message/fusion/mptlan.c +++ b/drivers/message/fusion/mptlan.c @@ -26,7 +26,7 @@ * Copyright (c) 2000-2001 LSI Logic Corporation * Originally By: Noah Romer * - * $Id: mptlan.c,v 1.25 2001/03/02 22:12:04 sralston Exp $ + * $Id: mptlan.c,v 1.32.2.2 2001/07/12 19:43:33 nromer Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -93,6 +93,12 @@ * Fusion MPT LAN private structures */ +struct NAA_Hosed { + u16 NAA; + u8 ieee[FC_ALEN]; + struct NAA_Hosed *next; +}; + struct BufferControl { struct sk_buff *skb; dma_addr_t dma; @@ -153,6 +159,7 @@ static int mpt_lan_receive_post_reply(struct net_device *dev, static int mpt_lan_send_turbo(struct net_device *dev, u32 tmsg); static int mpt_lan_send_reply(struct net_device *dev, LANSendReply_t *pSendRep); +static int mpt_lan_ioc_reset(MPT_ADAPTER *ioc, int reset_phase); static int mpt_lan_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply); static unsigned short mpt_lan_type_trans(struct sk_buff *skb, struct net_device *dev); @@ -168,6 +175,9 @@ static u32 tx_max_out_p = 127 - 16; static struct net_device *mpt_landev[MPT_MAX_ADAPTERS+1]; +static struct NAA_Hosed *mpt_bad_naa = NULL; +rwlock_t bad_naa_lock; + /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* * Fusion MPT LAN external data @@ -318,6 +328,41 @@ lan_reply (MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *reply) /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ static int +mpt_lan_ioc_reset(MPT_ADAPTER *ioc, int reset_phase) +{ + struct net_device *dev = mpt_landev[ioc->id]; + struct mpt_lan_priv *priv = (struct mpt_lan_priv *) dev->priv; + + dprintk((KERN_INFO MYNAM ": IOC %s_reset routed to LAN driver!\n", + reset_phase==MPT_IOC_PRE_RESET ? "pre" : "post")); + + if (priv->mpt_rxfidx == NULL) + return (1); + + if (reset_phase == MPT_IOC_PRE_RESET) { + int i; + unsigned long flags; + + netif_stop_queue(dev); + + atomic_set(&priv->buckets_out, 0); + + /* Reset Rx Free Tail index and re-populate the queue. */ + spin_lock_irqsave(&priv->rxfidx_lock, flags); + priv->mpt_rxfidx_tail = -1; + for (i = 0; i < priv->max_buckets_out; i++) + priv->mpt_rxfidx[++priv->mpt_rxfidx_tail] = i; + spin_unlock_irqrestore(&priv->rxfidx_lock, flags); + } else { + mpt_lan_post_receive_buckets(dev); + netif_wake_queue(dev); + } + + return 1; +} + +/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +static int mpt_lan_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply) { dprintk((KERN_INFO MYNAM ": MPT event routed to LAN driver!\n")); @@ -356,7 +401,19 @@ mpt_lan_open(struct net_device *dev) struct mpt_lan_priv *priv = (struct mpt_lan_priv *) dev->priv; int i; - mpt_lan_reset(dev); + if (mpt_lan_reset(dev) != 0) { + MPT_ADAPTER *mpt_dev = priv->mpt_dev; + + printk (KERN_WARNING MYNAM "/lan_open: lan_reset failed."); + + if (mpt_dev->active) + printk ("The ioc is active. Perhaps it needs to be" + " reset?\n"); + else + printk ("The ioc in inactive, most likely in the " + "process of being reset. Please try again in " + "a moment.\n"); + } priv->mpt_txfidx = kmalloc(priv->tx_max_out * sizeof(int), GFP_KERNEL); if (priv->mpt_txfidx == NULL) @@ -402,7 +459,10 @@ mpt_lan_open(struct net_device *dev) IOC_AND_NETDEV_NAMES_s_s(dev)); if (mpt_event_register(LanCtx, mpt_lan_event_process) != 0) { - /* FIXME! */ + printk (KERN_WARNING MYNAM "/lo: Unable to register for Event" + " Notifications. This is a bad thing! We're not going " + "to go ahead, but I'd be leery of system stability at " + "this point.\n"); } netif_start_queue(dev); @@ -422,6 +482,8 @@ out: return -ENOMEM; } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ +/* Send a LanReset message to the FW. This should result in the FW returning + any buckets it still has. */ static int mpt_lan_reset(struct net_device *dev) { @@ -660,6 +722,8 @@ mpt_lan_sdu_send (struct sk_buff *skb, struct net_device *dev) dma_addr_t dma; unsigned long flags; int ctx; + struct NAA_Hosed *nh; + u16 cur_naa = 0x1000; dioprintk((KERN_INFO MYNAM ": %s called, skb_addr = %p\n", __FUNCTION__, skb)); @@ -707,8 +771,10 @@ mpt_lan_sdu_send (struct sk_buff *skb, struct net_device *dev) priv->SendCtl[ctx].len = skb->len; /* Message Header */ + pSendReq->Reserved = 0; pSendReq->Function = MPI_FUNCTION_LAN_SEND; pSendReq->ChainOffset = 0; + pSendReq->Reserved2 = 0; pSendReq->MsgFlags = 0; pSendReq->PortNumber = priv->pnum; @@ -725,7 +791,26 @@ mpt_lan_sdu_send (struct sk_buff *skb, struct net_device *dev) // IOC_AND_NETDEV_NAMES_s_s(dev), // ctx, skb, skb->data)); - pTrans->TransactionDetails[0] = cpu_to_le32((0x1000 << 16) | + /* Munge the NAA for Tx packets to QLogic boards, which don't follow + RFC 2625. The longer I look at this, the more my opinion of Qlogic + drops. */ + read_lock_irq(&bad_naa_lock); + for (nh = mpt_bad_naa; nh != NULL; nh=nh->next) { + if ((nh->ieee[0] == skb->mac.raw[0]) && + (nh->ieee[1] == skb->mac.raw[1]) && + (nh->ieee[2] == skb->mac.raw[2]) && + (nh->ieee[3] == skb->mac.raw[3]) && + (nh->ieee[4] == skb->mac.raw[4]) && + (nh->ieee[5] == skb->mac.raw[5])) { + cur_naa = nh->NAA; + dprintk ((KERN_INFO "mptlan/sdu_send: using NAA value " + "= %04x.\n", cur_naa)); + break; + } + } + read_unlock_irq(&bad_naa_lock); + + pTrans->TransactionDetails[0] = cpu_to_le32((cur_naa << 16) | (skb->mac.raw[0] << 8) | (skb->mac.raw[1] << 0)); pTrans->TransactionDetails[1] = cpu_to_le32((skb->mac.raw[2] << 24) | @@ -735,9 +820,15 @@ mpt_lan_sdu_send (struct sk_buff *skb, struct net_device *dev) pSimple = (SGESimple64_t *) &pTrans->TransactionDetails[2]; + /* If we ever decide to send more than one Simple SGE per LANSend, then + we will need to make sure that LAST_ELEMENT only gets set on the + last one. Otherwise, bad voodoo and evil funkiness will commence. */ pSimple->FlagsLength = cpu_to_le32( - ((MPI_SGE_FLAGS_END_OF_BUFFER | + ((MPI_SGE_FLAGS_LAST_ELEMENT | + MPI_SGE_FLAGS_END_OF_BUFFER | MPI_SGE_FLAGS_SIMPLE_ELEMENT | + MPI_SGE_FLAGS_SYSTEM_ADDRESS | + MPI_SGE_FLAGS_HOST_TO_IOC | MPI_SGE_FLAGS_64_BIT_ADDRESSING | MPI_SGE_FLAGS_END_OF_LIST) << MPI_SGE_FLAGS_SHIFT) | skb->len); @@ -1252,12 +1343,12 @@ mpt_register_lan_device (MPT_ADAPTER *mpt_dev, int pnum) priv->total_posted = 0; priv->total_received = 0; priv->max_buckets_out = max_buckets_out; - if (mpt_dev->pfacts0.MaxLanBuckets < max_buckets_out) - priv->max_buckets_out = mpt_dev->pfacts0.MaxLanBuckets; + if (mpt_dev->pfacts[0].MaxLanBuckets < max_buckets_out) + priv->max_buckets_out = mpt_dev->pfacts[0].MaxLanBuckets; dprintk((KERN_INFO MYNAM "@%d: MaxLanBuckets=%d, max_buckets_out/priv=%d/%d\n", __LINE__, - mpt_dev->pfacts0.MaxLanBuckets, + mpt_dev->pfacts[0].MaxLanBuckets, max_buckets_out, priv->max_buckets_out)); @@ -1316,7 +1407,11 @@ mpt_lan_init (void) show_mptmod_ver(LANAME, LANVER); - if ((LanCtx = mpt_register(lan_reply, MPTLAN_DRIVER)) < 0) { + /* Init the global r/w lock for the bad_naa list. We want to do this + before any boards are initialized and may be used. */ + rwlock_init(&bad_naa_lock); + + if ((LanCtx = mpt_register(lan_reply, MPTLAN_DRIVER)) <= 0) { printk (KERN_ERR MYNAM ": Failed to register with MPT base driver\n"); return -EBUSY; } @@ -1326,6 +1421,15 @@ mpt_lan_init (void) dprintk((KERN_INFO MYNAM ": assigned context of %d\n", LanCtx)); + if (mpt_reset_register(LanCtx, mpt_lan_ioc_reset) == 0) { + dprintk((KERN_INFO MYNAM ": Registered for IOC reset notifications\n")); + } else { + printk(KERN_ERR MYNAM ": Eieee! unable to register a reset " + "handler with mptbase! The world is at an end! " + "Everything is fading to black! Goodbye.\n"); + return -EBUSY; + } + for (j = 0; j < MPT_MAX_ADAPTERS; j++) { mpt_landev[j] = NULL; } @@ -1333,14 +1437,14 @@ mpt_lan_init (void) curadapter = mpt_adapter_find_first(); while (curadapter != NULL) { - for (i = 0; i < curadapter->facts0.NumberOfPorts; i++) { + for (i = 0; i < curadapter->facts.NumberOfPorts; i++) { printk (KERN_INFO MYNAM ": %s: PortNum=%x, ProtocolFlags=%02Xh (%c%c%c%c)\n", curadapter->name, - curadapter->pfacts0.PortNumber, - curadapter->pfacts0.ProtocolFlags, - MPT_PROTOCOL_FLAGS_c_c_c_c(curadapter->pfacts0.ProtocolFlags)); + curadapter->pfacts[i].PortNumber, + curadapter->pfacts[i].ProtocolFlags, + MPT_PROTOCOL_FLAGS_c_c_c_c(curadapter->pfacts[i].ProtocolFlags)); - if (curadapter->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { + if (curadapter->pfacts[i].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) { dev = mpt_register_lan_device (curadapter, i); if (dev != NULL) { printk (KERN_INFO MYNAM ": %s: Fusion MPT LAN device registered as '%s'\n", @@ -1361,7 +1465,7 @@ mpt_lan_init (void) } else { printk (KERN_ERR MYNAM ": %s: Unable to register port%d as a LAN device\n", curadapter->name, - curadapter->pfacts0.PortNumber); + curadapter->pfacts[i].PortNumber); } } else { printk (KERN_INFO MYNAM ": %s: Hmmm... LAN protocol seems to be disabled on this adapter port!\n", @@ -1379,6 +1483,8 @@ void __init mpt_lan_exit(void) { int i; + mpt_reset_deregister(LanCtx); + for (i = 0; mpt_landev[i] != NULL; i++) { struct net_device *dev = mpt_landev[i]; @@ -1411,6 +1517,7 @@ mpt_lan_type_trans(struct sk_buff *skb, struct net_device *dev) { struct mpt_lan_ohdr *fch = (struct mpt_lan_ohdr *)skb->data; struct fcllc *fcllc; + u16 source_naa = fch->stype, found = 0; skb->mac.raw = skb->data; skb_pull(skb, sizeof(struct mpt_lan_ohdr)); @@ -1444,11 +1551,80 @@ mpt_lan_type_trans(struct sk_buff *skb, struct net_device *dev) } } + fcllc = (struct fcllc *)skb->data; + + /* Workaround for QLogic not following RFC 2625 in regards to the NAA + value. */ + + if ((source_naa & 0xF000) == 0) + source_naa = swab16(source_naa); + + if (fcllc->ethertype == htons(ETH_P_ARP)) + dprintk ((KERN_INFO "mptlan/type_trans: got arp req/rep w/ naa of " + "%04x.\n", source_naa)); + + if ((fcllc->ethertype == htons(ETH_P_ARP)) && + ((source_naa >> 12) != MPT_LAN_NAA_RFC2625)){ + struct NAA_Hosed *nh, *prevnh; + int i; + + dprintk ((KERN_INFO "mptlan/type_trans: ARP Req/Rep from " + "system with non-RFC 2625 NAA value (%04x).\n", + source_naa)); + + write_lock_irq(&bad_naa_lock); + for (prevnh = nh = mpt_bad_naa; nh != NULL; + prevnh=nh, nh=nh->next) { + if ((nh->ieee[0] == fch->saddr[0]) && + (nh->ieee[1] == fch->saddr[1]) && + (nh->ieee[2] == fch->saddr[2]) && + (nh->ieee[3] == fch->saddr[3]) && + (nh->ieee[4] == fch->saddr[4]) && + (nh->ieee[5] == fch->saddr[5])) { + found = 1; + dprintk ((KERN_INFO "mptlan/type_trans: ARP Re" + "q/Rep w/ bad NAA from system already" + " in DB.\n")); + break; + } + } + + if ((!found) && (nh == NULL)) { + + nh = kmalloc(sizeof(struct NAA_Hosed), GFP_KERNEL); + dprintk ((KERN_INFO "mptlan/type_trans: ARP Req/Rep w/" + " bad NAA from system not yet in DB.\n")); + + if (nh != NULL) { + nh->next = NULL; + if (!mpt_bad_naa) + mpt_bad_naa = nh; + if (prevnh) + prevnh->next = nh; + + nh->NAA = source_naa; /* Set the S_NAA value. */ + for (i = 0; i < FC_ALEN; i++) + nh->ieee[i] = fch->saddr[i]; + dprintk ((KERN_INFO "Got ARP from %02x:%02x:%02x:%02x:" + "%02x:%02x with non-compliant S_NAA value.\n", + fch->saddr[0], fch->saddr[1], fch->saddr[2], + fch->saddr[3], fch->saddr[4],fch->saddr[5])); + } else { + printk (KERN_ERR "mptlan/type_trans: Unable to" + " kmalloc a NAA_Hosed struct.\n"); + } + } else if (!found) { + printk (KERN_ERR "mptlan/type_trans: found not" + " set, but nh isn't null. Evil " + "funkiness abounds.\n"); + } + write_unlock_irq(&bad_naa_lock); + } + + /* Strip the SNAP header from ARP packets since we don't * pass them through to the 802.2/SNAP layers. */ - fcllc = (struct fcllc *)skb->data; - if (fcllc->dsap == EXTENDED_SAP && (fcllc->ethertype == htons(ETH_P_IP) || fcllc->ethertype == htons(ETH_P_ARP))) { diff --git a/drivers/message/fusion/mptlan.h b/drivers/message/fusion/mptlan.h index c32cfa01f2c1..10f2976dff64 100644 --- a/drivers/message/fusion/mptlan.h +++ b/drivers/message/fusion/mptlan.h @@ -51,6 +51,9 @@ MODULE_DESCRIPTION(LANAME); #define MPT_LAN_MAX_MTU 65280 /* RFC2625 */ #define MPT_LAN_MTU 16128 /* be nice to slab allocator */ +#define MPT_LAN_NAA_RFC2625 0x1 +#define MPT_LAN_NAA_QLOGIC 0x2 + /* MPT LAN Reset and Suspend Resource Flags Defines */ #define MPT_LAN_RESOURCE_FLAG_RETURN_POSTED_BUCKETS 0x01 diff --git a/drivers/message/fusion/mptscsih.c b/drivers/message/fusion/mptscsih.c index d1a21e1e0c43..74a76bc75c31 100644 --- a/drivers/message/fusion/mptscsih.c +++ b/drivers/message/fusion/mptscsih.c @@ -19,7 +19,7 @@ * Original author: Steven J. Ralston * (mailto:Steve.Ralston@lsil.com) * - * $Id: mptscsih.c,v 1.24 2001/03/22 08:45:08 sralston Exp $ + * $Id: mptscsih.c,v 1.29 2001/06/18 18:59:05 sralston Exp $ */ /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /* @@ -95,7 +95,6 @@ typedef struct _MPT_SCSI_HOST { u8 *SgHunks; dma_addr_t SgHunksDMA; u32 qtag_tick; - FCDEV_TRACKER TargetsQ; } MPT_SCSI_HOST; typedef struct _MPT_SCSI_DEV { @@ -119,6 +118,7 @@ static int mptscsih_io_direction(Scsi_Cmnd *cmd); static void copy_sense_data(Scsi_Cmnd *sc, MPT_SCSI_HOST *hd, MPT_FRAME_HDR *mf, SCSIIOReply_t *pScsiReply); static u32 SCPNT_TO_MSGCTX(Scsi_Cmnd *sc); +static int mptscsih_ioc_reset(MPT_ADAPTER *ioc, int post_reset); static int mptscsih_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply); @@ -205,7 +205,7 @@ mptscsih_io_done(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *r) dprintk((KERN_INFO MYNAM ": *NEW* SCSI device (%d:%d:%d)!\n", sc->device->id, sc->device->lun, sc->device->channel)); if ((sc->device->hostdata = kmalloc(sizeof(MPT_SCSI_DEV), GFP_ATOMIC)) == NULL) { - printk(KERN_ERR MYNAM ": ERROR: kmalloc(%d) FAILED!\n", (int)sizeof(MPT_SCSI_DEV)); + printk(KERN_ERR MYNAM ": ERROR - kmalloc(%d) FAILED!\n", (int)sizeof(MPT_SCSI_DEV)); } else { memset(sc->device->hostdata, 0, sizeof(MPT_SCSI_DEV)); mpt_sdev = (MPT_SCSI_DEV *) sc->device->hostdata; @@ -555,8 +555,14 @@ mptscsih_detect(Scsi_Host_Template *tpnt) if (! BeenHereDoneThat++) { show_mptmod_ver(my_NAME, my_VERSION); - ScsiDoneCtx = mpt_register(mptscsih_io_done, MPTSCSIH_DRIVER); - ScsiTaskCtx = mpt_register(mptscsih_taskmgmt_complete, MPTSCSIH_DRIVER); + if ((ScsiDoneCtx = mpt_register(mptscsih_io_done, MPTSCSIH_DRIVER)) <= 0) { + printk(KERN_ERR MYNAM ": Failed to register callback1 with MPT base driver\n"); + return mpt_scsi_hosts; + } + if ((ScsiTaskCtx = mpt_register(mptscsih_taskmgmt_complete, MPTSCSIH_DRIVER)) <= 0) { + printk(KERN_ERR MYNAM ": Failed to register callback2 with MPT base driver\n"); + return mpt_scsi_hosts; + } #ifndef MPT_SCSI_USE_NEW_EH Q_INIT(&mpt_scsih_taskQ, MPT_FRAME_HDR); @@ -568,6 +574,12 @@ mptscsih_detect(Scsi_Host_Template *tpnt) } else { /* FIXME! */ } + + if (mpt_reset_register(ScsiDoneCtx, mptscsih_ioc_reset) == 0) { + dprintk((KERN_INFO MYNAM ": Registered for IOC reset notifications\n")); + } else { + /* FIXME! */ + } } dprintk((KERN_INFO MYNAM ": mpt_scsih_detect()\n")); @@ -582,7 +594,7 @@ mptscsih_detect(Scsi_Host_Template *tpnt) * Added sanity check on SCSI Initiator-mode enabled * for this MPT adapter. */ - if (!(this->pfacts0.ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR)) { + if (!(this->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR)) { printk(KERN_ERR MYNAM ": Skipping %s because SCSI Initiator mode is NOT enabled!\n", this->name); this = mpt_adapter_find_next(this); @@ -612,10 +624,18 @@ mptscsih_detect(Scsi_Host_Template *tpnt) /* Yikes! This is important! * Otherwise, by default, linux only scans target IDs 0-7! + * + * BUG FIX! 20010618 -sralston & pdelaney + * FC919 testing was encountering "duplicate" FC devices, + * as it turns out because the 919 was returning 512 + * for PortFacts.MaxDevices, causing a wraparound effect + * in SCSI IO requests. So instead of using: + * sh->max_id = this->pfacts[0].MaxDevices - 1 + * we'll use a definitive max here. */ - sh->max_id = this->pfacts0.MaxDevices - 1; + sh->max_id = MPT_MAX_FC_DEVICES; - sh->this_id = this->pfacts0.PortSCSIID; + sh->this_id = this->pfacts[0].PortSCSIID; restore_flags(flags); @@ -730,6 +750,9 @@ mptscsih_release(struct Scsi_Host *host) #if 0 mptscsih_flush_pending(); #endif + mpt_reset_deregister(ScsiDoneCtx); + dprintk((KERN_INFO MYNAM ": Deregistered for IOC reset notifications\n")); + mpt_event_deregister(ScsiDoneCtx); dprintk((KERN_INFO MYNAM ": Deregistered for IOC event notifications\n")); @@ -765,7 +788,7 @@ mptscsih_info(struct Scsi_Host *SChost) h = (MPT_SCSI_HOST *)SChost->hostdata; info_kbuf[0] = '\0'; - mpt_print_ioc_summary(h->ioc, info_kbuf, &size, 0); + mpt_print_ioc_summary(h->ioc, info_kbuf, &size, 0, 0); info_kbuf[size-1] = '\0'; return info_kbuf; @@ -1235,7 +1258,6 @@ mptscsih_qcmd(Scsi_Cmnd *SCpnt, void (*done)(Scsi_Cmnd *)) dprintk((KERN_INFO MYNAM ": Queue depth now %d.\n", max_qd)); } - mb(); dmfprintk((KERN_INFO MYNAM ": Issued SCSI cmd (%p)\n", SCpnt)); return 0; @@ -1265,6 +1287,7 @@ mptscsih_abort(Scsi_Cmnd * SCpnt) u32 *msg; u32 ctx2abort; int i; + unsigned long flags; printk(KERN_WARNING MYNAM ": Attempting _ABORT SCSI IO (=%p)\n", SCpnt); printk(KERN_WARNING MYNAM ": IOs outstanding = %d\n", atomic_read(&queue_depth)); @@ -1309,41 +1332,59 @@ mptscsih_abort(Scsi_Cmnd * SCpnt) * the controller, so it does not matter. -DaveM */ ctx2abort = SCPNT_TO_MSGCTX(SCpnt); - dprintk((KERN_INFO MYNAM ":DbG: ctx2abort = %08x\n", ctx2abort)); - pScsiTm->TaskMsgContext = ctx2abort; - - wmb(); + if (ctx2abort == -1) { + printk(KERN_ERR MYNAM ": ERROR - ScsiLookup fail(#2) for SCpnt=%p\n", SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + } else { + dprintk((KERN_INFO MYNAM ":DbG: ctx2abort = %08x\n", ctx2abort)); + pScsiTm->TaskMsgContext = ctx2abort; -/* MPI v0.10 requires SCSITaskMgmt requests be sent via Doorbell/handshake - mpt_put_msg_frame(hd->ioc->id, mf); -*/ -/* FIXME! Check return status! */ - (void) mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, sizeof(SCSITaskMgmt_t), msg); - wmb(); + /* MPI v0.10 requires SCSITaskMgmt requests be sent via Doorbell/handshake + mpt_put_msg_frame(hd->ioc->id, mf); + */ + if ((i = mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, + sizeof(SCSITaskMgmt_t), msg)) + != 0) { + printk(KERN_WARNING MYNAM + ": WARNING[2] - IOC error (%d) processing TaskMgmt request (mf=%p:sc=%p)\n", + i, mf, SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + } + } - return SUCCESS; + //return SUCCESS; + return FAILED; } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /** - * mptscsih_bus_reset - Perform a SCSI BUS_RESET! new_eh variant + * mptscsih_dev_reset - Perform a SCSI TARGET_RESET! new_eh variant * @SCpnt: Pointer to Scsi_Cmnd structure, IO which reset is due to * - * (linux Scsi_Host_Template.eh_bus_reset_handler routine) + * (linux Scsi_Host_Template.eh_dev_reset_handler routine) * * Returns SUCCESS or FAILED. */ int -mptscsih_bus_reset(Scsi_Cmnd * SCpnt) +mptscsih_dev_reset(Scsi_Cmnd * SCpnt) { MPT_FRAME_HDR *mf; SCSITaskMgmt_t *pScsiTm; MPT_SCSI_HOST *hd; u32 *msg; int i; + unsigned long flags; - printk(KERN_WARNING MYNAM ": Attempting _BUS_RESET (%p)\n", SCpnt); + printk(KERN_WARNING MYNAM ": Attempting _TARGET_RESET (%p)\n", SCpnt); printk(KERN_WARNING MYNAM ": IOs outstanding = %d\n", atomic_read(&queue_depth)); hd = (MPT_SCSI_HOST *) SCpnt->host->hostdata; @@ -1356,7 +1397,7 @@ mptscsih_bus_reset(Scsi_Cmnd * SCpnt) } pScsiTm = (SCSITaskMgmt_t *) mf; - msg = (u32 *) mf; + msg = (u32*)mf; pScsiTm->TargetID = SCpnt->target; pScsiTm->Bus = hd->port; @@ -1364,10 +1405,11 @@ mptscsih_bus_reset(Scsi_Cmnd * SCpnt) pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT; pScsiTm->Reserved = 0; - pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS; + pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET; pScsiTm->Reserved1 = 0; pScsiTm->MsgFlags = 0; + /* _TARGET_RESET goes to LUN 0 always! */ for (i = 0; i < 8; i++) pScsiTm->LUN[i] = 0; @@ -1377,38 +1419,47 @@ mptscsih_bus_reset(Scsi_Cmnd * SCpnt) pScsiTm->TaskMsgContext = cpu_to_le32(0); - wmb(); - /* MPI v0.10 requires SCSITaskMgmt requests be sent via Doorbell/handshake mpt_put_msg_frame(hd->ioc->id, mf); */ /* FIXME! Check return status! */ - (void) mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, sizeof(SCSITaskMgmt_t), msg); - - wmb(); + if ((i = mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, + sizeof(SCSITaskMgmt_t), msg)) + != 0) { + printk(KERN_WARNING MYNAM + ": WARNING[3] - IOC error (%d) processing TaskMgmt request (mf=%p:sc=%p)\n", + i, mf, SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + } - return SUCCESS; + //return SUCCESS; + return FAILED; } /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ /** - * mptscsih_dev_reset - Perform a SCSI TARGET_RESET! new_eh variant + * mptscsih_bus_reset - Perform a SCSI BUS_RESET! new_eh variant * @SCpnt: Pointer to Scsi_Cmnd structure, IO which reset is due to * - * (linux Scsi_Host_Template.eh_dev_reset_handler routine) + * (linux Scsi_Host_Template.eh_bus_reset_handler routine) * * Returns SUCCESS or FAILED. */ int -mptscsih_dev_reset(Scsi_Cmnd * SCpnt) +mptscsih_bus_reset(Scsi_Cmnd * SCpnt) { MPT_FRAME_HDR *mf; SCSITaskMgmt_t *pScsiTm; MPT_SCSI_HOST *hd; u32 *msg; int i; + unsigned long flags; - printk(KERN_WARNING MYNAM ": Attempting _TARGET_RESET (%p)\n", SCpnt); + printk(KERN_WARNING MYNAM ": Attempting _BUS_RESET (%p)\n", SCpnt); printk(KERN_WARNING MYNAM ": IOs outstanding = %d\n", atomic_read(&queue_depth)); hd = (MPT_SCSI_HOST *) SCpnt->host->hostdata; @@ -1421,7 +1472,7 @@ mptscsih_dev_reset(Scsi_Cmnd * SCpnt) } pScsiTm = (SCSITaskMgmt_t *) mf; - msg = (u32*)mf; + msg = (u32 *) mf; pScsiTm->TargetID = SCpnt->target; pScsiTm->Bus = hd->port; @@ -1429,11 +1480,10 @@ mptscsih_dev_reset(Scsi_Cmnd * SCpnt) pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT; pScsiTm->Reserved = 0; - pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET; + pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS; pScsiTm->Reserved1 = 0; pScsiTm->MsgFlags = 0; - /* _TARGET_RESET goes to LUN 0 always! */ for (i = 0; i < 8; i++) pScsiTm->LUN[i] = 0; @@ -1443,15 +1493,22 @@ mptscsih_dev_reset(Scsi_Cmnd * SCpnt) pScsiTm->TaskMsgContext = cpu_to_le32(0); - wmb(); - /* MPI v0.10 requires SCSITaskMgmt requests be sent via Doorbell/handshake mpt_put_msg_frame(hd->ioc->id, mf); */ /* FIXME! Check return status! */ - (void) mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, sizeof(SCSITaskMgmt_t), msg); - - wmb(); + if ((i = mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, + sizeof(SCSITaskMgmt_t), msg)) + != 0) { + printk(KERN_WARNING MYNAM + ": WARNING[4] - IOC error (%d) processing TaskMgmt request (mf=%p:sc=%p)\n", + i, mf, SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + } return SUCCESS; } @@ -1646,6 +1703,9 @@ mptscsih_taskmgmt_bh(void *sc) spin_unlock_irqrestore(&mpt_scsih_taskQ_lock, flags); while (1) { + current->state = TASK_INTERRUPTIBLE; + schedule_timeout(HZ/4); + /* * We MUST remove item from taskQ *before* we format the * frame as a SCSITaskMgmt request and send it down to the IOC. @@ -1664,9 +1724,10 @@ mptscsih_taskmgmt_bh(void *sc) SCpnt = (Scsi_Cmnd*)mf->u.frame.linkage.argp1; if (SCpnt == NULL) { - printk(KERN_ERR MYNAM ": ERROR: TaskMgmt has NULL SCpnt! (%p:%p)\n", mf, SCpnt); + printk(KERN_ERR MYNAM ": ERROR - TaskMgmt has NULL SCpnt! (%p:%p)\n", mf, SCpnt); continue; } + hd = (MPT_SCSI_HOST *) SCpnt->host->hostdata; pScsiTm = (SCSITaskMgmt_t *) mf; for (i = 0; i < 8; i++) { @@ -1674,9 +1735,9 @@ mptscsih_taskmgmt_bh(void *sc) } task_type = mf->u.frame.linkage.arg1; - if (task_type == MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK) - { - printk(KERN_WARNING MYNAM ": Attempting _ABORT SCSI IO! (mf:sc=%p:%p)\n", mf, SCpnt); + if (task_type == MPI_SCSITASKMGMT_TASKTYPE_ABORT_TASK) { + printk(KERN_WARNING MYNAM ": Attempting _ABORT SCSI IO! (mf=%p:sc=%p)\n", + mf, SCpnt); /* Most important! Set TaskMsgContext to SCpnt's MsgContext! * (the IO to be ABORT'd) @@ -1686,11 +1747,20 @@ mptscsih_taskmgmt_bh(void *sc) * the controller, so it does not matter. -DaveM */ ctx2abort = SCPNT_TO_MSGCTX(SCpnt); + if (ctx2abort == -1) { + printk(KERN_ERR MYNAM ": ERROR - ScsiLookup fail(#1) for SCpnt=%p\n", SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + continue; + } pScsiTm->LUN[1] = SCpnt->lun; } else if (task_type == MPI_SCSITASKMGMT_TASKTYPE_RESET_BUS) { - printk(KERN_WARNING MYNAM ": Attempting _BUS_RESET! (against SCSI IO mf:sc=%p:%p)\n", mf, SCpnt); + printk(KERN_WARNING MYNAM ": Attempting _BUS_RESET! (against SCSI IO mf=%p:sc=%p)\n", mf, SCpnt); } #if 0 else if (task_type == MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET) {} @@ -1699,8 +1769,6 @@ mptscsih_taskmgmt_bh(void *sc) printk(KERN_WARNING MYNAM ": IOs outstanding = %d\n", atomic_read(&queue_depth)); - hd = (MPT_SCSI_HOST *) SCpnt->host->hostdata; - pScsiTm->TargetID = SCpnt->target; pScsiTm->Bus = hd->port; pScsiTm->ChainOffset = 0; @@ -1725,15 +1793,22 @@ mptscsih_taskmgmt_bh(void *sc) * mpt_put_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); * SCSITaskMgmt requests MUST be sent ONLY via * Doorbell/handshake now. :-( - * - * FIXME! Check return status! */ - (void) mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, sizeof(SCSITaskMgmt_t), (u32*)mf); - - /* Spin-Wait for TaskMgmt complete!!! */ - while (mpt_scsih_active_taskmgmt_mf != NULL) { - current->state = TASK_INTERRUPTIBLE; - schedule_timeout(HZ/2); + if ((i = mpt_send_handshake_request(ScsiTaskCtx, hd->ioc->id, + sizeof(SCSITaskMgmt_t), (u32*) mf)) + != 0) { + printk(KERN_WARNING MYNAM ": WARNING[1] - IOC error (%d) processing TaskMgmt request (mf=%p:sc=%p)\n", i, mf, SCpnt); + SCpnt->result = DID_SOFT_ERROR << 16; + spin_lock_irqsave(&io_request_lock, flags); + SCpnt->scsi_done(SCpnt); + spin_unlock_irqrestore(&io_request_lock, flags); + mpt_free_msg_frame(ScsiTaskCtx, hd->ioc->id, mf); + } else { + /* Spin-Wait for TaskMgmt complete!!! */ + while (mpt_scsih_active_taskmgmt_mf != NULL) { + current->state = TASK_INTERRUPTIBLE; + schedule_timeout(HZ/4); + } } } @@ -2005,6 +2080,22 @@ SCPNT_TO_MSGCTX(Scsi_Cmnd *sc) /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/ static int +mptscsih_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 int mptscsih_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *pEvReply) { u8 event = le32_to_cpu(pEvReply->Event) & 0xFF; diff --git a/drivers/message/fusion/scsi3.h b/drivers/message/fusion/scsi3.h index fbb4e37154bf..421b6e3667bd 100644 --- a/drivers/message/fusion/scsi3.h +++ b/drivers/message/fusion/scsi3.h @@ -8,7 +8,7 @@ * Written By: Steven J. Ralston (19960517) * (mailto:Steve.Ralston@lsil.com) * - * $Id: scsi3.h,v 1.4 2001/01/06 15:54:25 sralston Exp $ + * $Id: scsi3.h,v 1.5 2001/04/06 14:31:32 sralston Exp $ */ #ifndef SCSI3_H_INCLUDED @@ -64,12 +64,15 @@ #define CMD_WriteVerify 0x2E #define CMD_Verify 0x2F #define CMD_ReadDefectData 0x37 +#define CMD_ReadLong 0x3E #define CMD_LogSelect 0x4C #define CMD_LogSense 0x4D #define CMD_ModeSelect10 0x55 #define CMD_Reserve10 0x56 #define CMD_Release10 0x57 #define CMD_ModeSense10 0x5A +#define CMD_PersistReserveIn 0x5E +#define CMD_PersistReserveOut 0x5F #define CMD_ReportLuns 0xA0 /* |
