Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 03da3098 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
* git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6: (276 commits)
  [SCSI] zfcp: Trigger logging in the FCP channel on qdio error conditions
  [SCSI] zfcp: Introduce experimental support for DIF/DIX
  [SCSI] zfcp: Enable data division support for FCP devices
  [SCSI] zfcp: Prevent access on uninitialized memory.
  [SCSI] zfcp: Post events through FC transport class
  [SCSI] zfcp: Cleanup QDIO attachment and improve processing.
  [SCSI] zfcp: Cleanup function parameters for sbal value.
  [SCSI] zfcp: Use correct width for timer_interval field
  [SCSI] zfcp: Remove SCSI device when removing unit
  [SCSI] zfcp: Use memdup_user and kstrdup
  [SCSI] zfcp: Fix retry after failed "open port" erp action
  [SCSI] zfcp: Fail erp after timeout
  [SCSI] zfcp: Use forced_reopen in terminate_rport_io callback
  [SCSI] zfcp: Register SCSI devices after successful fc_remote_port_add
  [SCSI] zfcp: Do not try "forced close" when port is already closed
  [SCSI] zfcp: Do not unblock rport from REOPEN_PORT_FORCED
  [SCSI] sd: add support for runtime PM
  [SCSI] implement runtime Power Management
  [SCSI] convert to the new PM framework
  [SCSI] Unify SAM_ and SAM_STAT_ macros
  ...
parents 6ba74014 339f4f4e
Loading
Loading
Loading
Loading
+107 −0
Original line number Diff line number Diff line

HPSA - Hewlett Packard Smart Array driver
-----------------------------------------

This file describes the hpsa SCSI driver for HP Smart Array controllers.
The hpsa driver is intended to supplant the cciss driver for newer
Smart Array controllers.  The hpsa driver is a SCSI driver, while the
cciss driver is a "block" driver.  Actually cciss is both a block
driver (for logical drives) AND a SCSI driver (for tape drives). This
"split-brained" design of the cciss driver is a source of excess
complexity and eliminating that complexity is one of the reasons
for hpsa to exist.

Supported devices:
------------------

Smart Array P212
Smart Array P410
Smart Array P410i
Smart Array P411
Smart Array P812
Smart Array P712m
Smart Array P711m
StorageWorks P1210m

Additionally, older Smart Arrays may work with the hpsa driver if the kernel
boot parameter "hpsa_allow_any=1" is specified, however these are not tested
nor supported by HP with this driver.  For older Smart Arrays, the cciss
driver should still be used.

HPSA specific entries in /sys
-----------------------------

  In addition to the generic SCSI attributes available in /sys, hpsa supports
  the following attributes:

  HPSA specific host attributes:
  ------------------------------

  /sys/class/scsi_host/host*/rescan
  /sys/class/scsi_host/host*/firmware_revision

  the host "rescan" attribute is a write only attribute.  Writing to this
  attribute will cause the driver to scan for new, changed, or removed devices
  (e.g. hot-plugged tape drives, or newly configured or deleted logical drives,
  etc.) and notify the SCSI midlayer of any changes detected.  Normally this is
  triggered automatically by HP's Array Configuration Utility (either the GUI or
  command line variety) so for logical drive changes, the user should not
  normally have to use this.  It may be useful when hot plugging devices like
  tape drives, or entire storage boxes containing pre-configured logical drives.

  The "firmware_revision" attribute contains the firmware version of the Smart Array.
  For example:

	root@host:/sys/class/scsi_host/host4# cat firmware_revision
	7.14

  HPSA specific disk attributes:
  ------------------------------

  /sys/class/scsi_disk/c:b:t:l/device/unique_id
  /sys/class/scsi_disk/c:b:t:l/device/raid_level
  /sys/class/scsi_disk/c:b:t:l/device/lunid

  (where c:b:t:l are the controller, bus, target and lun of the device)

  For example:

	root@host:/sys/class/scsi_disk/4:0:0:0/device# cat unique_id
	600508B1001044395355323037570F77
	root@host:/sys/class/scsi_disk/4:0:0:0/device# cat lunid
	0x0000004000000000
	root@host:/sys/class/scsi_disk/4:0:0:0/device# cat raid_level
	RAID 0

HPSA specific ioctls:
---------------------

  For compatibility with applications written for the cciss driver, many, but
  not all of the ioctls supported by the cciss driver are also supported by the
  hpsa driver.  The data structures used by these are described in
  include/linux/cciss_ioctl.h

  CCISS_DEREGDISK
  CCISS_REGNEWDISK
  CCISS_REGNEWD

  The above three ioctls all do exactly the same thing, which is to cause the driver
  to rescan for new devices.  This does exactly the same thing as writing to the
  hpsa specific host "rescan" attribute.

  CCISS_GETPCIINFO

	Returns PCI domain, bus, device and function and "board ID" (PCI subsystem ID).

  CCISS_GETDRIVVER

	Returns driver version in three bytes encoded as:
		(major_version << 16) | (minor_version << 8) | (subminor_version)

  CCISS_PASSTHRU
  CCISS_BIG_PASSTHRU

	Allows "BMIC" and "CISS" commands to be passed through to the Smart Array.
	These are used extensively by the HP Array Configuration Utility, SNMP storage
	agents, etc.  See cciss_vol_status at http://cciss.sf.net for some examples.
+8 −0
Original line number Diff line number Diff line
@@ -2625,6 +2625,14 @@ S: Maintained
F:	Documentation/blockdev/cpqarray.txt
F:	drivers/block/cpqarray.*

HEWLETT-PACKARD SMART ARRAY RAID DRIVER (hpsa)
M:	Stephen M. Cameron <scameron@beardog.cce.hp.com>
L:	iss_storagedev@hp.com
S:	Supported
F:	Documentation/scsi/hpsa.txt
F:	drivers/scsi/hpsa*.[ch]
F:	include/linux/cciss*.h

HEWLETT-PACKARD SMART CISS RAID DRIVER (cciss)
M:	Mike Miller <mike.miller@hp.com>
L:	iss_storagedev@hp.com
+6 −0
Original line number Diff line number Diff line
@@ -84,6 +84,7 @@ struct qdr {

#define QIB_AC_OUTBOUND_PCI_SUPPORTED	0x40
#define QIB_RFLAGS_ENABLE_QEBSM		0x80
#define QIB_RFLAGS_ENABLE_DATA_DIV	0x02

/**
 * struct qib - queue information block (QIB)
@@ -284,6 +285,9 @@ struct slsb {
	u8 val[QDIO_MAX_BUFFERS_PER_Q];
} __attribute__ ((packed, aligned(256)));

#define CHSC_AC2_DATA_DIV_AVAILABLE	0x0010
#define CHSC_AC2_DATA_DIV_ENABLED	0x0002

struct qdio_ssqd_desc {
	u8 flags;
	u8:8;
@@ -332,6 +336,7 @@ typedef void qdio_handler_t(struct ccw_device *, unsigned int, int,
 * @adapter_name: name for the adapter
 * @qib_param_field_format: format for qib_parm_field
 * @qib_param_field: pointer to 128 bytes or NULL, if no param field
 * @qib_rflags: rflags to set
 * @input_slib_elements: pointer to no_input_qs * 128 words of data or NULL
 * @output_slib_elements: pointer to no_output_qs * 128 words of data or NULL
 * @no_input_qs: number of input queues
@@ -348,6 +353,7 @@ struct qdio_initialize {
	unsigned char adapter_name[8];
	unsigned int qib_param_field_format;
	unsigned char *qib_param_field;
	unsigned char qib_rflags;
	unsigned long *input_slib_elements;
	unsigned long *output_slib_elements;
	unsigned int no_input_qs;
+31 −18
Original line number Diff line number Diff line
@@ -115,6 +115,7 @@ MODULE_PARM_DESC(mpt_fwfault_debug, "Enable detection of Firmware fault"
	" and halt Firmware on fault - (default=0)");


static char	MptCallbacksName[MPT_MAX_PROTOCOL_DRIVERS][50];

#ifdef MFCNT
static int mfcounter = 0;
@@ -213,7 +214,7 @@ static int ProcessEventNotification(MPT_ADAPTER *ioc,
static void	mpt_iocstatus_info(MPT_ADAPTER *ioc, u32 ioc_status, MPT_FRAME_HDR *mf);
static void	mpt_fc_log_info(MPT_ADAPTER *ioc, u32 log_info);
static void	mpt_spi_log_info(MPT_ADAPTER *ioc, u32 log_info);
static void	mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info);
static void	mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info , u8 cb_idx);
static int	mpt_read_ioc_pg_3(MPT_ADAPTER *ioc);
static void	mpt_inactive_raid_list_free(MPT_ADAPTER *ioc);

@@ -490,7 +491,7 @@ mpt_reply(MPT_ADAPTER *ioc, u32 pa)
		else if (ioc->bus_type == SPI)
			mpt_spi_log_info(ioc, log_info);
		else if (ioc->bus_type == SAS)
			mpt_sas_log_info(ioc, log_info);
			mpt_sas_log_info(ioc, log_info, cb_idx);
	}

	if (ioc_stat & MPI_IOCSTATUS_MASK)
@@ -644,7 +645,7 @@ mptbase_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply)
 *	considered an error by the caller.
 */
u8
mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass)
mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass, char *func_name)
{
	u8 cb_idx;
	last_drv_idx = MPT_MAX_PROTOCOL_DRIVERS;
@@ -659,6 +660,8 @@ mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass)
			MptDriverClass[cb_idx] = dclass;
			MptEvHandlers[cb_idx] = NULL;
			last_drv_idx = cb_idx;
			memcpy(MptCallbacksName[cb_idx], func_name,
			    strlen(func_name) > 50 ? 50 : strlen(func_name));
			break;
		}
	}
@@ -1632,6 +1635,7 @@ mpt_mapresources(MPT_ADAPTER *ioc)
		} else {
			printk(MYIOC_s_WARN_FMT "no suitable DMA mask for %s\n",
			    ioc->name, pci_name(pdev));
			pci_release_selected_regions(pdev, ioc->bars);
			return r;
		}
	} else {
@@ -1645,6 +1649,7 @@ mpt_mapresources(MPT_ADAPTER *ioc)
		} else {
			printk(MYIOC_s_WARN_FMT "no suitable DMA mask for %s\n",
			    ioc->name, pci_name(pdev));
			pci_release_selected_regions(pdev, ioc->bars);
			return r;
		}
	}
@@ -1675,6 +1680,7 @@ mpt_mapresources(MPT_ADAPTER *ioc)
	if (mem == NULL) {
		printk(MYIOC_s_ERR_FMT ": ERROR - Unable to map adapter"
			" memory!\n", ioc->name);
		pci_release_selected_regions(pdev, ioc->bars);
		return -EINVAL;
	}
	ioc->memmap = mem;
@@ -1770,7 +1776,6 @@ mpt_attach(struct pci_dev *pdev, const struct pci_device_id *id)
	ioc->req_sz = MPT_DEFAULT_FRAME_SIZE;		/* avoid div by zero! */
	ioc->reply_sz = MPT_REPLY_FRAME_SIZE;

	ioc->pcidev = pdev;

	spin_lock_init(&ioc->taskmgmt_lock);
	mutex_init(&ioc->internal_cmds.mutex);
@@ -1913,6 +1918,9 @@ mpt_attach(struct pci_dev *pdev, const struct pci_device_id *id)
		ioc->msi_enable = 0;
		break;
	}

	ioc->fw_events_off = 1;

	if (ioc->errata_flag_1064)
		pci_disable_io_access(pdev);

@@ -2051,7 +2059,6 @@ mpt_detach(struct pci_dev *pdev)

	mpt_adapter_dispose(ioc);

	pci_set_drvdata(pdev, NULL);
}

/**************************************************************************
@@ -5062,8 +5069,9 @@ mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode)
		if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_DID_IOCRESET)
			goto out;
		if (!timeleft) {
			printk(KERN_DEBUG "%s: Issuing Reset from %s!!\n",
			    ioc->name, __func__);
			printk(MYIOC_s_WARN_FMT
			       "Issuing Reset from %s!!, doorbell=0x%08x\n",
			       ioc->name, __func__, mpt_GetIocState(ioc, 0));
			mpt_Soft_Hard_ResetHandler(ioc, CAN_SLEEP);
			mpt_free_msg_frame(ioc, mf);
		}
@@ -6454,8 +6462,9 @@ mpt_config(MPT_ADAPTER *ioc, CONFIGPARMS *pCfg)
	mutex_unlock(&ioc->mptbase_cmds.mutex);
	if (issue_hard_reset) {
		issue_hard_reset = 0;
		printk(MYIOC_s_WARN_FMT "Issuing Reset from %s!!\n",
		    ioc->name, __func__);
		printk(MYIOC_s_WARN_FMT
		       "Issuing Reset from %s!!, doorbell=0x%08x\n",
		       ioc->name, __func__, mpt_GetIocState(ioc, 0));
		if (retry_count == 0) {
			if (mpt_Soft_Hard_ResetHandler(ioc, CAN_SLEEP) != 0)
				retry_count++;
@@ -6971,6 +6980,7 @@ mpt_SoftResetHandler(MPT_ADAPTER *ioc, int sleepFlag)

	spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
	if (ioc->taskmgmt_in_progress) {
		ioc->ioc_reset_in_progress = 0;
		spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
		return -1;
	}
@@ -7144,7 +7154,8 @@ mpt_HardResetHandler(MPT_ADAPTER *ioc, int sleepFlag)
	rc = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_RECOVER, sleepFlag);
	if (rc != 0) {
		printk(KERN_WARNING MYNAM
		    ": WARNING - (%d) Cannot recover %s\n", rc, ioc->name);
		       ": WARNING - (%d) Cannot recover %s, doorbell=0x%08x\n",
		       rc, ioc->name, mpt_GetIocState(ioc, 0));
	} else {
		if (ioc->hard_resets < -1)
			ioc->hard_resets++;
@@ -7997,7 +8008,7 @@ mpt_spi_log_info(MPT_ADAPTER *ioc, u32 log_info)
 *	Refer to lsi/mpi_log_sas.h.
 **/
static void
mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info)
mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info, u8 cb_idx)
{
union loginfo_type {
	u32	loginfo;
@@ -8051,21 +8062,22 @@ union loginfo_type {
	if (sub_code_desc != NULL)
		printk(MYIOC_s_INFO_FMT
			"LogInfo(0x%08x): Originator={%s}, Code={%s},"
			" SubCode={%s}\n",
			" SubCode={%s} cb_idx %s\n",
			ioc->name, log_info, originator_desc, code_desc,
			sub_code_desc);
			sub_code_desc, MptCallbacksName[cb_idx]);
	else if (code_desc != NULL)
		printk(MYIOC_s_INFO_FMT
			"LogInfo(0x%08x): Originator={%s}, Code={%s},"
			" SubCode(0x%04x)\n",
			" SubCode(0x%04x) cb_idx %s\n",
			ioc->name, log_info, originator_desc, code_desc,
			sas_loginfo.dw.subcode);
			sas_loginfo.dw.subcode, MptCallbacksName[cb_idx]);
	else
		printk(MYIOC_s_INFO_FMT
			"LogInfo(0x%08x): Originator={%s}, Code=(0x%02x),"
			" SubCode(0x%04x)\n",
			" SubCode(0x%04x) cb_idx %s\n",
			ioc->name, log_info, originator_desc,
			sas_loginfo.dw.code, sas_loginfo.dw.subcode);
			sas_loginfo.dw.code, sas_loginfo.dw.subcode,
			MptCallbacksName[cb_idx]);
}

/*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
@@ -8430,7 +8442,8 @@ fusion_init(void)
	/*  Register ourselves (mptbase) in order to facilitate
	 *  EventNotification handling.
	 */
	mpt_base_index = mpt_register(mptbase_reply, MPTBASE_DRIVER);
	mpt_base_index = mpt_register(mptbase_reply, MPTBASE_DRIVER,
	    "mptbase_reply");

	/* Register for hard reset handling callbacks.
	 */
+9 −4
Original line number Diff line number Diff line
@@ -76,8 +76,8 @@
#define COPYRIGHT	"Copyright (c) 1999-2008 " MODULEAUTHOR
#endif

#define MPT_LINUX_VERSION_COMMON	"3.04.15"
#define MPT_LINUX_PACKAGE_NAME		"@(#)mptlinux-3.04.15"
#define MPT_LINUX_VERSION_COMMON	"3.04.17"
#define MPT_LINUX_PACKAGE_NAME		"@(#)mptlinux-3.04.17"
#define WHAT_MAGIC_STRING		"@" "(" "#" ")"

#define show_mptmod_ver(s,ver)  \
@@ -396,6 +396,8 @@ typedef struct _VirtTarget {
	u8			 raidVolume;	/* set, if RAID Volume */
	u8			 type;		/* byte 0 of Inquiry data */
	u8			 deleted;	/* target in process of being removed */
	u8			 inDMD;		/* currently in the device
						   removal delay timer */
	u32			 num_luns;
} VirtTarget;

@@ -580,6 +582,7 @@ struct mptfc_rport_info
typedef void (*MPT_ADD_SGE)(void *pAddr, u32 flagslength, dma_addr_t dma_addr);
typedef void (*MPT_ADD_CHAIN)(void *pAddr, u8 next, u16 length,
		dma_addr_t dma_addr);
typedef void (*MPT_SCHEDULE_TARGET_RESET)(void *ioc);

/*
 *  Adapter Structure - pci_dev specific. Maximum: MPT_MAX_ADAPTERS
@@ -601,7 +604,7 @@ typedef struct _MPT_ADAPTER
	u16			 nvdata_version_default;
	int			 debug_level;
	u8			 io_missing_delay;
	u8			 device_missing_delay;
	u16			 device_missing_delay;
	SYSIF_REGS __iomem	*chip;		/* == c8817000 (mmap) */
	SYSIF_REGS __iomem	*pio_chip;	/* Programmed IO (downloadboot) */
	u8			 bus_type;
@@ -738,6 +741,7 @@ typedef struct _MPT_ADAPTER
	int			 taskmgmt_in_progress;
	u8			 taskmgmt_quiesce_io;
	u8			 ioc_reset_in_progress;
	MPT_SCHEDULE_TARGET_RESET schedule_target_reset;
	struct work_struct	 sas_persist_task;

	struct work_struct	 fc_setup_reset_work;
@@ -922,7 +926,8 @@ extern void mpt_detach(struct pci_dev *pdev);
extern int	 mpt_suspend(struct pci_dev *pdev, pm_message_t state);
extern int	 mpt_resume(struct pci_dev *pdev);
#endif
extern u8	 mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass);
extern u8	 mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass,
		char *func_name);
extern void	 mpt_deregister(u8 cb_idx);
extern int	 mpt_event_register(u8 cb_idx, MPT_EVHANDLER ev_cbfunc);
extern void	 mpt_event_deregister(u8 cb_idx);
Loading