Re: [GIT PULL] SCSI updates for the 4.0+ merge window
On 04/16/2015 07:34 PM, James Bottomley wrote: > This is the usual grab bag of driver updates (lpfc, qla2xxx, storvsc, > aacraid, ipr) plus an assortment of minor updates. There's also a major > update to aic1542 which moves the driver into this millenium. > > The patch is available here: > > git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi.git scsi-misc > What about my patch to fixup am53c974 (cf "am53c974: Fix crash during modprobe")? Do I need to resend it? Cheers, Hannes -- Dr. Hannes ReineckezSeries & Storage h...@suse.de +49 911 74053 688 SUSE LINUX GmbH, Maxfeldstr. 5, 90409 Nürnberg GF: F. Imendörffer, J. Smithard, J. Guild, D. Upmanyu, G. Norton HRB 21284 (AG Nürnberg) -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: mvsas panics and dies when attached to a port extender on newer kernels
Tested against main RAID6, 7 disk array, with sas extender and work with out error. Tested against 2X mirror of SSD's, direct attached, and worked with out error. Check was a simple RAID check. "echo check > /sys/block/md126/md/sync_action" Patched against: root@nas:~# uname -a Linux nas 4.0.0 #1 SMP Thu Apr 16 09:05:59 PDT 2015 x86_64 GNU/Linux Many thanks to all involved in helping me debug this. Should this patch be tested by a few other then added to the kernel tree? On Thu, Apr 16, 2015 at 10:31 AM, Adam Talbot wrote: > Oh! Good idea. ;-) > I will test it in 6~8 hours, once the raid check finishes. > > On Thu, Apr 16, 2015 at 10:28 AM, James Bottomley > wrote: >> On Thu, 2015-04-16 at 10:26 -0700, Adam Talbot wrote: >>> Wow, I forgot how long it takes to compile a full kernel. Glad I ran >>> Gentoo for a few years and knew how to compile and apply patches. I >>> will admit I had to dust off some mental cobwebs. >>> >>> Pre-patched 4.0.0 kernel tree: Oops, as expected >>> Patched 4.0.0 kernel tree: IT WORKED! Basic mount, and checking a >>> few files all looks good. I will start a RAID check as that should >>> really push the driver. I will report back tomorrow when it finishes. >> >> Could you also check the direct ATA attachment case to make sure I >> didn't screw that up. The fix is based on a theory about how the driver >> operates rather than any actual documentation. >> >> Thanks, >> >> James >> >> -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: [PATCH v4 42/43] hpsa: add PMC to copyright
> -Original Message- > From: linux-scsi-ow...@vger.kernel.org [mailto:linux-scsi- > ow...@vger.kernel.org] On Behalf Of Don Brace > Sent: Thursday, April 16, 2015 8:51 AM > Subject: [PATCH v4 42/43] hpsa: add PMC to copyright > > need to add PMC to copyright notice and update the Hewlett-Packard > copyright notification. ... > diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c ... > *Disk Array driver for HP Smart Array SAS controllers > - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. > + *Copyright 2014-2015 PMC-Sierra, Inc. > + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, > L.P. ... > diff --git a/drivers/scsi/hpsa.h b/drivers/scsi/hpsa.h ... > *Disk Array driver for HP Smart Array SAS controllers > - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. > + *Copyright 2014-2015 PMC-Sierra, Inc. > + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, > L.P. ... > diff --git a/drivers/scsi/hpsa_cmd.h b/drivers/scsi/hpsa_cmd.h ... > *Disk Array driver for HP Smart Array SAS controllers > - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. > + *Copyright 2014-2015 PMC-Sierra, Inc. > + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, > L.P. ... HP would prefer to not add the word "Portions" there. Also, I don't think the earliest date should change from what was submitted in the first commit edd163687ea5 (Dec 2009), which was "2000, 2009". Maybe use "2000, 2009-2015" based on: * 2000: original earliest claimed date * 2009: date of first inclusion in kernel * 2015: some of the HP-era patches are still trickling out this year. --- Robert Elliott, HP Server Storage N�r��yb�X��ǧv�^�){.n�+{���"�{ay�ʇڙ�,j��f���h���z��w��� ���j:+v���w�j�mzZ+�ݢj"��!�i
Re: [PATCH 6/7] be2iscsi: Logout of FW Boot Session
On 04/16/2015 02:52 PM, Mike Christie wrote: > On 04/17/2015 04:34 AM, John Soni Jose wrote: >> Once be2iscsi driver is loaded and operational close Boot >> session established by FW. >> >> Signed-off-by: John Soni Jose >> Signed-off-by: Jayamohan Kallickal >> --- >> drivers/scsi/be2iscsi/be_cmds.h | 12 ++ >> drivers/scsi/be2iscsi/be_iscsi.c | 12 ++ >> drivers/scsi/be2iscsi/be_main.c |1 + >> drivers/scsi/be2iscsi/be_main.h |2 + >> drivers/scsi/be2iscsi/be_mgmt.c | 70 >> ++ >> drivers/scsi/be2iscsi/be_mgmt.h |3 ++ >> 6 files changed, 100 insertions(+), 0 deletions(-) >> >> diff --git a/drivers/scsi/be2iscsi/be_cmds.h >> b/drivers/scsi/be2iscsi/be_cmds.h >> index d0097a2..0586815 100644 >> --- a/drivers/scsi/be2iscsi/be_cmds.h >> +++ b/drivers/scsi/be2iscsi/be_cmds.h >> @@ -304,6 +304,17 @@ struct mgmt_auth_method_format { >> struct mgmt_chap_format chap; >> } __packed; >> >> +struct be_cmd_req_logout_fw_sess { >> +struct be_cmd_req_hdr hdr; /* dw[4] */ >> +uint32_t session_handle; >> +} __packed; >> + >> +struct be_cmd_resp_logout_fw_sess { >> +struct be_cmd_resp_hdr hdr; /* dw[4] */ >> +#define BEISCSI_MGMT_SESSION_CLOSE 0x20 >> +uint32_t session_status; >> +} __packed; >> + >> struct mgmt_conn_login_options { >> u8 flags; >> u8 header_digest; >> @@ -1136,6 +1147,7 @@ struct be_cmd_get_all_if_id_req { >> #define OPCODE_ISCSI_INI_CFG_GET_HBA_NAME 6 >> #define OPCODE_ISCSI_INI_CFG_SET_HBA_NAME 7 >> #define OPCODE_ISCSI_INI_SESSION_GET_A_SESSION 14 >> +#define OPCODE_ISCSI_INI_SESSION_LOGOUT_TARGET 24 >> #define OPCODE_ISCSI_INI_DRIVER_REOPEN_ALL_SESSIONS 36 >> #define OPCODE_ISCSI_INI_DRIVER_OFFLOAD_SESSION 41 >> #define OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION 42 >> diff --git a/drivers/scsi/be2iscsi/be_iscsi.c >> b/drivers/scsi/be2iscsi/be_iscsi.c >> index 508f017..566d27c 100644 >> --- a/drivers/scsi/be2iscsi/be_iscsi.c >> +++ b/drivers/scsi/be2iscsi/be_iscsi.c >> @@ -998,6 +998,18 @@ int beiscsi_conn_start(struct iscsi_cls_conn *cls_conn) >> beiscsi_set_params_for_offld(beiscsi_conn, ¶ms); >> beiscsi_offload_connection(beiscsi_conn, ¶ms); >> iscsi_conn_start(cls_conn); >> + >> +/* Logout from the FW boot session */ >> +if (phba->fw_boot_state) { >> +int rc; >> + >> +rc = beiscsi_logout_fw_sess(phba, >> +phba->boot_sess.session_handle); >> + >> +if (!rc) >> +phba->fw_boot_state = 0 >> +} >> + >> return 0; >> } > > How do you know the boot session being logged out is the one we are > replacing and logging into at this time? If userspace logged into > sessions out of order and you logged into a non root one first, then > would this kill the session that we might need to access still? Ignore that, I forgot we get the boot info a pci probe time or from the health check. But the, why not just have beiscsi_setup_boot_info log out the session once its done getting the boot info? It just seems odd to have that logout in the middle of the connection startup. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 6/7] be2iscsi: Logout of FW Boot Session
On 04/17/2015 04:34 AM, John Soni Jose wrote: > Once be2iscsi driver is loaded and operational close Boot > session established by FW. > > Signed-off-by: John Soni Jose > Signed-off-by: Jayamohan Kallickal > --- > drivers/scsi/be2iscsi/be_cmds.h | 12 ++ > drivers/scsi/be2iscsi/be_iscsi.c | 12 ++ > drivers/scsi/be2iscsi/be_main.c |1 + > drivers/scsi/be2iscsi/be_main.h |2 + > drivers/scsi/be2iscsi/be_mgmt.c | 70 > ++ > drivers/scsi/be2iscsi/be_mgmt.h |3 ++ > 6 files changed, 100 insertions(+), 0 deletions(-) > > diff --git a/drivers/scsi/be2iscsi/be_cmds.h b/drivers/scsi/be2iscsi/be_cmds.h > index d0097a2..0586815 100644 > --- a/drivers/scsi/be2iscsi/be_cmds.h > +++ b/drivers/scsi/be2iscsi/be_cmds.h > @@ -304,6 +304,17 @@ struct mgmt_auth_method_format { > struct mgmt_chap_format chap; > } __packed; > > +struct be_cmd_req_logout_fw_sess { > + struct be_cmd_req_hdr hdr; /* dw[4] */ > + uint32_t session_handle; > +} __packed; > + > +struct be_cmd_resp_logout_fw_sess { > + struct be_cmd_resp_hdr hdr; /* dw[4] */ > +#define BEISCSI_MGMT_SESSION_CLOSE 0x20 > + uint32_t session_status; > +} __packed; > + > struct mgmt_conn_login_options { > u8 flags; > u8 header_digest; > @@ -1136,6 +1147,7 @@ struct be_cmd_get_all_if_id_req { > #define OPCODE_ISCSI_INI_CFG_GET_HBA_NAME6 > #define OPCODE_ISCSI_INI_CFG_SET_HBA_NAME7 > #define OPCODE_ISCSI_INI_SESSION_GET_A_SESSION 14 > +#define OPCODE_ISCSI_INI_SESSION_LOGOUT_TARGET24 > #define OPCODE_ISCSI_INI_DRIVER_REOPEN_ALL_SESSIONS 36 > #define OPCODE_ISCSI_INI_DRIVER_OFFLOAD_SESSION 41 > #define OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION 42 > diff --git a/drivers/scsi/be2iscsi/be_iscsi.c > b/drivers/scsi/be2iscsi/be_iscsi.c > index 508f017..566d27c 100644 > --- a/drivers/scsi/be2iscsi/be_iscsi.c > +++ b/drivers/scsi/be2iscsi/be_iscsi.c > @@ -998,6 +998,18 @@ int beiscsi_conn_start(struct iscsi_cls_conn *cls_conn) > beiscsi_set_params_for_offld(beiscsi_conn, ¶ms); > beiscsi_offload_connection(beiscsi_conn, ¶ms); > iscsi_conn_start(cls_conn); > + > + /* Logout from the FW boot session */ > + if (phba->fw_boot_state) { > + int rc; > + > + rc = beiscsi_logout_fw_sess(phba, > + phba->boot_sess.session_handle); > + > + if (!rc) > + phba->fw_boot_state = 0; > + } > + > return 0; > } How do you know the boot session being logged out is the one we are replacing and logging into at this time? If userspace logged into sessions out of order and you logged into a non root one first, then would this kill the session that we might need to access still? -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[GIT PULL] SCSI updates for the 4.0+ merge window
This is the usual grab bag of driver updates (lpfc, qla2xxx, storvsc, aacraid, ipr) plus an assortment of minor updates. There's also a major update to aic1542 which moves the driver into this millenium. The patch is available here: git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi.git scsi-misc The Short Changelog is Andrew Vasquez (1): qla2xxx: Add serdes read/write support for ISP27XX Brian King (5): ipr: Driver version 2.6.1 ipr: Re-enable write same ipr: Fix possible error path oops during initialization ipr: Reset in task context ipr: Reboot speed improvements Chad Dupuis (1): qla2xxx: Increase the wait time for firmware to be ready for P3P. Christoph Hellwig (3): scsi: proper state checking and module refcount handling in scsi_device_get sd: don't grab a device references from driver methods scsi: serialize ->rescan against ->remove Geert Uytterhoeven (1): g_NCR5380: Kill compiler warning if builtin Himanshu Madhani (8): qla2xxx: Update driver version to 8.07.00.18-k qla2xxx: Prevent multiple firmware dump collection for ISP27XX. qla2xxx: Disable Interrupt handshake for ISP27XX. qla2xxx: Add debugging info for MBX timeout. qla2xxx: Add udev notification to save fw dump for ISP27XX qla2xxx: Add message for sucessful FW dump collected for ISP27XX. qla2xxx: Fix crash due to wrong casting of reg for ISP27XX. qla2xxx: Fix warnings reported by static checker. James Bottomley (2): change SCSI Maintainer email sd, mmc, virtio_blk, string_helpers: fix block size units James Smart (21): lpfc: Update version to 10.5.0.0 for upstream patch set lpfc: Update copyright to 2015 lpfc: Fix for lun discovery issue with saturn adapter. lpfc: Fix crash in device reset handler. lpfc: Fix OS crash when running loopback test in applications lpfc: Fix internal loopback failure. lpfc: Fix premature release of rpi bit in bitmask lpfc: Initiator sends wrong BBCredit value for either FLOGI or FLOGI_ACC lpfc: Fix null ndlp dereference in target_reset_handler lpfc: Fix FDMI Fabric support in driver for Brocade lpfc: Fix provide host name and OS name in RSNN-NN FC-GS command lpfc: Parse the new 20G, 25G and 40G link speeds in the lpfc driver lpfc: Add support for reporting option_rom_version on newer adapters lpfc: Fix setting of EQ (interrupt) delay Multiplier lpfc: Fix host reset escalation killing all IOs. lpfc: Linux lpfc driver doesn't re-establish the link after a cable pull on LPe12002 lpfc: Fix to handle PLOGI when already logged in lpfc: Add new mbx cmd recognition lpfc: Add Lancer Temperature Event support to the lpfc driver lpfc: Fix the iteration count to match the 30 sec comment in the routine lpfc_pci_function_reset scsi_transport_fc: Add support for 25Gbit speed K. Y. Srinivasan (7): scsi: storvsc: Set the tablesize based on the information given by the host scsi: storvsc: Don't assume that the scatterlist is not chained scsi: storvsc: Fix a bug in copy_from_bounce_buffer() scsi: storvsc: Retrieve information about the capability of the target scsi: storvsc: Always send on the selected outgoing channel scsi: storvsc: Size the queue depth based on the ringbuffer size scsi: storvsc: Increase the ring buffer size Mahesh Rajashekhara (11): aacraid: driver version change aacraid: AIF raw device remove support aacraid: performance improvement changes aacraid: IOCTL fix aacraid: IOP RESET command handling changes aacraid: 240 simple volume support aacraid: vpd page code 0x83 support aacraid: MSI-x support aacraid: 4KB sector support aacraid: IOCTL pass-through command fix aacraid: AIF support for SES device add/remove Michael Opdenacker (1): aic7xxx: replace kmalloc/memset by kzalloc Nicholas Mc Guire (1): ncr5380: Harmonize jiffies conversion with msecs_to_jiffies Nigel Kirkland (1): qla2xxx: Fix beacon blink for ISP27XX. Ondrej Zary (36): aha1542: remove loop from aha1542_outb aha1542: Fix bus reset aha1542: rework locking aha1542: Don't reduce functionality with DEBUG enabled aha1542: Use print_hex_dump_bytes in debug code aha1542: remove DEB macro and simplify debug code aha1542: Use shost_printk instead of printk aha1542: Change aha1542_set_bus_times parameters aha1542: Pass struct Scsi_Host * to functions aha1542: cleanup includes aha1542: remove useless changelog aha1542: fix include guard and remove useless changelog aha1542: Always name Scsi_Host variables sh aha1524: Use struct scsi_cmnd aha1542: clean up cmd variables aha1542: Simplify aha1542_biosparam aha1542: rework configuration parameters aha1542: rewor
Re: mvsas panics and dies when attached to a port extender on newer kernels
Oh! Good idea. ;-) I will test it in 6~8 hours, once the raid check finishes. On Thu, Apr 16, 2015 at 10:28 AM, James Bottomley wrote: > On Thu, 2015-04-16 at 10:26 -0700, Adam Talbot wrote: >> Wow, I forgot how long it takes to compile a full kernel. Glad I ran >> Gentoo for a few years and knew how to compile and apply patches. I >> will admit I had to dust off some mental cobwebs. >> >> Pre-patched 4.0.0 kernel tree: Oops, as expected >> Patched 4.0.0 kernel tree: IT WORKED! Basic mount, and checking a >> few files all looks good. I will start a RAID check as that should >> really push the driver. I will report back tomorrow when it finishes. > > Could you also check the direct ATA attachment case to make sure I > didn't screw that up. The fix is based on a theory about how the driver > operates rather than any actual documentation. > > Thanks, > > James > > -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: mvsas panics and dies when attached to a port extender on newer kernels
On Thu, 2015-04-16 at 10:26 -0700, Adam Talbot wrote: > Wow, I forgot how long it takes to compile a full kernel. Glad I ran > Gentoo for a few years and knew how to compile and apply patches. I > will admit I had to dust off some mental cobwebs. > > Pre-patched 4.0.0 kernel tree: Oops, as expected > Patched 4.0.0 kernel tree: IT WORKED! Basic mount, and checking a > few files all looks good. I will start a RAID check as that should > really push the driver. I will report back tomorrow when it finishes. Could you also check the direct ATA attachment case to make sure I didn't screw that up. The fix is based on a theory about how the driver operates rather than any actual documentation. Thanks, James -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: mvsas panics and dies when attached to a port extender on newer kernels
Wow, I forgot how long it takes to compile a full kernel. Glad I ran Gentoo for a few years and knew how to compile and apply patches. I will admit I had to dust off some mental cobwebs. Pre-patched 4.0.0 kernel tree: Oops, as expected Patched 4.0.0 kernel tree: IT WORKED! Basic mount, and checking a few files all looks good. I will start a RAID check as that should really push the driver. I will report back tomorrow when it finishes. Logs below. [5.072154] scsi host4: mvsas [5.180706] floppy0: no floppy controllers found [5.339613] ata12.00: ATA-8: ST32000542AS, CC35, max UDMA/133 [5.339616] ata10.00: ATA-7: HDS725050KLA360, K2AOAD1A, max UDMA/133 [5.339624] ata10.00: 976773168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.339892] ata11.00: ATA-7: HDS725050KLA360, K2AOAD1A, max UDMA/133 [5.339893] ata11.00: 976773168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.340146] ata13.00: ATA-8: ST2000DL003-9VT166, CC32, max UDMA/133 [5.340147] ata13.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.341015] ata10.00: configured for UDMA/133 [5.341344] ata11.00: configured for UDMA/133 [5.341406] ata13.00: configured for UDMA/133 [5.373207] ata5.00: ATA-8: WDC WD20EADS-11R6B1, 80.00A80, max UDMA/133 [5.373208] ata5.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.374223] ata8.00: ATA-8: WDC WD20EADS-42R6B0, 02.00A02, max UDMA/133 [5.374224] ata8.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.379766] ata5.00: configured for UDMA/133 [5.380106] ata8.00: configured for UDMA/133 [5.397396] ata7.00: ATA-8: WDC WD20EARS-00S8B1, 80.00A80, max UDMA/133 [5.397396] ata7.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.403539] ata7.00: configured for UDMA/133 [5.451846] ata12.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.460457] ata12.00: configured for UDMA/133 [5.738535] ata6.00: ATA-8: WDC WD20EADS-11R6B1, 80.00A80, max UDMA/133 [5.745214] ata6.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.745267] ata9.00: ATA-8: WDC WD20EADS-42R6B0, 02.00A02, max UDMA/133 [5.745268] ata9.00: 3907029168 sectors, multi 0: LBA48 NCQ (depth 31/32) [5.765626] ata9.00: configured for UDMA/133 [5.771347] ata6.00: configured for UDMA/133 [5.784708] scsi 4:0:0:0: Direct-Access ATA WDC WD20EADS-11R 0A80 PQ: 0 ANSI: 5 [5.793137] scsi 4:0:1:0: Direct-Access ATA WDC WD20EADS-11R 0A80 PQ: 0 ANSI: 5 [5.801560] scsi 4:0:2:0: Direct-Access ATA WDC WD20EARS-00S 0A80 PQ: 0 ANSI: 5 [5.809982] scsi 4:0:3:0: Direct-Access ATA WDC WD20EADS-42R 0A02 PQ: 0 ANSI: 5 [5.818404] scsi 4:0:4:0: Direct-Access ATA WDC WD20EADS-42R 0A02 PQ: 0 ANSI: 5 [5.826816] scsi 4:0:5:0: Direct-Access ATA HDS725050KLA360 AD1A PQ: 0 ANSI: 5 [5.835171] scsi 4:0:6:0: Direct-Access ATA HDS725050KLA360 AD1A PQ: 0 ANSI: 5 [5.843526] scsi 4:0:7:0: Direct-Access ATA ST32000542AS CC35 PQ: 0 ANSI: 5 [5.851928] scsi 4:0:8:0: Direct-Access ATA ST2000DL003-9VT1 CC32 PQ: 0 ANSI: 5 [5.862669] scsi 4:0:9:0: Enclosure LSILOGIC SASX28 A.1 7014 PQ: 0 ANSI: 3 [6.140482] scsi 5:0:0:0: Direct-Access Generic USB EDC 1.00 PQ: 0 ANSI: 2 [6.148955] sd 5:0:0:0: Attached scsi generic sg2 type 0 [6.149610] sd 5:0:0:0: [sdc] 2007040 512-byte logical blocks: (1.02 GB/980 MiB) [6.150218] sd 5:0:0:0: [sdc] Write Protect is off [6.150840] sd 5:0:0:0: [sdc] No Caching mode page found [6.150841] sd 5:0:0:0: [sdc] Assuming drive cache: write through [6.153552] sdc: sdc1 [6.156225] sd 5:0:0:0: [sdc] Attached SCSI disk [6.185605] sd 4:0:0:0: [sdd] 3907029168 512-byte logical blocks: (2.00 TB/1.81 TiB) [6.185633] sd 4:0:0:0: Attached scsi generic sg3 type 0 [6.185799] sd 4:0:1:0: Attached scsi generic sg4 type 0 [6.185801] sd 4:0:1:0: [sde] 3907029168 512-byte logical blocks: (2.00 TB/1.81 TiB) [6.185802] sd 4:0:1:0: [sde] 4096-byte physical blocks [6.185837] sd 4:0:1:0: [sde] Write Protect is off [6.185848] sd 4:0:1:0: [sde] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA [6.185978] sd 4:0:2:0: [sdf] 3907029168 512-byte logical blocks: (2.00 TB/1.81 TiB) [6.185986] sd 4:0:2:0: Attached scsi generic sg5 type 0 [6.186059] sd 4:0:2:0: [sdf] Write Protect is off [6.186148] sd 4:0:3:0: [sdg] 3907029168 512-byte logical blocks: (2.00 TB/1.81 TiB) [6.186149] sd 4:0:2:0: [sdf] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA [6.186163] sd 4:0:3:0: Attached scsi generic sg6 type 0 [6.186188] sde: sde1 [6.186205] sd 4:0:3:0: [sdg] Write Protect is off [6.186234] sd 4:0:3:0: [sdg] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA [6.186395] sd 4:0:4:0: [sdh] 3907029168 512-byte logical blocks: (2.00 TB/1.81 TiB) [6.186417] sd 4:0:1:0: [sde] Attached S
[PATCH 5/7] be2iscsi : Update the copyright year
Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be.h |2 +- drivers/scsi/be2iscsi/be_cmds.c |2 +- drivers/scsi/be2iscsi/be_cmds.h |2 +- drivers/scsi/be2iscsi/be_iscsi.c |2 +- drivers/scsi/be2iscsi/be_iscsi.h |2 +- drivers/scsi/be2iscsi/be_main.c |2 +- drivers/scsi/be2iscsi/be_main.h |2 +- drivers/scsi/be2iscsi/be_mgmt.c |2 +- drivers/scsi/be2iscsi/be_mgmt.h |2 +- 9 files changed, 9 insertions(+), 9 deletions(-) diff --git a/drivers/scsi/be2iscsi/be.h b/drivers/scsi/be2iscsi/be.h index 81e83a6..273e6f4 100644 --- a/drivers/scsi/be2iscsi/be.h +++ b/drivers/scsi/be2iscsi/be.h @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_cmds.c b/drivers/scsi/be2iscsi/be_cmds.c index 8e16c49..ff69493 100644 --- a/drivers/scsi/be2iscsi/be_cmds.c +++ b/drivers/scsi/be2iscsi/be_cmds.c @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_cmds.h b/drivers/scsi/be2iscsi/be_cmds.h index 9889743..d0097a2 100644 --- a/drivers/scsi/be2iscsi/be_cmds.h +++ b/drivers/scsi/be2iscsi/be_cmds.h @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_iscsi.c b/drivers/scsi/be2iscsi/be_iscsi.c index b7391a3..508f017 100644 --- a/drivers/scsi/be2iscsi/be_iscsi.c +++ b/drivers/scsi/be2iscsi/be_iscsi.c @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_iscsi.h b/drivers/scsi/be2iscsi/be_iscsi.h index e0b3b2d..096c928 100644 --- a/drivers/scsi/be2iscsi/be_iscsi.h +++ b/drivers/scsi/be2iscsi/be_iscsi.h @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index 1fbbece..b700fad 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_main.h b/drivers/scsi/be2iscsi/be_main.h index 0aa0cb3..3ddde6f 100644 --- a/drivers/scsi/be2iscsi/be_main.h +++ b/drivers/scsi/be2iscsi/be_main.h @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_mgmt.c b/drivers/scsi/be2iscsi/be_mgmt.c index 681d4e8..78f56a6 100644 --- a/drivers/scsi/be2iscsi/be_mgmt.c +++ b/drivers/scsi/be2iscsi/be_mgmt.c @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/be2iscsi/be_mgmt.h b/drivers/scsi/be2iscsi/be_mgmt.h index bd81446..95fd99b 100644 --- a/drivers/scsi/be2iscsi/be_mgmt.h +++ b/drivers/scsi/be2iscsi/be_mgmt.h @@ -1,5 +1,5 @@ /** - * Copyright (C) 2005 - 2014 Emulex + * Copyright (C) 2005 - 2015 Emulex * All rights reserved. * * This program is free software; you can redistribute it and/or -- 1.7.1 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 7/7] be2iscsi : Bump the driver version
Bump the driver version Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_main.h |2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_main.h b/drivers/scsi/be2iscsi/be_main.h index 8aff7cd..f375f85 100644 --- a/drivers/scsi/be2iscsi/be_main.h +++ b/drivers/scsi/be2iscsi/be_main.h @@ -36,7 +36,7 @@ #include #define DRV_NAME "be2iscsi" -#define BUILD_STR "10.4.114.0" +#define BUILD_STR "10.6.0.0" #define BE_NAME"Emulex OneConnect" \ "Open-iSCSI Driver version" BUILD_STR #define DRV_DESC BE_NAME " " "Driver" -- 1.7.1 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 4/7] be2iscsi : Fix memory check before unmapping.
Check DMA memory before it is unmapped. Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_main.c | 10 +++--- 1 files changed, 7 insertions(+), 3 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index dca3a55..1fbbece 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -1368,8 +1368,10 @@ be_complete_io(struct beiscsi_conn *beiscsi_conn, if (io_task->cmd_bhs->iscsi_hdr.flags & ISCSI_FLAG_CMD_READ) conn->rxdata_octets += resid; unmap: - scsi_dma_unmap(io_task->scsi_cmnd); - io_task->scsi_cmnd = NULL; + if (io_task->scsi_cmnd) { + scsi_dma_unmap(io_task->scsi_cmnd); + io_task->scsi_cmnd = NULL; + } iscsi_complete_scsi_task(task, exp_cmdsn, max_cmdsn); } @@ -4609,11 +4611,13 @@ beiscsi_free_mgmt_task_handles(struct beiscsi_conn *beiscsi_conn, spin_unlock_bh(&phba->mgmt_sgl_lock); } - if (io_task->mtask_addr) + if (io_task->mtask_addr) { pci_unmap_single(phba->pcidev, io_task->mtask_addr, io_task->mtask_data_count, PCI_DMA_TODEVICE); + io_task->mtask_addr = 0; + } } /** -- 1.7.1 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/7] be2iscsi : Fix the PCI request region reserving.
Reserve device PCI I/O and Memory resources. Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_main.c | 22 ++ 1 files changed, 18 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index 66ea88c..4d95596 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -668,14 +668,20 @@ static int beiscsi_enable_pci(struct pci_dev *pcidev) return ret; } + ret = pci_request_regions(pcidev, DRV_NAME); + if (ret) { + dev_err(&pcidev->dev, + "beiscsi_enable_pci - request region failed\n"); + goto pci_dev_disable; + } + pci_set_master(pcidev); ret = pci_set_dma_mask(pcidev, DMA_BIT_MASK(64)); if (ret) { ret = pci_set_dma_mask(pcidev, DMA_BIT_MASK(32)); if (ret) { dev_err(&pcidev->dev, "Could not set PCI DMA Mask\n"); - pci_disable_device(pcidev); - return ret; + goto pci_region_release; } else { ret = pci_set_consistent_dma_mask(pcidev, DMA_BIT_MASK(32)); @@ -684,11 +690,17 @@ static int beiscsi_enable_pci(struct pci_dev *pcidev) ret = pci_set_consistent_dma_mask(pcidev, DMA_BIT_MASK(64)); if (ret) { dev_err(&pcidev->dev, "Could not set PCI DMA Mask\n"); - pci_disable_device(pcidev); - return ret; + goto pci_region_release; } } return 0; + +pci_region_release: + pci_release_regions(pcidev); +pci_dev_disable: + pci_disable_device(pcidev); + + return ret; } static int be_ctrl_init(struct beiscsi_hba *phba, struct pci_dev *pdev) @@ -5275,6 +5287,7 @@ static void beiscsi_remove(struct pci_dev *pcidev) iscsi_host_free(phba->shost); pci_disable_pcie_error_reporting(pcidev); pci_set_drvdata(pcidev, NULL); + pci_release_regions(pcidev); pci_disable_device(pcidev); } @@ -5755,6 +5768,7 @@ hba_free: iscsi_host_free(phba->shost); pci_set_drvdata(pcidev, NULL); disable_pci: + pci_release_regions(pcidev); pci_disable_device(pcidev); return ret; } -- 1.7.1 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 0/7] be2iscsi driver update to 10.6.0.0
The patchset updates be2iscsi driver to 10.6.0.0 version. These patches are generated aganist scsi for-next branch John Soni Jose (7): be2iscsi : Fix the retry count for boot targets be2iscsi : Fix the PCI request region reserving. be2iscsi : Fix memory leak in the unload path be2iscsi : Fix memory check before unmapping. be2iscsi : Update the copyright year be2iscsi: Logout of FW Boot Session be2iscsi : Bump the driver version drivers/scsi/be2iscsi/be.h |2 +- drivers/scsi/be2iscsi/be_cmds.c |6 ++- drivers/scsi/be2iscsi/be_cmds.h | 14 ++- drivers/scsi/be2iscsi/be_iscsi.c | 14 ++- drivers/scsi/be2iscsi/be_iscsi.h |2 +- drivers/scsi/be2iscsi/be_main.c | 76 +- drivers/scsi/be2iscsi/be_main.h | 10 - drivers/scsi/be2iscsi/be_mgmt.c | 72 +++- drivers/scsi/be2iscsi/be_mgmt.h |5 ++- 9 files changed, 175 insertions(+), 26 deletions(-) -- 1.7.9.5 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 6/7] be2iscsi: Logout of FW Boot Session
Once be2iscsi driver is loaded and operational close Boot session established by FW. Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_cmds.h | 12 ++ drivers/scsi/be2iscsi/be_iscsi.c | 12 ++ drivers/scsi/be2iscsi/be_main.c |1 + drivers/scsi/be2iscsi/be_main.h |2 + drivers/scsi/be2iscsi/be_mgmt.c | 70 ++ drivers/scsi/be2iscsi/be_mgmt.h |3 ++ 6 files changed, 100 insertions(+), 0 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_cmds.h b/drivers/scsi/be2iscsi/be_cmds.h index d0097a2..0586815 100644 --- a/drivers/scsi/be2iscsi/be_cmds.h +++ b/drivers/scsi/be2iscsi/be_cmds.h @@ -304,6 +304,17 @@ struct mgmt_auth_method_format { struct mgmt_chap_format chap; } __packed; +struct be_cmd_req_logout_fw_sess { + struct be_cmd_req_hdr hdr; /* dw[4] */ + uint32_t session_handle; +} __packed; + +struct be_cmd_resp_logout_fw_sess { + struct be_cmd_resp_hdr hdr; /* dw[4] */ +#define BEISCSI_MGMT_SESSION_CLOSE 0x20 + uint32_t session_status; +} __packed; + struct mgmt_conn_login_options { u8 flags; u8 header_digest; @@ -1136,6 +1147,7 @@ struct be_cmd_get_all_if_id_req { #define OPCODE_ISCSI_INI_CFG_GET_HBA_NAME 6 #define OPCODE_ISCSI_INI_CFG_SET_HBA_NAME 7 #define OPCODE_ISCSI_INI_SESSION_GET_A_SESSION 14 +#define OPCODE_ISCSI_INI_SESSION_LOGOUT_TARGET 24 #define OPCODE_ISCSI_INI_DRIVER_REOPEN_ALL_SESSIONS 36 #define OPCODE_ISCSI_INI_DRIVER_OFFLOAD_SESSION 41 #define OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION 42 diff --git a/drivers/scsi/be2iscsi/be_iscsi.c b/drivers/scsi/be2iscsi/be_iscsi.c index 508f017..566d27c 100644 --- a/drivers/scsi/be2iscsi/be_iscsi.c +++ b/drivers/scsi/be2iscsi/be_iscsi.c @@ -998,6 +998,18 @@ int beiscsi_conn_start(struct iscsi_cls_conn *cls_conn) beiscsi_set_params_for_offld(beiscsi_conn, ¶ms); beiscsi_offload_connection(beiscsi_conn, ¶ms); iscsi_conn_start(cls_conn); + + /* Logout from the FW boot session */ + if (phba->fw_boot_state) { + int rc; + + rc = beiscsi_logout_fw_sess(phba, + phba->boot_sess.session_handle); + + if (!rc) + phba->fw_boot_state = 0; + } + return 0; } diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index b700fad..dd0173b 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -4400,6 +4400,7 @@ static int beiscsi_get_boot_info(struct beiscsi_hba *phba) memcpy(&phba->boot_sess, &session_resp->session_info, sizeof(struct mgmt_session_info)); + phba->fw_boot_state = BEISCSI_FW_BOOT_SESS_ACTIVE; ret = 0; boot_freemem: diff --git a/drivers/scsi/be2iscsi/be_main.h b/drivers/scsi/be2iscsi/be_main.h index 3ddde6f..8aff7cd 100644 --- a/drivers/scsi/be2iscsi/be_main.h +++ b/drivers/scsi/be2iscsi/be_main.h @@ -429,6 +429,8 @@ struct beiscsi_hba { struct be_ctrl_info ctrl; unsigned int generation; unsigned int interface_handle; + unsigned char fw_boot_state; +#define BEISCSI_FW_BOOT_SESS_ACTIVE0x01 struct mgmt_session_info boot_sess; struct invalidate_command_table inv_tbl[128]; diff --git a/drivers/scsi/be2iscsi/be_mgmt.c b/drivers/scsi/be2iscsi/be_mgmt.c index 78f56a6..1b37bbd 100644 --- a/drivers/scsi/be2iscsi/be_mgmt.c +++ b/drivers/scsi/be2iscsi/be_mgmt.c @@ -1706,4 +1706,74 @@ void beiscsi_offload_cxn_v2(struct beiscsi_offload_params *params, pwrb, (params->dw[offsetof(struct amap_beiscsi_offload_params, exp_statsn) / 32] + 1)); + +} + +/** + * beiscsi_logout_fw_sess()- Firmware Session Logout + * @phba: Device priv structure instance + * @fw_sess_handle: FW session handle + * + * Logout from the FW established sessions. + * returns + * Success: 0 + * Failure: Non-Zero Value + * + */ +int beiscsi_logout_fw_sess(struct beiscsi_hba *phba, + uint32_t fw_sess_handle) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb; + struct be_cmd_req_logout_fw_sess *req; + struct be_cmd_resp_logout_fw_sess *resp; + unsigned int tag; + int rc; + + beiscsi_log(phba, KERN_INFO, + BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX, + "BG_%d : In bescsi_logout_fwboot_sess\n"); + + spin_lock(&ctrl->mbox_lock); + tag = alloc_mcc_tag(phba); + if (!tag) { + spin_unlock(&ctrl->mbox_lock); + beiscsi_log(phba, KERN_INFO, + BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX, + "BG_%d : MBX Tag Failure\n"); + return -EINVAL; + } + + wrb = wrb_from_mccq(phba); + req = embedded_payload(wrb); + wrb->tag0 |= tag; + be_wrb_hdr_p
[PATCH 3/7] be2iscsi : Fix memory leak in the unload path
Driver was not freeing the DMA memory allocated for EQ/CQ in the unload path. This patch frees the DMA memory during the driver unload. Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_main.c | 18 -- 1 files changed, 12 insertions(+), 6 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index 4d95596..dca3a55 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -3695,14 +3695,16 @@ static void be_mcc_queues_destroy(struct beiscsi_hba *phba) struct be_ctrl_info *ctrl = &phba->ctrl; q = &phba->ctrl.mcc_obj.q; - if (q->created) + if (q->created) { beiscsi_cmd_q_destroy(ctrl, q, QTYPE_MCCQ); - be_queue_free(phba, q); + be_queue_free(phba, q); + } q = &phba->ctrl.mcc_obj.cq; - if (q->created) + if (q->created) { beiscsi_cmd_q_destroy(ctrl, q, QTYPE_CQ); - be_queue_free(phba, q); + be_queue_free(phba, q); + } } static void hwi_cleanup(struct beiscsi_hba *phba) @@ -3746,8 +3748,10 @@ static void hwi_cleanup(struct beiscsi_hba *phba) for (i = 0; i < (phba->num_cpus); i++) { q = &phwi_context->be_cq[i]; - if (q->created) + if (q->created) { + be_queue_free(phba, q); beiscsi_cmd_q_destroy(ctrl, q, QTYPE_CQ); + } } be_mcc_queues_destroy(phba); @@ -3757,8 +3761,10 @@ static void hwi_cleanup(struct beiscsi_hba *phba) eq_for_mcc = 0; for (i = 0; i < (phba->num_cpus + eq_for_mcc); i++) { q = &phwi_context->be_eq[i].q; - if (q->created) + if (q->created) { + be_queue_free(phba, q); beiscsi_cmd_q_destroy(ctrl, q, QTYPE_EQ); + } } be_cmd_fw_uninit(ctrl); } -- 1.7.1 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 1/7] be2iscsi : Fix the retry count for boot targets
Increment the retry count to get the boot target info when port async event is received by the driver. Update sysfs enteries with the boot target parameters. Signed-off-by: Minh Tran Signed-off-by: John Soni Jose Signed-off-by: Jayamohan Kallickal --- drivers/scsi/be2iscsi/be_cmds.c |4 drivers/scsi/be2iscsi/be_main.c | 23 --- drivers/scsi/be2iscsi/be_main.h |4 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/drivers/scsi/be2iscsi/be_cmds.c b/drivers/scsi/be2iscsi/be_cmds.c index 80d97f3..8e16c49 100644 --- a/drivers/scsi/be2iscsi/be_cmds.c +++ b/drivers/scsi/be2iscsi/be_cmds.c @@ -452,6 +452,7 @@ void beiscsi_async_link_state_process(struct beiscsi_hba *phba, ((evt->port_link_status & ASYNC_EVENT_LOGICAL) && (evt->port_fault == BEISCSI_PHY_LINK_FAULT_NONE))) { phba->state = BE_ADAPTER_LINK_UP | BE_ADAPTER_CHECK_BOOT; + phba->get_boot = BE_GET_BOOT_RETRIES; beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG | BEISCSI_LOG_INIT, @@ -480,6 +481,7 @@ int beiscsi_process_mcc(struct beiscsi_hba *phba) case ASYNC_EVENT_NEW_ISCSI_CONN: case ASYNC_EVENT_NEW_TCP_CONN: phba->state |= BE_ADAPTER_CHECK_BOOT; + phba->get_boot = BE_GET_BOOT_RETRIES; beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX, @@ -488,6 +490,8 @@ int beiscsi_process_mcc(struct beiscsi_hba *phba) compl->flags); break; default: + phba->state |= BE_ADAPTER_CHECK_BOOT; + phba->get_boot = BE_GET_BOOT_RETRIES; beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_CONFIG | BEISCSI_LOG_MBOX, diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c index 923a2b5..66ea88c 100644 --- a/drivers/scsi/be2iscsi/be_main.c +++ b/drivers/scsi/be2iscsi/be_main.c @@ -2037,11 +2037,16 @@ static void beiscsi_process_mcc_isr(struct beiscsi_hba *phba) /* Interpret compl as a async link evt */ beiscsi_async_link_state_process(phba, (struct be_async_event_link_state *) mcc_compl); - else + else { beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_MBOX, "BM_%d : Unsupported Async Event, flags" " = 0x%08x\n", mcc_compl->flags); + if (phba->state & BE_ADAPTER_LINK_UP) { + phba->state |= BE_ADAPTER_CHECK_BOOT; + phba->get_boot = BE_GET_BOOT_RETRIES; + } + } } else if (mcc_compl->flags & CQE_FLAGS_COMPLETED_MASK) { be_mcc_compl_process_isr(&phba->ctrl, mcc_compl); atomic_dec(&phba->ctrl.mcc_obj.q.used); @@ -4328,8 +4333,14 @@ static int beiscsi_get_boot_info(struct beiscsi_hba *phba) beiscsi_log(phba, KERN_ERR, BEISCSI_LOG_INIT | BEISCSI_LOG_CONFIG, "BM_%d : No boot session\n"); + + if (ret == -ENXIO) + phba->get_boot = 0; + + return ret; } + phba->get_boot = 0; nonemb_cmd.va = pci_zalloc_consistent(phba->ctrl.pdev, sizeof(*session_resp), &nonemb_cmd.dma); @@ -5374,8 +5385,14 @@ beiscsi_hw_health_check(struct work_struct *work) be_eqd_update(phba); if (phba->state & BE_ADAPTER_CHECK_BOOT) { - phba->state &= ~BE_ADAPTER_CHECK_BOOT; - be_check_boot_session(phba); + if ((phba->get_boot > 0) && (!phba->boot_kset)) { + phba->get_boot--; + if (!(phba->get_boot % BE_GET_BOOT_TO)) + be_check_boot_session(phba); + } else { + phba->state &= ~BE_ADAPTER_CHECK_BOOT; + phba->get_boot = 0; + } } beiscsi_ue_detect(phba); diff --git a/drivers/scsi/be2iscsi/be_main.h b/drivers/scsi/be2iscsi/be_main.h index 7ee0ffc.
Re: [RFC] Simlify dif_verify routines and fixup fileio protection information code.
On 4/16/2015 6:58 PM, Sagi Grimberg wrote: On 4/16/2015 4:46 PM, Akinobu Mita wrote: 2015-04-16 17:52 GMT+09:00 Sagi Grimberg : On 4/15/2015 7:10 PM, Martin K. Petersen wrote: "Sagi" == Sagi Grimberg writes: By the commit 436f4a0a ("loopback: Add fabric_prot_type attribute support"), When WRITE_SAME command with WRPROTECT=0 is executed, sbc_dif_generate() is called but cmd->t_prot_sg is NULL as block layer didn't allocate it for WRITE_SAME. Sagi> Actually this is a bug. Why didn't the initiator allocate Sagi> integrity meta-data for WRITE_SAME? Looking at the code it looks Sagi> like it should. We don't issue WRITE SAME with PI so there is no prot SGL. Is there a specific reason why we don't? It is not only for the WRITE SAME requests from block device but also for READ/WRITE with PROTECT=0 requests by SG_IO. This is specific to loopback which is using target_submit_cmd_map_sgls() Other fabrics would allocate sgls per IO and the core would allocate protection SGLs as well. By "This" I meant the NULL deref you are witnessing in for wrprotect=0. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Backport of a fix for HPSA (Disabling a disabled device problem during kdump) driver
On Mon, Apr 13, 2015 at 03:18:44PM +0200, Tomas Henzl wrote: > On 04/11/2015 12:45 AM, Vinson Lee wrote: > > On Tue, Jan 27, 2015 at 4:18 PM, Greg KH wrote: > >> On Tue, Jan 06, 2015 at 05:15:19PM +0100, Tomas Henzl wrote: > >>> On 01/05/2015 07:41 PM, Masoud Sharbiani wrote: > Dear stable maintainers, > Can you please backport commitid 132aa220b45d60e9b20def1e9d8be9422eed9616 > (hpsa: refine the pci enable/disable handling) to 3.10 stable (and > earlier, if applicable)? > >>> Please do not apply this patch isolated from his friend, the > >>> 859c75aba20264d87dd026bab0d0ca3bff385955 hpsa: add missing pci_set_master > >>> in kdump path > >>> needs to be applied together with the > >>> 132aa220b45d60e9b20def1e9d8be9422eed9616 . > >>> > >>> In addition to that, after the original issue goes away you may notice > >>> sometimes > >>> an unhandled irq 16 message, to fix this a patch is posted > >>> here http://www.spinics.net/lists/linux-scsi/msg80316.html > >>> This patch still awaits a maintainers review though. > >>> > >>> Probably the best idea is to wait until the issue is solved completely. > >> I'll wait, when it all gets worked out, please let stable@ know what > >> patches to apply where. > >> > >> thanks, > >> > >> greg k-h > >> -- > >> To unsubscribe from this list: send the line "unsubscribe stable" in > >> the body of a message to majord...@vger.kernel.org > >> More majordomo info at http://vger.kernel.org/majordomo-info.html > > > > Hi, Thomas. > > > > The unhandled irq 16 issue seems to be fixed by 4.0-rc1 commit "hpsa: > > turn off interrupts when kdump starts". > > > > Are the following patches suitable for stable now? > > Yes, I believe they are, just note that > 03741d9 hpsa: fix memory leak in kdump hard reset > is not a part of that group we discussed before, but it may be added > to stable too. > > Cheers, > Tomas > > > > > 3b74729 hpsa: turn off interrupts when kdump starts > > 03741d9 hpsa: fix memory leak in kdump hard reset > > 859c75a hpsa: add missing pci_set_master in kdump path > > 132aa22 hpsa: refine the pci enable/disable handling > > > > Cheers, > > Vinson > I am queuing these 4 patches for the 3.16 kernel as well. Cheers, -- Luís > -- > To unsubscribe from this list: send the line "unsubscribe stable" in > the body of a message to majord...@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [RFC] Simlify dif_verify routines and fixup fileio protection information code.
On 4/16/2015 4:46 PM, Akinobu Mita wrote: 2015-04-16 17:52 GMT+09:00 Sagi Grimberg : On 4/15/2015 7:10 PM, Martin K. Petersen wrote: "Sagi" == Sagi Grimberg writes: By the commit 436f4a0a ("loopback: Add fabric_prot_type attribute support"), When WRITE_SAME command with WRPROTECT=0 is executed, sbc_dif_generate() is called but cmd->t_prot_sg is NULL as block layer didn't allocate it for WRITE_SAME. Sagi> Actually this is a bug. Why didn't the initiator allocate Sagi> integrity meta-data for WRITE_SAME? Looking at the code it looks Sagi> like it should. We don't issue WRITE SAME with PI so there is no prot SGL. Is there a specific reason why we don't? It is not only for the WRITE SAME requests from block device but also for READ/WRITE with PROTECT=0 requests by SG_IO. This is specific to loopback which is using target_submit_cmd_map_sgls() Other fabrics would allocate sgls per IO and the core would allocate protection SGLs as well. So isn't is appropreate to allocate prot SGL in target_write_prot_action() (and mark se_cmd->se_cmd_flags to release it at deallocation time)? I'd say that given this is specific to loopback, than tcm_loop needs to be fixed... But specifically for WRITE_SAME, I'd be careful with allocating a single 8 byte protection buffer because as Martin said, unlike the data block, the protection field may change from sector to sector (ref_tag in Type 1). So allocating a single 8 byte buf will take it's toll in the backend (iblock backend would need to allocate all the protection information and add it to the bio anyway, file/rd will need to do multiple writes). It might be better that for the special WRITE_SAME case, allocate 8 * sectors sgl and set it up (incrementing ref_tag for type 1). This way, the backend code can stay the same (other than opening write_same with PI in iblock). Sagi. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [RFC] Simlify dif_verify routines and fixup fileio protection information code.
> "Akinobu" == Akinobu Mita writes: >>> We don't issue WRITE SAME with PI so there is no prot SGL. >> Is there a specific reason why we don't? There really isn't much of a benefit when all you're doing is replicating zeroes. So it hasn't been very high on my list. Akinobu> It is not only for the WRITE SAME requests from block device Akinobu> but also for READ/WRITE with PROTECT=0 requests by SG_IO. Akinobu> So isn't is appropreate to allocate prot SGL in Akinobu> target_write_prot_action() (and mark se_cmd->se_cmd_flags to Akinobu> release it at deallocation time)? Correct. Just because a target is formatted with PI does not mean that every I/O it receives has PI attached. That's entirely driven by RDPROTECT/WRPROTECT/VRPROTECT at the initiator's discretion. It is an absolute requirement that the device, if formatted with PI, will generate and write the correct protection information when WRPROTECT is 0. -- Martin K. Petersen Oracle Linux Engineering -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/3] uas: Add US_FL_MAX_SECTORS_240 flag
On Thu, 16 Apr 2015, Hans de Goede wrote: > The usb-storage driver sets max_sectors = 240 in its scsi-host template, for > uas we do not want to do that for all devices, but testing has shown that > some devices need it. > > This commit adds a US_FL_MAX_SECTORS_240 flag for such devices, and implements > support for it in uas.c, while at it it also adds support for > US_FL_MAX_SECTORS_64 to uas.c. > > Signed-off-by: Hans de Goede You forgot to update Documentation/kernel-parameters.txt. Alan Stern -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/3] uas: Allow uas_use_uas_driver to return usb-storage flags
On Thu, 2015-04-16 at 14:17 +0200, Hans de Goede wrote: > uas_use_uas_driver may set some US_FL_foo flags during detection, currently > these are stored in a local variable and then throw away, but these may be > of interest to the caller, so add an extra parameter to (optionally) return > the detected flags, and use this in the uas driver. > > Signed-off-by: Hans de Goede Patched (all 3 of them) and compile tested on the current Fedora kernel (3.19.3-200), device is accessible and functioning without a kernel parameter Steve > --- > drivers/usb/storage/uas-detect.h | 6 +- > drivers/usb/storage/uas.c| 6 +++--- > drivers/usb/storage/usb.c| 2 +- > 3 files changed, 9 insertions(+), 5 deletions(-) > > diff --git a/drivers/usb/storage/uas-detect.h > b/drivers/usb/storage/uas-detect.h > index 9893d69..63ae161 100644 > --- a/drivers/usb/storage/uas-detect.h > +++ b/drivers/usb/storage/uas-detect.h > @@ -51,7 +51,8 @@ static int uas_find_endpoints(struct usb_host_interface > *alt, > } > > static int uas_use_uas_driver(struct usb_interface *intf, > - const struct usb_device_id *id) > + const struct usb_device_id *id, > + unsigned long *flags_ret) > { > struct usb_host_endpoint *eps[4] = { }; > struct usb_device *udev = interface_to_usbdev(intf); > @@ -132,5 +133,8 @@ static int uas_use_uas_driver(struct usb_interface *intf, > return 0; > } > > + if (flags_ret) > + *flags_ret = flags; > + > return 1; > } > diff --git a/drivers/usb/storage/uas.c b/drivers/usb/storage/uas.c > index 6cdabdc..c6109c1 100644 > --- a/drivers/usb/storage/uas.c > +++ b/drivers/usb/storage/uas.c > @@ -887,8 +887,9 @@ static int uas_probe(struct usb_interface *intf, const > struct usb_device_id *id) > struct Scsi_Host *shost = NULL; > struct uas_dev_info *devinfo; > struct usb_device *udev = interface_to_usbdev(intf); > + unsigned long dev_flags; > > - if (!uas_use_uas_driver(intf, id)) > + if (!uas_use_uas_driver(intf, id, &dev_flags)) > return -ENODEV; > > if (uas_switch_interface(udev, intf)) > @@ -910,8 +911,7 @@ static int uas_probe(struct usb_interface *intf, const > struct usb_device_id *id) > devinfo->udev = udev; > devinfo->resetting = 0; > devinfo->shutdown = 0; > - devinfo->flags = id->driver_info; > - usb_stor_adjust_quirks(udev, &devinfo->flags); > + devinfo->flags = dev_flags; > init_usb_anchor(&devinfo->cmd_urbs); > init_usb_anchor(&devinfo->sense_urbs); > init_usb_anchor(&devinfo->data_urbs); > diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c > index 5600c33..db6f6b5 100644 > --- a/drivers/usb/storage/usb.c > +++ b/drivers/usb/storage/usb.c > @@ -1080,7 +1080,7 @@ static int storage_probe(struct usb_interface *intf, > > /* If uas is enabled and this device can do uas then ignore it. */ > #if IS_ENABLED(CONFIG_USB_UAS) > - if (uas_use_uas_driver(intf, id)) > + if (uas_use_uas_driver(intf, id, NULL)) > return -ENXIO; > #endif > -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 31/43] hpsa: call pci_release_regions after pci_disable_device
From: Robert Elliott Despite the fact that PCI devices are enabled in this order: 1. pci_enable_device 2. pci_request_regions Documentation/PCI/pci.txt specifies that they be undone in this order 1. pci_disable_device 2. pci_release_regions Tested by injecting error in the call to pci_enable_device in hpsa_init_one -> hpsa_pci_init: [9.095001] hpsa :04:00.0: failed to enable PCI device [9.095005] hpsa: probe of :04:00.0 failed with error -22 (-22 is -EINVAL) and then in the call pci_request_regions: [9.178623] hpsa :04:00.0: failed to obtain PCI resources [9.178671] hpsa: probe of :04:00.0 failed with error -16 (-16 is -EBUSY) and then by adding reset_devices to the kernel command line and inject errors into the two calls to pci_enable_device and the call to pci_request_regions in hpsa_init_one -> hpsa_init_reset_devices. (inject on 6th call, 1st to hpsa2) [ 62.413750] hpsa :04:00.0: Failed to enable PCI device (inject on 7th call, 2nd to hpsa2) [ 62.807571] hpsa :04:00.0: failed to enable device. (inject on 8th call, 3rd to hpsa2) [ 62.697198] hpsa :04:00.0: failed to obtain PCI resources [ 62.697234] hpsa: probe of :04:00.0 failed with error -16 The reset_devices path calls return -ENODEV on failure rather than passing the result, which apparently doesn't cause the pci driver to print anything. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace < don.br...@pmcs.com> --- drivers/scsi/hpsa.c | 17 + 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 5e12520..8aeef06 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7048,8 +7048,12 @@ static void hpsa_free_pci_init(struct ctlr_info *h) iounmap(h->vaddr); /* pci_init 3 */ h->vaddr = NULL; hpsa_disable_interrupt_mode(h); /* pci_init 2 */ - pci_release_regions(h->pdev); /* pci_init 2 */ + /* +* call pci_disable_device before pci_release_regions per +* Documentation/PCI/pci.txt +*/ pci_disable_device(h->pdev);/* pci_init 1 */ + pci_release_regions(h->pdev); /* pci_init 2 */ } /* several items must be freed later */ @@ -7072,6 +7076,7 @@ static int hpsa_pci_init(struct ctlr_info *h) err = pci_enable_device(h->pdev); if (err) { dev_err(&h->pdev->dev, "failed to enable PCI device\n"); + pci_disable_device(h->pdev); return err; } @@ -7079,7 +7084,8 @@ static int hpsa_pci_init(struct ctlr_info *h) if (err) { dev_err(&h->pdev->dev, "failed to obtain PCI resources\n"); - goto clean1;/* pci */ + pci_disable_device(h->pdev); + return err; } pci_set_master(h->pdev); @@ -7120,9 +7126,12 @@ clean3: /* vaddr, intmode+region, pci */ h->vaddr = NULL; clean2:/* intmode+region, pci */ hpsa_disable_interrupt_mode(h); - pci_release_regions(h->pdev); -clean1:/* pci */ + /* +* call pci_disable_device before pci_release_regions per +* Documentation/PCI/pci.txt +*/ pci_disable_device(h->pdev); + pci_release_regions(h->pdev); return err; } -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 39/43] hpsa: propagate the error code in hpsa_kdump_soft_reset
From: Robert Elliott If hpsa_wait_for_board_state fails, hpsa_kdump_soft_reset should propagate its return value (e.g., -ENODEV) rather than just returning -1. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 11 +++ 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index f65333d..f36ab70 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7458,19 +7458,22 @@ static int hpsa_request_irqs(struct ctlr_info *h, static int hpsa_kdump_soft_reset(struct ctlr_info *h) { + int rc; hpsa_send_host_reset(h, RAID_CTLR_LUNID, HPSA_RESET_TYPE_CONTROLLER); dev_info(&h->pdev->dev, "Waiting for board to soft reset.\n"); - if (hpsa_wait_for_board_state(h->pdev, h->vaddr, BOARD_NOT_READY)) { + rc = hpsa_wait_for_board_state(h->pdev, h->vaddr, BOARD_NOT_READY); + if (rc) { dev_warn(&h->pdev->dev, "Soft reset had no effect.\n"); - return -1; + return rc; } dev_info(&h->pdev->dev, "Board reset, awaiting READY status.\n"); - if (hpsa_wait_for_board_state(h->pdev, h->vaddr, BOARD_READY)) { + rc = hpsa_wait_for_board_state(h->pdev, h->vaddr, BOARD_READY); + if (rc) { dev_warn(&h->pdev->dev, "Board failed to become ready " "after soft reset.\n"); - return -1; + return rc; } return 0; -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 35/43] hpsa: create workqueue after the driver is ready for use
From: Robert Elliott Don't create the resubmit workqueue in hpsa_init_one until everything else is ready to use, so everything can be freed in reverse order of when they were allocated without risking freeing things while workqueue items are still active. Destroy the workqueue in the right order in hpsa_undo_allocations_after_kdump_soft_reset too. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 60 ++- 1 file changed, 31 insertions(+), 29 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index c6e950e..fb755a8 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7688,30 +7688,18 @@ reinit_after_soft_reset: atomic_set(&h->passthru_cmds_avail, HPSA_MAX_CONCURRENT_PASSTHRUS); atomic_set(&h->abort_cmds_available, HPSA_CMDS_RESERVED_FOR_ABORTS); - h->rescan_ctlr_wq = hpsa_create_controller_wq(h, "rescan"); - if (!h->rescan_ctlr_wq) { - rc = -ENOMEM; - goto clean1; - } - - h->resubmit_wq = hpsa_create_controller_wq(h, "resubmit"); - if (!h->resubmit_wq) { - rc = -ENOMEM; - goto clean1;/* aer/h */ - } - /* Allocate and clear per-cpu variable lockup_detected */ h->lockup_detected = alloc_percpu(u32); if (!h->lockup_detected) { dev_err(&h->pdev->dev, "Failed to allocate lockup detector\n"); rc = -ENOMEM; - goto clean1;/* wq/aer/h */ + goto clean1;/* aer/h */ } set_lockup_detected_for_all_cpus(h, 0); rc = hpsa_pci_init(h); if (rc) - goto clean2;/* lockup, wq/aer/h */ + goto clean2;/* lockup, aer/h */ sprintf(h->devname, HPSA "%d", number_of_controllers); h->ctlr = number_of_controllers; @@ -7727,7 +7715,7 @@ reinit_after_soft_reset: dac = 0; } else { dev_err(&pdev->dev, "no suitable DMA available\n"); - goto clean3;/* pci, lockup, wq/aer/h */ + goto clean3;/* pci, lockup, aer/h */ } } @@ -7736,16 +7724,16 @@ reinit_after_soft_reset: rc = hpsa_request_irqs(h, do_hpsa_intr_msi, do_hpsa_intr_intx); if (rc) - goto clean3;/* pci, lockup, wq/aer/h */ + goto clean3;/* pci, lockup, aer/h */ dev_info(&pdev->dev, "%s: <0x%x> at IRQ %d%s using DAC\n", h->devname, pdev->device, h->intr[h->intr_mode], dac ? "" : " not"); rc = hpsa_alloc_cmd_pool(h); if (rc) - goto clean4;/* irq, pci, lockup, wq/aer/h */ + goto clean4;/* irq, pci, lockup, aer/h */ rc = hpsa_alloc_sg_chain_blocks(h); if (rc) - goto clean5;/* cmd, irq, pci, lockup, wq/aer/h */ + goto clean5;/* cmd, irq, pci, lockup, aer/h */ init_waitqueue_head(&h->scan_wait_queue); init_waitqueue_head(&h->abort_cmd_wait_queue); init_waitqueue_head(&h->abort_sync_wait_queue); @@ -7758,7 +7746,20 @@ reinit_after_soft_reset: spin_lock_init(&h->devlock); rc = hpsa_put_ctlr_into_performant_mode(h); if (rc) - goto clean6;/* sg, cmd, irq, pci, lockup, wq/aer/h */ + goto clean6;/* sg, cmd, irq, pci, lockup, aer/h */ + + /* create the resubmit workqueue */ + h->rescan_ctlr_wq = hpsa_create_controller_wq(h, "rescan"); + if (!h->rescan_ctlr_wq) { + rc = -ENOMEM; + goto clean7; + } + + h->resubmit_wq = hpsa_create_controller_wq(h, "resubmit"); + if (!h->resubmit_wq) { + rc = -ENOMEM; + goto clean7;/* aer/h */ + } /* * At this point, the controller is ready to take commands. @@ -7800,7 +7801,7 @@ reinit_after_soft_reset: rc = hpsa_kdump_soft_reset(h); if (rc) /* Neither hard nor soft reset worked, we're hosed. */ - goto clean7; + goto clean8; dev_info(&h->pdev->dev, "Board READY.\n"); dev_info(&h->pdev->dev, @@ -7837,7 +7838,7 @@ reinit_after_soft_reset: hpsa_hba_inquiry(h); rc = hpsa_register_scsi(h); /* hook ourselves into SCSI subsystem */ if (rc) - goto clean7; + goto clean8; /* wq, perf, sg, cmd, irq, pci, lockup, aer/h */ /* Monitor the controller for firmware lockups */ h->heartbeat_sample_interval = HEARTBEAT_SAMPLE_INTERVAL; @@ -7849,19 +7850,20 @@ reinit_after_soft_reset: h->heartbeat_sample_interval); return 0; -clean7: /* perf, sg, cmd, irq, pci,
[PATCH v4 29/43] hpsa: refactor and rework support for sending TEST_UNIT_READY
From: Webb Scales Factor out the code which sends the TEST_UNIT_READY from wait_for_device_to_become_ready() into its own function. Move the code which waits for the TEST_UNIT_READY from wait_for_device_to_become_ready() into its own function. If a logical drive has failed, resetting it will ensure outstanding commands are completed, but polling it with TURs after the reset will not work because the TURs will never report good status. So successful TUR should not be a condition of success for the device reset error handler. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 117 ++- 1 file changed, 87 insertions(+), 30 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index ef2d209..753026a 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -4792,51 +4792,108 @@ static int hpsa_register_scsi(struct ctlr_info *h) return -ENOMEM; } -static int wait_for_device_to_become_ready(struct ctlr_info *h, - unsigned char lunaddr[]) +/* + * Send a TEST_UNIT_READY command to the specified LUN using the specified + * reply queue; returns zero if the unit is ready, and non-zero otherwise. + */ +static int hpsa_send_test_unit_ready(struct ctlr_info *h, + struct CommandList *c, unsigned char lunaddr[], + int reply_queue) +{ + int rc; + + /* Send the Test Unit Ready, fill_cmd can't fail, no mapping */ + (void) fill_cmd(c, TEST_UNIT_READY, h, + NULL, 0, 0, lunaddr, TYPE_CMD); + rc = hpsa_scsi_do_simple_cmd(h, c, reply_queue, NO_TIMEOUT); + if (rc) + return rc; + /* no unmap needed here because no data xfer. */ + + /* Check if the unit is already ready. */ + if (c->err_info->CommandStatus == CMD_SUCCESS) + return 0; + + /* +* The first command sent after reset will receive "unit attention" to +* indicate that the LUN has been reset...this is actually what we're +* looking for (but, success is good too). +*/ + if (c->err_info->CommandStatus == CMD_TARGET_STATUS && + c->err_info->ScsiStatus == SAM_STAT_CHECK_CONDITION && + (c->err_info->SenseInfo[2] == NO_SENSE || +c->err_info->SenseInfo[2] == UNIT_ATTENTION)) + return 0; + + return 1; +} + +/* + * Wait for a TEST_UNIT_READY command to complete, retrying as necessary; + * returns zero when the unit is ready, and non-zero when giving up. + */ +static int hpsa_wait_for_test_unit_ready(struct ctlr_info *h, + struct CommandList *c, + unsigned char lunaddr[], int reply_queue) { int rc; int count = 0; int waittime = 1; /* seconds */ - struct CommandList *c; - - c = cmd_alloc(h); /* Send test unit ready until device ready, or give up. */ - while (count < HPSA_TUR_RETRY_LIMIT) { + for (count = 0; count < HPSA_TUR_RETRY_LIMIT; count++) { - /* Wait for a bit. do this first, because if we send + /* +* Wait for a bit. do this first, because if we send * the TUR right away, the reset will just abort it. */ msleep(1000 * waittime); - count++; - rc = 0; /* Device ready. */ + + rc = hpsa_send_test_unit_ready(h, c, lunaddr, reply_queue); + if (!rc) + break; /* Increase wait time with each try, up to a point. */ if (waittime < HPSA_MAX_WAIT_INTERVAL_SECS) - waittime = waittime * 2; + waittime *= 2; - /* Send the Test Unit Ready, fill_cmd can't fail, no mapping */ - (void) fill_cmd(c, TEST_UNIT_READY, h, - NULL, 0, 0, lunaddr, TYPE_CMD); - rc = hpsa_scsi_do_simple_cmd(h, c, DEFAULT_REPLY_QUEUE, - NO_TIMEOUT); - if (rc) - goto do_it_again; - /* no unmap needed here because no data xfer. */ + dev_warn(&h->pdev->dev, +"waiting %d secs for device to become ready.\n", +waittime); + } - if (c->err_info->CommandStatus == CMD_SUCCESS) - break; + return rc; +} - if (c->err_info->CommandStatus == CMD_TARGET_STATUS && - c->err_info->ScsiStatus == SAM_STAT_CHECK_CONDITION && - (c->err_info->SenseInfo[2] == NO_SENSE || - c->err_info->SenseInfo[2] == UNIT_ATTENTION)) +static int wait_for_device_to_become_ready(struct ctlr_info *h,
[PATCH v4 36/43] hpsa: add interrupt number to /proc/interrupts interrupt name
From: Robert Elliott Add the interrupt number to the interrupt names that appear in /proc/interrupts, so they are unique Also, delete the IRQ and DAC prints. Other parts of the kernel already print the IRQ assignments, and dual-address-cycle support has not been interesting since the parallel PCI bus went from 32 to 64 bits wide. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 20 ++-- drivers/scsi/hpsa.h |1 + 2 files changed, 15 insertions(+), 6 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index fb755a8..83d7df0 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7310,8 +7310,9 @@ static int hpsa_request_irqs(struct ctlr_info *h, if (h->intr_mode == PERF_MODE_INT && h->msix_vector > 0) { /* If performant mode and MSI-X, use multiple reply queues */ for (i = 0; i < h->msix_vector; i++) { + sprintf(h->intrname[i], "%s-msix%d", h->devname, i); rc = request_irq(h->intr[i], msixhandler, - 0, h->devname, + 0, h->intrname[i], &h->q[i]); if (rc) { int j; @@ -7332,12 +7333,22 @@ static int hpsa_request_irqs(struct ctlr_info *h, } else { /* Use single reply pool */ if (h->msix_vector > 0 || h->msi_vector) { + if (h->msix_vector) + sprintf(h->intrname[h->intr_mode], + "%s-msix", h->devname); + else + sprintf(h->intrname[h->intr_mode], + "%s-msi", h->devname); rc = request_irq(h->intr[h->intr_mode], - msixhandler, 0, h->devname, + msixhandler, 0, + h->intrname[h->intr_mode], &h->q[h->intr_mode]); } else { + sprintf(h->intrname[h->intr_mode], + "%s-intx", h->devname); rc = request_irq(h->intr[h->intr_mode], - intxhandler, IRQF_SHARED, h->devname, + intxhandler, IRQF_SHARED, + h->intrname[h->intr_mode], &h->q[h->intr_mode]); } irq_set_affinity_hint(h->intr[h->intr_mode], NULL); @@ -7725,9 +7736,6 @@ reinit_after_soft_reset: rc = hpsa_request_irqs(h, do_hpsa_intr_msi, do_hpsa_intr_intx); if (rc) goto clean3;/* pci, lockup, aer/h */ - dev_info(&pdev->dev, "%s: <0x%x> at IRQ %d%s using DAC\n", - h->devname, pdev->device, - h->intr[h->intr_mode], dac ? "" : " not"); rc = hpsa_alloc_cmd_pool(h); if (rc) goto clean4;/* irq, pci, lockup, aer/h */ diff --git a/drivers/scsi/hpsa.h b/drivers/scsi/hpsa.h index 7cb8586..3ec8934 100644 --- a/drivers/scsi/hpsa.h +++ b/drivers/scsi/hpsa.h @@ -220,6 +220,7 @@ struct ctlr_info { int remove_in_progress; /* Address of h->q[x] is passed to intr handler to know which queue */ u8 q[MAX_REPLY_QUEUES]; + char intrname[MAX_REPLY_QUEUES][16];/* "hpsa0-msix00" names */ u32 TMFSupportFlags; /* cache what task mgmt funcs are supported. */ #define HPSATMF_BITS_SUPPORTED (1 << 0) #define HPSATMF_PHYS_LUN_RESET (1 << 1) -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 34/43] hpsa: fix try_soft_reset error handling
From: Robert Elliott If registering the special interrupt handlers in hpsa_init_one before a soft reset fails, the error exit needs to deallocate everything that was allocated before. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 16 +++- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 99fd4d3..c6e950e 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7784,9 +7784,15 @@ reinit_after_soft_reset: dev_warn(&h->pdev->dev, "Failed to request_irq after soft reset.\n"); /* -* clean4 starts with free_irqs, but that was just -* done. Then, request_irqs_failed, so there is -* nothing to free. So, goto the next label. +* cannot goto clean7 or free_irqs will be called +* again. Instead, do its work +*/ + hpsa_free_performant_mode(h); /* clean7 */ + hpsa_free_sg_chain_blocks(h); /* clean6 */ + hpsa_free_cmd_pool(h); /* clean5 */ + /* +* skip hpsa_free_irqs(h) clean4 since that +* was just called before request_irqs failed */ goto clean3; } @@ -7794,7 +7800,7 @@ reinit_after_soft_reset: rc = hpsa_kdump_soft_reset(h); if (rc) /* Neither hard nor soft reset worked, we're hosed. */ - goto clean4; + goto clean7; dev_info(&h->pdev->dev, "Board READY.\n"); dev_info(&h->pdev->dev, @@ -7815,7 +7821,7 @@ reinit_after_soft_reset: hpsa_undo_allocations_after_kdump_soft_reset(h); try_soft_reset = 0; if (rc) - /* don't go to clean4, we already unallocated */ + /* don't goto clean, we already unallocated */ return -ENODEV; goto reinit_after_soft_reset; -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 28/43] hpsa: don't return abort request until target is complete
From: Webb Scales Don't return from the abort request until the target command is complete. Mark outstanding commands which have a pending abort, and do not send them to the host if we can avoid it. If the current command has been aborted, do not call the SCSI command completion routine from the I/O path: when the abort returns successfully, the SCSI mid-layer will handle the completion implicitly. The following race was possible in theory. 1. LLD is requested to abort a scsi command 2. scsi command completes 3. The struct CommandList associated with 2 is made available. 4. new io request to LLD to another LUN re-uses struct CommandList 5. abort handler follows scsi_cmnd->host_scribble and finds struct CommandList and tries to aborts it. Now we have aborted the wrong command. Fix by resetting the scsi_cmd field of struct CommandList upon completion and making the abort handler check that the scsi_cmd pointer in the CommadList struct matches the scsi_cmnd that it has been asked to abort. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 120 +++ drivers/scsi/hpsa.h |1 drivers/scsi/hpsa_cmd.h |2 + 3 files changed, 93 insertions(+), 30 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 678b2bf..ef2d209 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -195,6 +195,10 @@ static struct board_type products[] = { {0x103C, "Unknown Smart Array", &SA5_access}, }; +#define SCSI_CMD_BUSY ((struct scsi_cmnd *)&hpsa_cmd_busy) +static const struct scsi_cmnd hpsa_cmd_busy; +#define SCSI_CMD_IDLE ((struct scsi_cmnd *)&hpsa_cmd_idle) +static const struct scsi_cmnd hpsa_cmd_idle; static int number_of_controllers; static irqreturn_t do_hpsa_intr_intx(int irq, void *dev_id); @@ -270,6 +274,11 @@ static inline struct ctlr_info *shost_to_hba(struct Scsi_Host *sh) return (struct ctlr_info *) *priv; } +static inline bool hpsa_is_cmd_idle(struct CommandList *c) +{ + return c->scsi_cmd == SCSI_CMD_IDLE; +} + /* extract sense key, asc, and ascq from sense data. -1 means invalid. */ static void decode_sense_data(const u8 *sense_data, int sense_data_len, int *sense_key, int *asc, int *ascq) @@ -959,9 +968,11 @@ static void __enqueue_cmd_and_start_io(struct ctlr_info *h, } } -static void enqueue_cmd_and_start_io(struct ctlr_info *h, - struct CommandList *c) +static void enqueue_cmd_and_start_io(struct ctlr_info *h, struct CommandList *c) { + if (unlikely(c->abort_pending)) + return finish_cmd(c); + __enqueue_cmd_and_start_io(h, c, DEFAULT_REPLY_QUEUE); } @@ -1980,9 +1991,36 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, return retry; /* retry on raid path? */ } +static void hpsa_cmd_resolve_events(struct ctlr_info *h, + struct CommandList *c) +{ + /* +* Prevent the following race in the abort handler: +* +* 1. LLD is requested to abort a SCSI command +* 2. The SCSI command completes +* 3. The struct CommandList associated with step 2 is made available +* 4. New I/O request to LLD to another LUN re-uses struct CommandList +* 5. Abort handler follows scsi_cmnd->host_scribble and +*finds struct CommandList and tries to aborts it +* Now we have aborted the wrong command. +* +* Clear c->scsi_cmd here so that the abort handler will know this +* command has completed. Then, check to see if the abort handler is +* waiting for this command, and, if so, wake it. +*/ + c->scsi_cmd = SCSI_CMD_IDLE; + mb(); /* Ensure c->scsi_cmd is set to SCSI_CMD_IDLE */ + if (c->abort_pending) { + c->abort_pending = false; + wake_up_all(&h->abort_sync_wait_queue); + } +} + static void hpsa_cmd_free_and_done(struct ctlr_info *h, struct CommandList *c, struct scsi_cmnd *cmd) { + hpsa_cmd_resolve_events(h, c); cmd_free(h, c); cmd->scsi_done(cmd); } @@ -1993,6 +2031,21 @@ static void hpsa_retry_cmd(struct ctlr_info *h, struct CommandList *c) queue_work_on(raw_smp_processor_id(), h->resubmit_wq, &c->work); } +static void hpsa_set_scsi_cmd_aborted(struct scsi_cmnd *cmd) +{ + cmd->result = DID_ABORT << 16; +} + +static void hpsa_cmd_abort_and_free(struct ctlr_info *h, struct CommandList *c, + struct scsi_cmnd *cmd) +{ + hpsa_set_scsi_cmd_aborted(cmd); + dev_warn(&h->pdev->dev, "CDB %16phN was aborted with status 0x%x\n", +c->Request.CDB, c->err_info->ScsiStatus); + hpsa_cmd_resolve_events(h, c); + cmd_free(h, c); /* FIX-ME: change to cmd_tagged_free(h, c) */ +} + static void
[PATCH v4 37/43] hpsa: use block layer tag for command allocation
From: Webb Scales Rework slave allocation: - separate the tagging support setup from the hostdata setup - make the hostdata setup act consistently when the lookup fails - make the hostdata setup act consistently when the device is not added - set up the queue depth consistently across these scenarios - if the block layer mq support is not available, explicitly enable and activate the SCSI layer tcq support (and do this at allocation-time so that the tags will be available for INQUIRY commands) Tweak slave configuration so that devices which are masked are also not attached. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 154 ++- drivers/scsi/hpsa.h |1 2 files changed, 126 insertions(+), 29 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 83d7df0..f6dddc7 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -44,6 +44,7 @@ #include #include #include +#include #include #include #include @@ -212,6 +213,9 @@ static int hpsa_compat_ioctl(struct scsi_device *dev, int cmd, static void cmd_free(struct ctlr_info *h, struct CommandList *c); static struct CommandList *cmd_alloc(struct ctlr_info *h); +static void cmd_tagged_free(struct ctlr_info *h, struct CommandList *c); +static struct CommandList *cmd_tagged_alloc(struct ctlr_info *h, + struct scsi_cmnd *scmd); static int fill_cmd(struct CommandList *c, u8 cmd, struct ctlr_info *h, void *buff, size_t size, u16 page_code, unsigned char *scsi3addr, int cmd_type); @@ -2017,11 +2021,17 @@ static void hpsa_cmd_resolve_events(struct ctlr_info *h, } } +static void hpsa_cmd_resolve_and_free(struct ctlr_info *h, + struct CommandList *c) +{ + hpsa_cmd_resolve_events(h, c); + cmd_tagged_free(h, c); +} + static void hpsa_cmd_free_and_done(struct ctlr_info *h, struct CommandList *c, struct scsi_cmnd *cmd) { - hpsa_cmd_resolve_events(h, c); - cmd_free(h, c); + hpsa_cmd_resolve_and_free(h, c); cmd->scsi_done(cmd); } @@ -2042,8 +2052,7 @@ static void hpsa_cmd_abort_and_free(struct ctlr_info *h, struct CommandList *c, hpsa_set_scsi_cmd_aborted(cmd); dev_warn(&h->pdev->dev, "CDB %16phN was aborted with status 0x%x\n", c->Request.CDB, c->err_info->ScsiStatus); - hpsa_cmd_resolve_events(h, c); - cmd_free(h, c); /* FIX-ME: change to cmd_tagged_free(h, c) */ + hpsa_cmd_resolve_and_free(h, c); } static void process_ioaccel2_completion(struct ctlr_info *h, @@ -4505,7 +4514,7 @@ static int hpsa_ciss_submit(struct ctlr_info *h, } if (hpsa_scatter_gather(h, c, cmd) < 0) { /* Fill SG list */ - cmd_free(h, c); + hpsa_cmd_resolve_and_free(h, c); return SCSI_MLQUEUE_HOST_BUSY; } enqueue_cmd_and_start_io(h, c); @@ -4551,6 +4560,8 @@ static inline void hpsa_cmd_partial_init(struct ctlr_info *h, int index, { dma_addr_t cmd_dma_handle = h->cmd_pool_dhandle + index * sizeof(*c); + BUG_ON(c->cmdindex != index); + memset(c->Request.CDB, 0, sizeof(c->Request.CDB)); memset(c->err_info, 0, sizeof(*c->err_info)); c->busaddr = (u32) cmd_dma_handle; @@ -4645,27 +4656,24 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) /* Get the ptr to our adapter structure out of cmd->host. */ h = sdev_to_hba(cmd->device); + + BUG_ON(cmd->request->tag < 0); + dev = cmd->device->hostdata; if (!dev) { cmd->result = DID_NO_CONNECT << 16; cmd->scsi_done(cmd); return 0; } - memcpy(scsi3addr, dev->scsi3addr, sizeof(scsi3addr)); - if (unlikely(lockup_detected(h))) { - cmd->result = DID_NO_CONNECT << 16; - cmd->scsi_done(cmd); - return 0; - } - c = cmd_alloc(h); + memcpy(scsi3addr, dev->scsi3addr, sizeof(scsi3addr)); if (unlikely(lockup_detected(h))) { cmd->result = DID_NO_CONNECT << 16; - cmd_free(h, c); cmd->scsi_done(cmd); return 0; } + c = cmd_tagged_alloc(h, cmd); /* * Call alternate submit routine for I/O accelerated commands. @@ -4678,7 +4686,7 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) if (rc == 0) return 0; if (rc == SCSI_MLQUEUE_HOST_BUSY) { - cmd_free(h, c); + hpsa_cmd_resolve_and_free(h, c); return SCSI_MLQUEUE_HOST_BUSY; } } @@ -4792,15 +4800,23 @@ static int hpsa_re
[PATCH v4 42/43] hpsa: add PMC to copyright
need to add PMC to copyright notice and update the Hewlett-Packard copyright notification. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Reviewed-by: Justin Lindley Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |3 ++- drivers/scsi/hpsa.h |3 ++- drivers/scsi/hpsa_cmd.h |3 ++- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 4b4df66..5fc4118 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1,6 +1,7 @@ /* *Disk Array driver for HP Smart Array SAS controllers - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. + *Copyright 2014-2015 PMC-Sierra, Inc. + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, L.P. * *This program is free software; you can redistribute it and/or modify *it under the terms of the GNU General Public License as published by diff --git a/drivers/scsi/hpsa.h b/drivers/scsi/hpsa.h index 6ee4da6..80cfc79 100644 --- a/drivers/scsi/hpsa.h +++ b/drivers/scsi/hpsa.h @@ -1,6 +1,7 @@ /* *Disk Array driver for HP Smart Array SAS controllers - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. + *Copyright 2014-2015 PMC-Sierra, Inc. + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, L.P. * *This program is free software; you can redistribute it and/or modify *it under the terms of the GNU General Public License as published by diff --git a/drivers/scsi/hpsa_cmd.h b/drivers/scsi/hpsa_cmd.h index c601622..23a8f0d 100644 --- a/drivers/scsi/hpsa_cmd.h +++ b/drivers/scsi/hpsa_cmd.h @@ -1,6 +1,7 @@ /* *Disk Array driver for HP Smart Array SAS controllers - *Copyright 2000, 2014 Hewlett-Packard Development Company, L.P. + *Copyright 2014-2015 PMC-Sierra, Inc. + *Portions Copyright 2008-2014 Hewlett-Packard Development Company, L.P. * *This program is free software; you can redistribute it and/or modify *it under the terms of the GNU General Public License as published by -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 33/43] hpsa: cleanup for init_one step 2 in kdump
From: Robert Elliott In hpsa_undo_allocations_after_kdump_soft_reset, the things allocated in hpsa_init_one step 2 - h->resubmit_wq and h->lockup_detected need to be freed, in the right order. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 10 ++ 1 file changed, 10 insertions(+) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index dc8299c..99fd4d3 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7395,6 +7395,16 @@ static void hpsa_undo_allocations_after_kdump_soft_reset(struct ctlr_info *h) hpsa_free_cmd_pool(h); /* init_one 5 */ hpsa_free_irqs(h); /* init_one 4 */ hpsa_free_pci_init(h); /* init_one 3 */ + free_percpu(h->lockup_detected);/* init_one 2 */ + h->lockup_detected = NULL; /* init_one 2 */ + if (h->resubmit_wq) { + destroy_workqueue(h->resubmit_wq); /* init_one 1 */ + h->resubmit_wq = NULL; + } + if (h->rescan_ctlr_wq) { + destroy_workqueue(h->rescan_ctlr_wq); + h->rescan_ctlr_wq = NULL; + } kfree(h); /* init_one 1 */ } -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 32/43] hpsa: skip free_irq calls if irqs are not allocated
From: Robert Elliott If try_soft_reset fails to re-allocate irqs, the error exit starts with free_irq calls, which generate kernel WARN messages since they were already freed a few lines earlier. Jump to the next exit label to skip the free_irq calls. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |7 ++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 8aeef06..dc8299c 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7773,7 +7773,12 @@ reinit_after_soft_reset: if (rc) { dev_warn(&h->pdev->dev, "Failed to request_irq after soft reset.\n"); - goto clean4; + /* +* clean4 starts with free_irqs, but that was just +* done. Then, request_irqs_failed, so there is +* nothing to free. So, goto the next label. +*/ + goto clean3; } rc = hpsa_kdump_soft_reset(h); -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 43/43] hpsa: add in new controller id
add in support for latest PMC controller Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 5fc4118..910d748 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -132,6 +132,7 @@ static const struct pci_device_id hpsa_pci_device_id[] = { {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSI, 0x103C, 0x21CC}, {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSI, 0x103C, 0x21CD}, {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSI, 0x103C, 0x21CE}, + {PCI_VENDOR_ID_ADAPTEC2, 0x0290, 0x9005, 0x0580}, {PCI_VENDOR_ID_HP_3PAR, 0x0075, 0x1590, 0x0076}, {PCI_VENDOR_ID_HP_3PAR, 0x0075, 0x1590, 0x0087}, {PCI_VENDOR_ID_HP_3PAR, 0x0075, 0x1590, 0x007D}, @@ -189,6 +190,7 @@ static struct board_type products[] = { {0x21CC103C, "Smart Array", &SA5_access}, {0x21CD103C, "Smart Array", &SA5_access}, {0x21CE103C, "Smart HBA", &SA5_access}, + {0x05809005, "SmartHBA-SA", &SA5_access}, {0x00761590, "HP Storage P1224 Array Controller", &SA5_access}, {0x00871590, "HP Storage P1224e Array Controller", &SA5_access}, {0x007D1590, "HP Storage P1228 Array Controller", &SA5_access}, -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 41/43] hpsa: change driver version
update driver version Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index a596de5..4b4df66 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -58,7 +58,7 @@ #include "hpsa.h" /* HPSA_DRIVER_VERSION must be 3 byte values (0-255) separated by '.' */ -#define HPSA_DRIVER_VERSION "3.4.4-1" +#define HPSA_DRIVER_VERSION "3.4.10-0" #define DRIVER_NAME "HP HPSA Driver (v " HPSA_DRIVER_VERSION ")" #define HPSA "hpsa" -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 30/43] hpsa: performance tweak for hpsa_scatter_gather()
From: Webb Scales Divide the loop in hpsa_scatter_gather() into two, one for the initial SG list and a second one for the chained list, if any. This allows the conditional check which resets the indicies for the chained list to be performed outside the loop instead of being done on every iteration inside the loop. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 39 --- 1 file changed, 28 insertions(+), 11 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 753026a..5e12520 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -3679,7 +3679,7 @@ static int hpsa_scatter_gather(struct ctlr_info *h, struct scsi_cmnd *cmd) { struct scatterlist *sg; - int use_sg, i, sg_index, chained; + int use_sg, i, sg_limit, chained, last_sg; struct SGDescriptor *curr_sg; BUG_ON(scsi_sg_count(cmd) > h->maxsgentries); @@ -3691,22 +3691,39 @@ static int hpsa_scatter_gather(struct ctlr_info *h, if (!use_sg) goto sglist_finished; + /* +* If the number of entries is greater than the max for a single list, +* then we have a chained list; we will set up all but one entry in the +* first list (the last entry is saved for link information); +* otherwise, we don't have a chained list and we'll set up at each of +* the entries in the one list. +*/ curr_sg = cp->SG; - chained = 0; - sg_index = 0; - scsi_for_each_sg(cmd, sg, use_sg, i) { - if (i == h->max_cmd_sg_entries - 1 && - use_sg > h->max_cmd_sg_entries) { - chained = 1; - curr_sg = h->cmd_sg_list[cp->cmdindex]; - sg_index = 0; - } + chained = use_sg > h->max_cmd_sg_entries; + sg_limit = chained ? h->max_cmd_sg_entries - 1 : use_sg; + last_sg = scsi_sg_count(cmd) - 1; + scsi_for_each_sg(cmd, sg, sg_limit, i) { hpsa_set_sg_descriptor(curr_sg, sg); curr_sg++; } + if (chained) { + /* +* Continue with the chained list. Set curr_sg to the chained +* list. Modify the limit to the total count less the entries +* we've already set up. Resume the scan at the list entry +* where the previous loop left off. +*/ + curr_sg = h->cmd_sg_list[cp->cmdindex]; + sg_limit = use_sg - sg_limit; + for_each_sg(sg, sg, sg_limit, i) { + hpsa_set_sg_descriptor(curr_sg, sg); + curr_sg++; + } + } + /* Back the pointer up to the last entry and mark it as "last". */ - (--curr_sg)->Ext = cpu_to_le32(HPSA_SG_LAST); + (curr_sg - 1)->Ext = cpu_to_le32(HPSA_SG_LAST); if (use_sg + chained > h->maxSG) h->maxSG = use_sg + chained; -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 40/43] hpsa: cleanup reset
From: Webb Scales Synchronize completion the reset with completion of outstanding commands Extending the newly-added synchronous abort functionality, now also synchronize resets with the completion of outstanding commands. Rename the wait queue to reflect the fact that it's being used for both types of waits. Also, don't complete commands which are terminated due to a reset operation. fix for controller lockup during reset Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 204 +-- drivers/scsi/hpsa.h |5 + drivers/scsi/hpsa_cmd.h |1 3 files changed, 182 insertions(+), 28 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index f36ab70..a596de5 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -283,6 +283,11 @@ static inline bool hpsa_is_cmd_idle(struct CommandList *c) return c->scsi_cmd == SCSI_CMD_IDLE; } +static inline bool hpsa_is_pending_event(struct CommandList *c) +{ + return c->abort_pending || c->reset_pending; +} + /* extract sense key, asc, and ascq from sense data. -1 means invalid. */ static void decode_sense_data(const u8 *sense_data, int sense_data_len, int *sense_key, int *asc, int *ascq) @@ -977,7 +982,7 @@ static void __enqueue_cmd_and_start_io(struct ctlr_info *h, static void enqueue_cmd_and_start_io(struct ctlr_info *h, struct CommandList *c) { - if (unlikely(c->abort_pending)) + if (unlikely(hpsa_is_pending_event(c))) return finish_cmd(c); __enqueue_cmd_and_start_io(h, c, DEFAULT_REPLY_QUEUE); @@ -1449,6 +1454,8 @@ static void hpsa_figure_phys_disk_ptrs(struct ctlr_info *h, if (nraid_map_entries > RAID_MAP_MAX_ENTRIES) nraid_map_entries = RAID_MAP_MAX_ENTRIES; + logical_drive->nphysical_disks = nraid_map_entries; + qdepth = 0; for (i = 0; i < nraid_map_entries; i++) { logical_drive->phys_disk[i] = NULL; @@ -2001,6 +2008,8 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, static void hpsa_cmd_resolve_events(struct ctlr_info *h, struct CommandList *c) { + bool do_wake = false; + /* * Prevent the following race in the abort handler: * @@ -2012,16 +2021,35 @@ static void hpsa_cmd_resolve_events(struct ctlr_info *h, *finds struct CommandList and tries to aborts it * Now we have aborted the wrong command. * -* Clear c->scsi_cmd here so that the abort handler will know this -* command has completed. Then, check to see if the abort handler is +* Reset c->scsi_cmd here so that the abort or reset handler will know +* this command has completed. Then, check to see if the handler is * waiting for this command, and, if so, wake it. */ c->scsi_cmd = SCSI_CMD_IDLE; - mb(); /* Ensure c->scsi_cmd is set to SCSI_CMD_IDLE */ + mb(); /* Declare command idle before checking for pending events. */ if (c->abort_pending) { + do_wake = true; c->abort_pending = false; - wake_up_all(&h->abort_sync_wait_queue); } + if (c->reset_pending) { + unsigned long flags; + struct hpsa_scsi_dev_t *dev; + + /* +* There appears to be a reset pending; lock the lock and +* reconfirm. If so, then decrement the count of outstanding +* commands and wake the reset command if this is the last one. +*/ + spin_lock_irqsave(&h->lock, flags); + dev = c->reset_pending; /* Re-fetch under the lock. */ + if (dev && atomic_dec_and_test(&dev->reset_cmds_out)) + do_wake = true; + c->reset_pending = NULL; + spin_unlock_irqrestore(&h->lock, flags); + } + + if (do_wake) + wake_up_all(&h->event_sync_wait_queue); } static void hpsa_cmd_resolve_and_free(struct ctlr_info *h, @@ -2069,10 +2097,6 @@ static void process_ioaccel2_completion(struct ctlr_info *h, c2->error_data.status == 0)) return hpsa_cmd_free_and_done(h, c, cmd); - /* don't requeue a command which is being aborted */ - if (unlikely(c->abort_pending)) - return hpsa_cmd_abort_and_free(h, c, cmd); - /* * Any RAID offload error results in retry which will use * the normal I/O path so the controller can handle whatever's @@ -2167,6 +2191,13 @@ static void complete_scsi_command(struct CommandList *cp) return hpsa_cmd_free_and_done(h, cp, cmd); } + if ((unlikely(hpsa_is_pending_event(cp { + if (cp->reset_pending) + return hpsa_cmd_resolve_an
[PATCH v4 27/43] hpsa: use helper routines for finishing commands
From: Webb Scales cleanup command completions Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 78 --- 1 file changed, 31 insertions(+), 47 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 3f86a61..678b2bf 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1980,6 +1980,19 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, return retry; /* retry on raid path? */ } +static void hpsa_cmd_free_and_done(struct ctlr_info *h, + struct CommandList *c, struct scsi_cmnd *cmd) +{ + cmd_free(h, c); + cmd->scsi_done(cmd); +} + +static void hpsa_retry_cmd(struct ctlr_info *h, struct CommandList *c) +{ + INIT_WORK(&c->work, hpsa_command_resubmit_worker); + queue_work_on(raw_smp_processor_id(), h->resubmit_wq, &c->work); +} + static void process_ioaccel2_completion(struct ctlr_info *h, struct CommandList *c, struct scsi_cmnd *cmd, struct hpsa_scsi_dev_t *dev) @@ -1988,13 +2001,11 @@ static void process_ioaccel2_completion(struct ctlr_info *h, /* check for good status */ if (likely(c2->error_data.serv_response == 0 && - c2->error_data.status == 0)) { - cmd_free(h, c); - cmd->scsi_done(cmd); - return; - } + c2->error_data.status == 0)) + return hpsa_cmd_free_and_done(h, c, cmd); - /* Any RAID offload error results in retry which will use + /* +* Any RAID offload error results in retry which will use * the normal I/O path so the controller can handle whatever's * wrong. */ @@ -2004,19 +2015,14 @@ static void process_ioaccel2_completion(struct ctlr_info *h, if (c2->error_data.status == IOACCEL2_STATUS_SR_IOACCEL_DISABLED) dev->offload_enabled = 0; - goto retry_cmd; + + return hpsa_retry_cmd(h, c); } if (handle_ioaccel_mode2_error(h, c, cmd, c2)) - goto retry_cmd; - - cmd_free(h, c); - cmd->scsi_done(cmd); - return; + return hpsa_retry_cmd(h, c); -retry_cmd: - INIT_WORK(&c->work, hpsa_command_resubmit_worker); - queue_work_on(raw_smp_processor_id(), h->resubmit_wq, &c->work); + return hpsa_cmd_free_and_done(h, c, cmd); } /* Returns 0 on success, < 0 otherwise. */ @@ -2089,22 +2095,15 @@ static void complete_scsi_command(struct CommandList *cp) if (unlikely(ei->CommandStatus == CMD_CTLR_LOCKUP)) { /* DID_NO_CONNECT will prevent a retry */ cmd->result = DID_NO_CONNECT << 16; - cmd_free(h, cp); - cmd->scsi_done(cmd); - return; + return hpsa_cmd_free_and_done(h, cp, cmd); } if (cp->cmd_type == CMD_IOACCEL2) return process_ioaccel2_completion(h, cp, cmd, dev); scsi_set_resid(cmd, ei->ResidualCnt); - if (ei->CommandStatus == 0) { - if (cp->cmd_type == CMD_IOACCEL1) - atomic_dec(&cp->phys_disk->ioaccel_cmds_out); - cmd_free(h, cp); - cmd->scsi_done(cmd); - return; - } + if (ei->CommandStatus == 0) + return hpsa_cmd_free_and_done(h, cp, cmd); /* For I/O accelerator commands, copy over some fields to the normal * CISS header used below for error handling. @@ -2126,10 +2125,7 @@ static void complete_scsi_command(struct CommandList *cp) if (is_logical_dev_addr_mode(dev->scsi3addr)) { if (ei->CommandStatus == CMD_IOACCEL_DISABLED) dev->offload_enabled = 0; - INIT_WORK(&cp->work, hpsa_command_resubmit_worker); - queue_work_on(raw_smp_processor_id(), - h->resubmit_wq, &cp->work); - return; + return hpsa_retry_cmd(h, cp); } } @@ -2260,8 +2256,8 @@ static void complete_scsi_command(struct CommandList *cp) dev_warn(&h->pdev->dev, "cp %p returned unknown status %x\n", cp, ei->CommandStatus); } - cmd_free(h, cp); - cmd->scsi_done(cmd); + + return hpsa_cmd_free_and_done(h, cp, cmd); } static void hpsa_pci_unmap(struct pci_dev *pdev, @@ -4514,16 +4510,13 @@ static void hpsa_command_resubmit_worker(struct work_struct *work) { struct scsi_cmnd *cmd; struct hpsa_scsi_dev_t *dev; - struct CommandList *c = - container_of(work, struct CommandList, work); + struct CommandList *c = container_of(work, struct CommandList, work);
[PATCH v4 38/43] hpsa: use scsi host_no as hpsa controller number
From: Robert Elliott Rather than numbering the hpsa controllers with an incrementing 0..n value (e.g., that shows up in /proc/interrupts), use the scsi midlayer host_no (e.g. matching /sys/class/scsi_host/hostNN). Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 134 --- 1 file changed, 74 insertions(+), 60 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index f6dddc7..f65333d 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -324,32 +324,35 @@ static int check_for_unit_attention(struct ctlr_info *h, switch (asc) { case STATE_CHANGED: dev_warn(&h->pdev->dev, - HPSA "%d: a state change detected, command retried\n", - h->ctlr); + "%s: a state change detected, command retried\n", + h->devname); break; case LUN_FAILED: dev_warn(&h->pdev->dev, - HPSA "%d: LUN failure detected\n", h->ctlr); + "%s: LUN failure detected\n", h->devname); break; case REPORT_LUNS_CHANGED: dev_warn(&h->pdev->dev, - HPSA "%d: report LUN data changed\n", h->ctlr); + "%s: report LUN data changed\n", h->devname); /* * Note: this REPORT_LUNS_CHANGED condition only occurs on the external * target (array) devices. */ break; case POWER_OR_RESET: - dev_warn(&h->pdev->dev, HPSA "%d: a power on " - "or device reset detected\n", h->ctlr); + dev_warn(&h->pdev->dev, + "%s: a power on or device reset detected\n", + h->devname); break; case UNIT_ATTENTION_CLEARED: - dev_warn(&h->pdev->dev, HPSA "%d: unit attention " - "cleared by another initiator\n", h->ctlr); + dev_warn(&h->pdev->dev, + "%s: unit attention cleared by another initiator\n", + h->devname); break; default: - dev_warn(&h->pdev->dev, HPSA "%d: unknown " - "unit attention detected\n", h->ctlr); + dev_warn(&h->pdev->dev, + "%s: unknown unit attention detected\n", + h->devname); break; } return 1; @@ -4769,22 +4772,16 @@ static int hpsa_scan_finished(struct Scsi_Host *sh, return finished; } -static void hpsa_unregister_scsi(struct ctlr_info *h) -{ - /* we are being forcibly unloaded, and may not refuse. */ - scsi_remove_host(h->scsi_host); - scsi_host_put(h->scsi_host); - h->scsi_host = NULL; -} - -static int hpsa_register_scsi(struct ctlr_info *h) +static int hpsa_scsi_host_alloc(struct ctlr_info *h) { struct Scsi_Host *sh; int error; sh = scsi_host_alloc(&hpsa_driver_template, sizeof(h)); - if (sh == NULL) - goto fail; + if (sh == NULL) { + dev_err(&h->pdev->dev, "scsi_host_alloc failed\n"); + return -ENOMEM; + } sh->io_port = 0; sh->n_io_port = 0; @@ -4796,7 +4793,6 @@ static int hpsa_register_scsi(struct ctlr_info *h) sh->can_queue = h->nr_cmds - HPSA_NRESERVED_CMDS; sh->cmd_per_lun = sh->can_queue; sh->sg_tablesize = h->maxsgentries; - h->scsi_host = sh; sh->hostdata[0] = (unsigned long) h; sh->irq = h->intr[h->intr_mode]; sh->unique_id = sh->irq; @@ -4805,24 +4801,24 @@ static int hpsa_register_scsi(struct ctlr_info *h) dev_err(&h->pdev->dev, "%s: scsi_init_shared_tag_map failed for controller %d\n", __func__, h->ctlr); - goto fail_host_put; - } - error = scsi_add_host(sh, &h->pdev->dev); - if (error) { - dev_err(&h->pdev->dev, "%s: scsi_add_host failed for controller %d\n", - __func__, h->ctlr); - goto fail_host_put; + scsi_host_put(sh); + return error; } - scsi_scan_host(sh); + h->scsi_host = sh; return 0; +} - fail_host_put: - scsi_host_put(sh); - return error; - fail: - dev_err(&h->pdev->dev, "%s: scsi_host_alloc" - " failed for controller %d\n", __func__, h->ctlr); - return -ENOMEM; +static int hpsa_scsi_add_host(struct ctlr_info *h) +{ + int rv; + + rv = scsi_add_host(h->scsi_host, &h->pdev->dev); + if (rv) { + dev_err(&h->pdev->dev, "scsi_add_host failed\n"); + return rv; + } + scsi_scan_host(h->scsi_host); +
[PATCH v4 25/43] hpsa: do not print ioaccel2 warning messages about unusual completions.
From: Robert Elliott The SCSI midlayer already prints more detail about completions, and has logging level options to filter them if not wanted. These just slow down the system if a lot of errors occur, stressing error handling even more. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 24 1 file changed, 24 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 15c5b81..3bbd579 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1876,9 +1876,6 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, case IOACCEL2_STATUS_SR_TASK_COMP_GOOD: break; case IOACCEL2_STATUS_SR_TASK_COMP_CHK_COND: - dev_warn(&h->pdev->dev, - "%s: task complete with check condition.\n", - "HP SSD Smart Path"); cmd->result |= SAM_STAT_CHECK_CONDITION; if (c2->error_data.data_present != IOACCEL2_SENSE_DATA_PRESENT) { @@ -1898,30 +1895,18 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_BUSY: - dev_warn(&h->pdev->dev, - "%s: task complete with BUSY status.\n", - "HP SSD Smart Path"); retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_RES_CON: - dev_warn(&h->pdev->dev, - "%s: task complete with reservation conflict.\n", - "HP SSD Smart Path"); retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_SET_FULL: retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_ABORTED: - dev_warn(&h->pdev->dev, - "%s: task complete with aborted status.\n", - "HP SSD Smart Path"); retry = 1; break; default: - dev_warn(&h->pdev->dev, - "%s: task complete with unrecognized status: 0x%02x\n", - "HP SSD Smart Path", c2->error_data.status); retry = 1; break; } @@ -1950,9 +1935,6 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, break; default: retry = 1; - dev_warn(&h->pdev->dev, - "unexpected delivery or target failure, status = 0x%02x\n", - c2->error_data.status); } break; case IOACCEL2_SERV_RESPONSE_TMF_COMPLETE: @@ -1960,17 +1942,11 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, case IOACCEL2_SERV_RESPONSE_TMF_SUCCESS: break; case IOACCEL2_SERV_RESPONSE_TMF_REJECTED: - dev_warn(&h->pdev->dev, "task management function rejected.\n"); retry = 1; break; case IOACCEL2_SERV_RESPONSE_TMF_WRONG_LUN: - dev_warn(&h->pdev->dev, "task management function invalid LUN\n"); break; default: - dev_warn(&h->pdev->dev, - "%s: Unrecognized server response: 0x%02x\n", - "HP SSD Smart Path", - c2->error_data.serv_response); retry = 1; break; } -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 26/43] hpsa: add support sending aborts to physical devices via the ioaccel2 path
From: Stephen Cameron add support for tmf when in ioaccel2 mode Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Joe Handzik Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 136 +-- drivers/scsi/hpsa.h |1 drivers/scsi/hpsa_cmd.h |6 +- 3 files changed, 135 insertions(+), 8 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 3bbd579..3f86a61 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -861,6 +861,28 @@ static void set_ioaccel1_performant_mode(struct ctlr_info *h, IOACCEL1_BUSADDR_CMDTYPE; } +static void set_ioaccel2_tmf_performant_mode(struct ctlr_info *h, + struct CommandList *c, + int reply_queue) +{ + struct hpsa_tmf_struct *cp = (struct hpsa_tmf_struct *) + &h->ioaccel2_cmd_pool[c->cmdindex]; + + /* Tell the controller to post the reply to the queue for this +* processor. This seems to give the best I/O throughput. +*/ + if (likely(reply_queue == DEFAULT_REPLY_QUEUE)) + cp->reply_queue = smp_processor_id() % h->nreply_queues; + else + cp->reply_queue = reply_queue % h->nreply_queues; + /* Set the bits in the address sent down to include: +* - performant mode bit not used in ioaccel mode 2 +* - pull count (bits 0-3) +* - command type isn't needed for ioaccel2 +*/ + c->busaddr |= h->ioaccel2_blockFetchTable[0]; +} + static void set_ioaccel2_performant_mode(struct ctlr_info *h, struct CommandList *c, int reply_queue) @@ -927,6 +949,10 @@ static void __enqueue_cmd_and_start_io(struct ctlr_info *h, set_ioaccel2_performant_mode(h, c, reply_queue); writel(c->busaddr, h->vaddr + IOACCEL2_INBOUND_POSTQ_32); break; + case IOACCEL2_TMF: + set_ioaccel2_tmf_performant_mode(h, c, reply_queue); + writel(c->busaddr, h->vaddr + IOACCEL2_INBOUND_POSTQ_32); + break; default: set_performant_mode(h, c, reply_queue); h->access.submit_command(h, c); @@ -4924,6 +4950,47 @@ static int hpsa_send_abort(struct ctlr_info *h, unsigned char *scsi3addr, return rc; } +static void setup_ioaccel2_abort_cmd(struct CommandList *c, struct ctlr_info *h, + struct CommandList *command_to_abort, int reply_queue) +{ + struct io_accel2_cmd *c2 = &h->ioaccel2_cmd_pool[c->cmdindex]; + struct hpsa_tmf_struct *ac = (struct hpsa_tmf_struct *) c2; + struct io_accel2_cmd *c2a = + &h->ioaccel2_cmd_pool[command_to_abort->cmdindex]; + struct scsi_cmnd *scmd = + (struct scsi_cmnd *) command_to_abort->scsi_cmd; + struct hpsa_scsi_dev_t *dev = scmd->device->hostdata; + + /* +* We're overlaying struct hpsa_tmf_struct on top of something which +* was allocated as a struct io_accel2_cmd, so we better be sure it +* actually fits, and doesn't overrun the error info space. +*/ + BUILD_BUG_ON(sizeof(struct hpsa_tmf_struct) > + sizeof(struct io_accel2_cmd)); + BUG_ON(offsetof(struct io_accel2_cmd, error_data) < + offsetof(struct hpsa_tmf_struct, error_len) + + sizeof(ac->error_len)); + + c->cmd_type = IOACCEL2_TMF; + /* Adjust the DMA address to point to the accelerated command buffer */ + c->busaddr = (u32) h->ioaccel2_cmd_pool_dhandle + + (c->cmdindex * sizeof(struct io_accel2_cmd)); + BUG_ON(c->busaddr & 0x007F); + + memset(ac, 0, sizeof(*c2)); /* yes this is correct */ + ac->iu_type = IOACCEL2_IU_TMF_TYPE; + ac->reply_queue = reply_queue; + ac->tmf = IOACCEL2_TMF_ABORT; + ac->it_nexus = cpu_to_le32(dev->ioaccel_handle); + memset(ac->lun_id, 0, sizeof(ac->lun_id)); + ac->tag = cpu_to_le64(c->cmdindex << DIRECT_LOOKUP_SHIFT); + ac->abort_tag = cpu_to_le64(le32_to_cpu(c2a->Tag)); + ac->error_ptr = cpu_to_le64(c->busaddr + + offsetof(struct io_accel2_cmd, error_data)); + ac->error_len = cpu_to_le32(sizeof(c2->error_data)); +} + /* ioaccel2 path firmware cannot handle abort task requests. * Change abort requests to physical target reset, and send to the * address of the physical disk used for the ioaccel 2 command. @@ -5002,17 +5069,72 @@ static int hpsa_send_reset_as_abort_ioaccel2(struct ctlr_info *h, return rc; /* success */ } +static int hpsa_send_abort_ioaccel2(struct ctlr_info *h, + struct CommandList *abort, int reply_queue) +{ + int rc = IO_OK; + struct CommandList *c; +
[PATCH v4 12/43] hpsa: factor out hpsa_ioaccel_submit function
From: Webb Scales clean up command submission Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 91 +-- 1 file changed, 66 insertions(+), 25 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 9c184d1..b342788 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -4378,6 +4378,33 @@ static inline void hpsa_cmd_partial_init(struct ctlr_info *h, int index, c->busaddr = (u32) cmd_dma_handle; } +static int hpsa_ioaccel_submit(struct ctlr_info *h, + struct CommandList *c, struct scsi_cmnd *cmd, + unsigned char *scsi3addr) +{ + struct hpsa_scsi_dev_t *dev = cmd->device->hostdata; + int rc = IO_ACCEL_INELIGIBLE; + + cmd->host_scribble = (unsigned char *) c; + + if (dev->offload_enabled) { + hpsa_cmd_init(h, c->cmdindex, c); + c->cmd_type = CMD_SCSI; + c->scsi_cmd = cmd; + rc = hpsa_scsi_ioaccel_raid_map(h, c); + if (rc < 0) /* scsi_dma_map failed. */ + rc = SCSI_MLQUEUE_HOST_BUSY; + } else if (dev->ioaccel_handle) { + hpsa_cmd_init(h, c->cmdindex, c); + c->cmd_type = CMD_SCSI; + c->scsi_cmd = cmd; + rc = hpsa_scsi_ioaccel_direct_map(h, c); + if (rc < 0) /* scsi_dma_map failed. */ + rc = SCSI_MLQUEUE_HOST_BUSY; + } + return rc; +} + static void hpsa_command_resubmit_worker(struct work_struct *work) { struct scsi_cmnd *cmd; @@ -4389,15 +4416,46 @@ static void hpsa_command_resubmit_worker(struct work_struct *work) dev = cmd->device->hostdata; if (!dev) { cmd->result = DID_NO_CONNECT << 16; + cmd_free(c->h, c); cmd->scsi_done(cmd); return; } + if (c->cmd_type == CMD_IOACCEL2) { + struct ctlr_info *h = c->h; + struct io_accel2_cmd *c2 = &h->ioaccel2_cmd_pool[c->cmdindex]; + int rc; + + if (c2->error_data.serv_response == + IOACCEL2_STATUS_SR_TASK_COMP_SET_FULL) { + rc = hpsa_ioaccel_submit(h, c, cmd, dev->scsi3addr); + if (rc == 0) + return; + if (rc == SCSI_MLQUEUE_HOST_BUSY) { + /* +* If we get here, it means dma mapping failed. +* Try again via scsi mid layer, which will +* then get SCSI_MLQUEUE_HOST_BUSY. +*/ + cmd->result = DID_IMM_RETRY << 16; + cmd->scsi_done(cmd); + cmd_free(h, c); /* FIX-ME: on merge, change +* to cmd_tagged_free() and +* ultimately to +* hpsa_cmd_free_and_done(). */ + return; + } + /* else, fall thru and resubmit down CISS path */ + } + } hpsa_cmd_partial_init(c->h, c->cmdindex, c); if (hpsa_ciss_submit(c->h, c, cmd, dev->scsi3addr)) { /* * If we get here, it means dma mapping failed. Try * again via scsi mid layer, which will then get * SCSI_MLQUEUE_HOST_BUSY. +* +* hpsa_ciss_submit will have already freed c +* if it encountered a dma mapping failure. */ cmd->result = DID_IMM_RETRY << 16; cmd->scsi_done(cmd); @@ -4447,31 +4505,14 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) if (likely(cmd->retries == 0 && cmd->request->cmd_type == REQ_TYPE_FS && h->acciopath_status)) { - - cmd->host_scribble = (unsigned char *) c; - - if (dev->offload_enabled) { - hpsa_cmd_init(h, c->cmdindex, c); - c->cmd_type = CMD_SCSI; - c->scsi_cmd = cmd; - rc = hpsa_scsi_ioaccel_raid_map(h, c); - if (rc == 0) - return 0; /* Sent on ioaccel path */ - if (rc < 0) { /* scsi_dma_map failed. */ - cmd_free(h, c); - return SCSI_MLQUEUE_HOST_BUSY; - } - } else if (dev->ioaccel_handle) { - hpsa_cmd_init(h, c->cmdindex, c); - c->cmd_type = CMD_SCSI; -
[PATCH v4 08/43] hpsa: make function names consistent
From: Robert Elliott make function names more consistent and meaningful Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 14 -- 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index adc0ad3..a9a301c 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -6790,7 +6790,7 @@ out_disable: return rc; } -static int hpsa_allocate_cmd_pool(struct ctlr_info *h) +static int hpsa_alloc_cmd_pool(struct ctlr_info *h) { h->cmd_pool_bits = kzalloc( DIV_ROUND_UP(h->nr_cmds, BITS_PER_LONG) * @@ -7321,7 +7321,7 @@ reinit_after_soft_reset: dev_info(&pdev->dev, "%s: <0x%x> at IRQ %d%s using DAC\n", h->devname, pdev->device, h->intr[h->intr_mode], dac ? "" : " not"); - rc = hpsa_allocate_cmd_pool(h); + rc = hpsa_alloc_cmd_pool(h); if (rc) goto clean2_and_free_irqs; if (hpsa_allocate_sg_chain_blocks(h)) @@ -7768,7 +7768,8 @@ static int hpsa_enter_performant_mode(struct ctlr_info *h, u32 trans_support) return 0; } -static int hpsa_alloc_ioaccel_cmd_and_bft(struct ctlr_info *h) +/* Allocate ioaccel1 mode command blocks and block fetch table */ +static int hpsa_alloc_ioaccel1_cmd_and_bft(struct ctlr_info *h) { h->ioaccel_maxsg = readl(&(h->cfgtable->io_accel_max_embedded_sg_count)); @@ -7807,7 +7808,8 @@ clean_up: return 1; } -static int ioaccel2_alloc_cmds_and_bft(struct ctlr_info *h) +/* Allocate ioaccel2 mode command blocks and block fetch table */ +static int hpsa_alloc_ioaccel2_cmd_and_bft(struct ctlr_info *h) { /* Allocate ioaccel2 mode command blocks and block fetch table */ @@ -7862,13 +7864,13 @@ static void hpsa_put_ctlr_into_performant_mode(struct ctlr_info *h) if (trans_support & CFGTBL_Trans_io_accel1) { transMethod |= CFGTBL_Trans_io_accel1 | CFGTBL_Trans_enable_directed_msix; - if (hpsa_alloc_ioaccel_cmd_and_bft(h)) + if (hpsa_alloc_ioaccel1_cmd_and_bft(h)) goto clean_up; } else { if (trans_support & CFGTBL_Trans_io_accel2) { transMethod |= CFGTBL_Trans_io_accel2 | CFGTBL_Trans_enable_directed_msix; - if (ioaccel2_alloc_cmds_and_bft(h)) + if (hpsa_alloc_ioaccel2_cmd_and_bft(h)) goto clean_up; } } -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 17/43] hpsa: clean up error handling
From: Robert Elliott refactor error cleanup and shutdown disable interrupts and pci_disable_device on critical failures add hpsa_free_cfgtables function Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 92 --- 1 file changed, 58 insertions(+), 34 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index b743f1a..9e26eb0 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -6519,6 +6519,17 @@ static int hpsa_find_cfg_addrs(struct pci_dev *pdev, void __iomem *vaddr, return 0; } +static void hpsa_free_cfgtables(struct ctlr_info *h) +{ + if (h->transtable) + iounmap(h->transtable); + if (h->cfgtable) + iounmap(h->cfgtable); +} + +/* Find and map CISS config table and transfer table ++ * several items must be unmapped (freed) later ++ * */ static int hpsa_find_cfgtables(struct ctlr_info *h) { u64 cfg_offset; @@ -6545,8 +6556,11 @@ static int hpsa_find_cfgtables(struct ctlr_info *h) h->transtable = remap_pci_mem(pci_resource_start(h->pdev, cfg_base_addr_index)+cfg_offset+trans_offset, sizeof(*h->transtable)); - if (!h->transtable) + if (!h->transtable) { + dev_err(&h->pdev->dev, "Failed mapping transfer table\n"); + hpsa_free_cfgtables(h); return -ENOMEM; + } return 0; } @@ -6722,6 +6736,17 @@ error: return -ENODEV; } +/* free items allocated or mapped by hpsa_pci_init */ +static void hpsa_free_pci_init(struct ctlr_info *h) +{ + hpsa_free_cfgtables(h); /* pci_init 4 */ + iounmap(h->vaddr); /* pci_init 3 */ + hpsa_disable_interrupt_mode(h); /* pci_init 2 */ + pci_release_regions(h->pdev); /* pci_init 2 */ + pci_disable_device(h->pdev);/* pci_init 1 */ +} + +/* several items must be freed later */ static int hpsa_pci_init(struct ctlr_info *h) { int prod_index, err; @@ -6740,15 +6765,15 @@ static int hpsa_pci_init(struct ctlr_info *h) err = pci_enable_device(h->pdev); if (err) { - dev_warn(&h->pdev->dev, "unable to enable PCI device\n"); + dev_err(&h->pdev->dev, "failed to enable PCI device\n"); return err; } err = pci_request_regions(h->pdev, HPSA); if (err) { dev_err(&h->pdev->dev, - "cannot obtain PCI resources, aborting\n"); - return err; + "failed to obtain PCI resources\n"); + goto clean1;/* pci */ } pci_set_master(h->pdev); @@ -6756,40 +6781,41 @@ static int hpsa_pci_init(struct ctlr_info *h) hpsa_interrupt_mode(h); err = hpsa_pci_find_memory_BAR(h->pdev, &h->paddr); if (err) - goto err_out_free_res; + goto clean2;/* intmode+region, pci */ h->vaddr = remap_pci_mem(h->paddr, 0x250); if (!h->vaddr) { + dev_err(&h->pdev->dev, "failed to remap PCI mem\n"); err = -ENOMEM; - goto err_out_free_res; + goto clean2;/* intmode+region, pci */ } err = hpsa_wait_for_board_state(h->pdev, h->vaddr, BOARD_READY); if (err) - goto err_out_free_res; + goto clean3;/* vaddr, intmode+region, pci */ err = hpsa_find_cfgtables(h); if (err) - goto err_out_free_res; + goto clean3;/* vaddr, intmode+region, pci */ hpsa_find_board_params(h); if (!hpsa_CISS_signature_present(h)) { err = -ENODEV; - goto err_out_free_res; + goto clean4;/* cfgtables, vaddr, intmode+region, pci */ } hpsa_set_driver_support_bits(h); hpsa_p600_dma_prefetch_quirk(h); err = hpsa_enter_simple_mode(h); if (err) - goto err_out_free_res; + goto clean4;/* cfgtables, vaddr, intmode+region, pci */ return 0; -err_out_free_res: - if (h->transtable) - iounmap(h->transtable); - if (h->cfgtable) - iounmap(h->cfgtable); - if (h->vaddr) - iounmap(h->vaddr); - pci_disable_device(h->pdev); +clean4:/* cfgtables, vaddr, intmode+region, pci */ + hpsa_free_cfgtables(h); +clean3:/* vaddr, intmode+region, pci */ + iounmap(h->vaddr); +clean2:/* intmode+region, pci */ + hpsa_disable_interrupt_mode(h); pci_release_regions(h->pdev); +clean1:/* pci */ + pci_disable_device(h->pdev); return err; } @@ -6998,8 +7024,9 @@ static int hpsa_request_irqs(struct ctlr_info *h, } }
[PATCH v4 07/43] hpsa: allow lockup detected to be viewed via sysfs
From: Stephen Cameron expose a detected lockup via sysfs Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 17 + 1 file changed, 17 insertions(+) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 68238dd..adc0ad3 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -351,6 +351,20 @@ static int check_for_busy(struct ctlr_info *h, struct CommandList *c) return 1; } +static u32 lockup_detected(struct ctlr_info *h); +static ssize_t host_show_lockup_detected(struct device *dev, + struct device_attribute *attr, char *buf) +{ + int ld; + struct ctlr_info *h; + struct Scsi_Host *shost = class_to_shost(dev); + + h = shost_to_hba(shost); + ld = lockup_detected(h); + + return sprintf(buf, "ld=%d\n", ld); +} + static ssize_t host_store_hp_ssd_smart_path_status(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) @@ -698,12 +712,15 @@ static DEVICE_ATTR(transport_mode, S_IRUGO, host_show_transport_mode, NULL); static DEVICE_ATTR(resettable, S_IRUGO, host_show_resettable, NULL); +static DEVICE_ATTR(lockup_detected, S_IRUGO, + host_show_lockup_detected, NULL); static struct device_attribute *hpsa_sdev_attrs[] = { &dev_attr_raid_level, &dev_attr_lunid, &dev_attr_unique_id, &dev_attr_hp_ssd_smart_path_enabled, + &dev_attr_lockup_detected, NULL, }; -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 04/43] hpsa: clean up aborts
From: Stephen Cameron Do not send aborts to logical devices that do not support aborts Instead of relying on what the Smart Array claims for supporting logical drives, simply try an abort and see how it responds at device discovery time. This way devices that do support aborts (e.g. MSA2000) can work and we do not waste time trying to send aborts to logical drives that do not support them (important for high IOPS devices.) While rescanning devices only test whether devices support aborts the first time we encounter a device rather than every time. Some Smart Arrays required aborts to be sent with tags in the wrong endian byte order. To avoid having to know about this, we would send two aborts with tags with each endian order. On high IOPS devices, this turns out to be not such a hot idea. So we now have a list of the devices that got the tag backwards, and we only send it one way. If all available commands are outstanding and the abort handler is invoked, the abort handler may not be able to allocate a command and may busy-wait excessivly. Reserve a small number of commands for the abort handler and limit the number of concurrent abort requests to the number of reserved commands. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 176 +-- drivers/scsi/hpsa.h |4 + 2 files changed, 147 insertions(+), 33 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index b81e5e4..2ac700b 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -428,7 +428,7 @@ static ssize_t host_show_hp_ssd_smart_path_status(struct device *dev, /* List of controllers which cannot be hard reset on kexec with reset_devices */ static u32 unresettable_controller[] = { 0x324a103C, /* Smart Array P712m */ - 0x324b103C, /* SmartArray P711m */ + 0x324b103C, /* Smart Array P711m */ 0x3223103C, /* Smart Array P800 */ 0x3234103C, /* Smart Array P400 */ 0x3235103C, /* Smart Array P400i */ @@ -470,24 +470,32 @@ static u32 soft_unresettable_controller[] = { 0x409D0E11, /* Smart Array 6400 EM */ }; -static int ctlr_is_hard_resettable(u32 board_id) +static u32 needs_abort_tags_swizzled[] = { + 0x323D103C, /* Smart Array P700m */ + 0x324a103C, /* Smart Array P712m */ + 0x324b103C, /* SmartArray P711m */ +}; + +static int board_id_in_array(u32 a[], int nelems, u32 board_id) { int i; - for (i = 0; i < ARRAY_SIZE(unresettable_controller); i++) - if (unresettable_controller[i] == board_id) - return 0; - return 1; + for (i = 0; i < nelems; i++) + if (a[i] == board_id) + return 1; + return 0; } -static int ctlr_is_soft_resettable(u32 board_id) +static int ctlr_is_hard_resettable(u32 board_id) { - int i; + return !board_id_in_array(unresettable_controller, + ARRAY_SIZE(unresettable_controller), board_id); +} - for (i = 0; i < ARRAY_SIZE(soft_unresettable_controller); i++) - if (soft_unresettable_controller[i] == board_id) - return 0; - return 1; +static int ctlr_is_soft_resettable(u32 board_id) +{ + return !board_id_in_array(soft_unresettable_controller, + ARRAY_SIZE(soft_unresettable_controller), board_id); } static int ctlr_is_resettable(u32 board_id) @@ -496,6 +504,12 @@ static int ctlr_is_resettable(u32 board_id) ctlr_is_soft_resettable(board_id); } +static int ctlr_needs_abort_tags_swizzled(u32 board_id) +{ + return board_id_in_array(needs_abort_tags_swizzled, + ARRAY_SIZE(needs_abort_tags_swizzled), board_id); +} + static ssize_t host_show_resettable(struct device *dev, struct device_attribute *attr, char *buf) { @@ -2808,6 +2822,50 @@ static int hpsa_volume_offline(struct ctlr_info *h, return 0; } +/* + * Find out if a logical device supports aborts by simply trying one. + * Smart Array may claim not to support aborts on logical drives, but + * if a MSA2000 * is connected, the drives on that will be presented + * by the Smart Array as logical drives, and aborts may be sent to + * those devices successfully. So the simplest way to find out is + * to simply try an abort and see how the device responds. + */ +static int hpsa_device_supports_aborts(struct ctlr_info *h, + unsigned char *scsi3addr) +{ + struct CommandList *c; + struct ErrorInfo *ei; + int rc = 0; + + u64 tag = (u64) -1; /* bogus tag */ + + /* Assume that physical devices support aborts */ + if (!is_logical_dev_addr_mode(scsi3addr)) + return 1; + + c = cmd_alloc(h); + if (!c) + return -ENOMEM; + (void) fill_cmd(c, HPSA_ABORT_MSG, h, &tag, 0, 0, scsi3addr, TYPE_MSG); +
[PATCH v4 19/43] hpsa: add ioaccel sg chaining for the ioaccel2 path
From: Webb Scales Increase the request size for ioaccel2 path. The error, if any, returned by hpsa_allocate_ioaccel2_sg_chain_blocks to hpsa_alloc_ioaccel2_cmd_and_bft should be returned upstream rather than assumed to be -ENOMEM. This differs slightly from hpsa_alloc_ioaccel1_cmd_and_bft, which does not call another hpsa_allocate function and only has -ENOMEM to return from some kmalloc calls. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 125 +++ drivers/scsi/hpsa.h |1 2 files changed, 116 insertions(+), 10 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index c9c42e9..1839761 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1704,6 +1704,46 @@ static void hpsa_slave_destroy(struct scsi_device *sdev) /* nothing to do. */ } +static void hpsa_free_ioaccel2_sg_chain_blocks(struct ctlr_info *h) +{ + int i; + + if (!h->ioaccel2_cmd_sg_list) + return; + for (i = 0; i < h->nr_cmds; i++) { + kfree(h->ioaccel2_cmd_sg_list[i]); + h->ioaccel2_cmd_sg_list[i] = NULL; + } + kfree(h->ioaccel2_cmd_sg_list); + h->ioaccel2_cmd_sg_list = NULL; +} + +static int hpsa_allocate_ioaccel2_sg_chain_blocks(struct ctlr_info *h) +{ + int i; + + if (h->chainsize <= 0) + return 0; + + h->ioaccel2_cmd_sg_list = + kzalloc(sizeof(*h->ioaccel2_cmd_sg_list) * h->nr_cmds, + GFP_KERNEL); + if (!h->ioaccel2_cmd_sg_list) + return -ENOMEM; + for (i = 0; i < h->nr_cmds; i++) { + h->ioaccel2_cmd_sg_list[i] = + kmalloc(sizeof(*h->ioaccel2_cmd_sg_list[i]) * + h->maxsgentries, GFP_KERNEL); + if (!h->ioaccel2_cmd_sg_list[i]) + goto clean; + } + return 0; + +clean: + hpsa_free_ioaccel2_sg_chain_blocks(h); + return -ENOMEM; +} + static void hpsa_free_sg_chain_blocks(struct ctlr_info *h) { int i; @@ -1746,6 +1786,39 @@ clean: return -ENOMEM; } +static int hpsa_map_ioaccel2_sg_chain_block(struct ctlr_info *h, + struct io_accel2_cmd *cp, struct CommandList *c) +{ + struct ioaccel2_sg_element *chain_block; + u64 temp64; + u32 chain_size; + + chain_block = h->ioaccel2_cmd_sg_list[c->cmdindex]; + chain_size = le32_to_cpu(cp->data_len); + temp64 = pci_map_single(h->pdev, chain_block, chain_size, + PCI_DMA_TODEVICE); + if (dma_mapping_error(&h->pdev->dev, temp64)) { + /* prevent subsequent unmapping */ + cp->sg->address = 0; + return -1; + } + cp->sg->address = cpu_to_le64(temp64); + return 0; +} + +static void hpsa_unmap_ioaccel2_sg_chain_block(struct ctlr_info *h, + struct io_accel2_cmd *cp) +{ + struct ioaccel2_sg_element *chain_sg; + u64 temp64; + u32 chain_size; + + chain_sg = cp->sg; + temp64 = le64_to_cpu(chain_sg->address); + chain_size = le32_to_cpu(cp->data_len); + pci_unmap_single(h->pdev, temp64, chain_size, PCI_DMA_TODEVICE); +} + static int hpsa_map_sg_chain_block(struct ctlr_info *h, struct CommandList *c) { @@ -1955,6 +2028,7 @@ static void complete_scsi_command(struct CommandList *cp) struct ctlr_info *h; struct ErrorInfo *ei; struct hpsa_scsi_dev_t *dev; + struct io_accel2_cmd *c2; int sense_key; int asc; /* additional sense code */ @@ -1965,12 +2039,17 @@ static void complete_scsi_command(struct CommandList *cp) cmd = cp->scsi_cmd; h = cp->h; dev = cmd->device->hostdata; + c2 = &h->ioaccel2_cmd_pool[cp->cmdindex]; scsi_dma_unmap(cmd); /* undo the DMA mappings */ if ((cp->cmd_type == CMD_SCSI) && (le16_to_cpu(cp->Header.SGTotal) > h->max_cmd_sg_entries)) hpsa_unmap_sg_chain_block(h, cp); + if ((cp->cmd_type == CMD_IOACCEL2) && + (c2->sg[0].chain_indicator == IOACCEL2_CHAIN)) + hpsa_unmap_ioaccel2_sg_chain_block(h, c2); + cmd->result = (DID_OK << 16); /* host byte */ cmd->result |= (COMMAND_COMPLETE << 8); /* msg byte */ @@ -3812,10 +3891,7 @@ static int hpsa_scsi_ioaccel2_queue_command(struct ctlr_info *h, u32 len; u32 total_len = 0; - if (scsi_sg_count(cmd) > h->ioaccel_maxsg) { - atomic_dec(&phys_disk->ioaccel_cmds_out); - return IO_ACCEL_INELIGIBLE; - } + BUG_ON(scsi_sg_count(cmd) > h->maxsgentries); if (fixup_ioaccel_cdb(cdb, &cdb_len)) { atomic_dec(&phys_disk->ioaccel_cmds_out); @@ -3838,8 +3914,19 @@ static int hpsa_scsi_ioaccel2_qu
[PATCH v4 20/43] hpsa: add more ioaccel2 error handling, including underrun statuses.
From: Joe Handzik improve ioaccel2 error handling, including better handling of underrun statuses Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Joe Handzik Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 33 - drivers/scsi/hpsa_cmd.h |6 ++ 2 files changed, 34 insertions(+), 5 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 1839761..fd9620d 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1868,6 +1868,7 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, { int data_len; int retry = 0; + u32 ioaccel2_resid = 0; switch (c2->error_data.serv_response) { case IOACCEL2_SERV_RESPONSE_COMPLETE: @@ -1926,11 +1927,33 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, } break; case IOACCEL2_SERV_RESPONSE_FAILURE: - /* don't expect to get here. */ - dev_warn(&h->pdev->dev, - "unexpected delivery or target failure, status = 0x%02x\n", - c2->error_data.status); - retry = 1; + switch (c2->error_data.status) { + case IOACCEL2_STATUS_SR_IO_ERROR: + case IOACCEL2_STATUS_SR_IO_ABORTED: + case IOACCEL2_STATUS_SR_OVERRUN: + retry = 1; + break; + case IOACCEL2_STATUS_SR_UNDERRUN: + cmd->result = (DID_OK << 16); /* host byte */ + cmd->result |= (COMMAND_COMPLETE << 8); /* msg byte */ + ioaccel2_resid = c2->error_data.resid_cnt[3] << 24; + ioaccel2_resid |= c2->error_data.resid_cnt[2] << 16; + ioaccel2_resid |= c2->error_data.resid_cnt[1] << 8; + ioaccel2_resid |= c2->error_data.resid_cnt[0]; + scsi_set_resid(cmd, ioaccel2_resid); + break; + case IOACCEL2_STATUS_SR_NO_PATH_TO_DEVICE: + case IOACCEL2_STATUS_SR_INVALID_DEVICE: + case IOACCEL2_STATUS_SR_IOACCEL_DISABLED: + /* We will get an event from ctlr to trigger rescan */ + retry = 1; + break; + default: + retry = 1; + dev_warn(&h->pdev->dev, + "unexpected delivery or target failure, status = 0x%02x\n", + c2->error_data.status); + } break; case IOACCEL2_SERV_RESPONSE_TMF_COMPLETE: break; diff --git a/drivers/scsi/hpsa_cmd.h b/drivers/scsi/hpsa_cmd.h index 0efb6f2b..cecb62b 100644 --- a/drivers/scsi/hpsa_cmd.h +++ b/drivers/scsi/hpsa_cmd.h @@ -532,6 +532,12 @@ struct io_accel2_scsi_response { #define IOACCEL2_STATUS_SR_TASK_COMP_SET_FULL 0x28 #define IOACCEL2_STATUS_SR_TASK_COMP_ABORTED 0x40 #define IOACCEL2_STATUS_SR_IOACCEL_DISABLED0x0E +#define IOACCEL2_STATUS_SR_IO_ERROR0x01 +#define IOACCEL2_STATUS_SR_IO_ABORTED 0x02 +#define IOACCEL2_STATUS_SR_NO_PATH_TO_DEVICE 0x03 +#define IOACCEL2_STATUS_SR_INVALID_DEVICE 0x04 +#define IOACCEL2_STATUS_SR_UNDERRUN0x51 +#define IOACCEL2_STATUS_SR_OVERRUN 0x75 u8 data_present;/* low 2 bits */ #define IOACCEL2_NO_DATAPRESENT0x000 #define IOACCEL2_RESPONSE_DATAPRESENT 0x001 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 21/43] hpsa: do not check cmd_alloc return value - it cannnot return NULL
From: Robert Elliott cmd_alloc can no longer return NULL, so don't check for NULL any more (which is unreachable code). Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 77 ++- 1 file changed, 15 insertions(+), 62 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index fd9620d..2da5306 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -2474,11 +2474,6 @@ static int hpsa_scsi_do_inquiry(struct ctlr_info *h, unsigned char *scsi3addr, c = cmd_alloc(h); - if (c == NULL) { - dev_warn(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return -ENOMEM; - } - if (fill_cmd(c, HPSA_INQUIRY, h, buf, bufsize, page, scsi3addr, TYPE_CMD)) { rc = -1; @@ -2507,11 +2502,6 @@ static int hpsa_bmic_ctrl_mode_sense(struct ctlr_info *h, struct ErrorInfo *ei; c = cmd_alloc(h); - if (c == NULL) {/* trouble... */ - dev_warn(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return -ENOMEM; - } - if (fill_cmd(c, BMIC_SENSE_CONTROLLER_PARAMETERS, h, buf, bufsize, page, scsi3addr, TYPE_CMD)) { rc = -1; @@ -2529,7 +2519,7 @@ static int hpsa_bmic_ctrl_mode_sense(struct ctlr_info *h, out: cmd_free(h, c); return rc; - } +} static int hpsa_send_reset(struct ctlr_info *h, unsigned char *scsi3addr, u8 reset_type, int reply_queue) @@ -2540,10 +2530,6 @@ static int hpsa_send_reset(struct ctlr_info *h, unsigned char *scsi3addr, c = cmd_alloc(h); - if (c == NULL) {/* trouble... */ - dev_warn(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return -ENOMEM; - } /* fill_cmd can't fail here, no data buffer to map. */ (void) fill_cmd(c, HPSA_DEVICE_RESET_MSG, h, NULL, 0, 0, @@ -2671,10 +2657,7 @@ static int hpsa_get_raid_map(struct ctlr_info *h, struct ErrorInfo *ei; c = cmd_alloc(h); - if (c == NULL) { - dev_warn(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return -ENOMEM; - } + if (fill_cmd(c, HPSA_GET_RAID_MAP, h, &this_device->raid_map, sizeof(this_device->raid_map), 0, scsi3addr, TYPE_CMD)) { @@ -2847,10 +2830,7 @@ static int hpsa_scsi_do_report_luns(struct ctlr_info *h, int logical, struct ErrorInfo *ei; c = cmd_alloc(h); - if (c == NULL) {/* trouble... */ - dev_err(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return -1; - } + /* address the controller */ memset(scsi3addr, 0, sizeof(scsi3addr)); if (fill_cmd(c, logical ? HPSA_REPORT_LOG : HPSA_REPORT_PHYS, h, @@ -2965,8 +2945,7 @@ static int hpsa_volume_offline(struct ctlr_info *h, #define ASCQ_LUN_NOT_READY_INITIALIZING_CMD_REQ 0x02 c = cmd_alloc(h); - if (!c) - return 0; + (void) fill_cmd(c, TEST_UNIT_READY, h, NULL, 0, 0, scsi3addr, TYPE_CMD); rc = hpsa_scsi_do_simple_cmd(h, c, DEFAULT_REPLY_QUEUE, NO_TIMEOUT); if (rc) { @@ -3040,8 +3019,7 @@ static int hpsa_device_supports_aborts(struct ctlr_info *h, return 1; c = cmd_alloc(h); - if (!c) - return -ENOMEM; + (void) fill_cmd(c, HPSA_ABORT_MSG, h, &tag, 0, 0, scsi3addr, TYPE_MSG); (void) hpsa_scsi_do_simple_cmd(h, c, DEFAULT_REPLY_QUEUE, NO_TIMEOUT); /* no unmap needed here because no data xfer. */ @@ -4612,10 +4590,7 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) return 0; } c = cmd_alloc(h); - if (c == NULL) {/* trouble... */ - dev_err(&h->pdev->dev, "cmd_alloc returned NULL!\n"); - return SCSI_MLQUEUE_HOST_BUSY; - } + if (unlikely(lockup_detected(h))) { cmd->result = DID_NO_CONNECT << 16; cmd_free(h, c); @@ -4776,11 +4751,6 @@ static int wait_for_device_to_become_ready(struct ctlr_info *h, struct CommandList *c; c = cmd_alloc(h); - if (!c) { - dev_warn(&h->pdev->dev, "out of memory in " - "wait_for_device_to_become_ready.\n"); - return IO_ERROR; - } /* Send test unit ready until device ready, or give up. */ while (count < HPSA_TUR_RETRY_LIMIT) { @@ -4943,10 +4913,6 @@ static int hpsa_send_abort(struct ctlr_info *h, unsigned char *scsi3addr, __le32 tagupper, taglower; c = cmd_alloc(h); - if (c == NULL) {/* trouble... */ - dev_warn(&h->pdev->dev, "cmd_alloc returned NU
[PATCH v4 13/43] hpsa: print accurate SSD Smart Path Enabled status
From: Robert Elliott offload_enabled changes are deferred until after the added/updated prints occur, so the values are incorrect. defer printing SSD Smart Path Enabled status information until the information is correct Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 12 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index b342788..9ab6af8 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1060,12 +1060,12 @@ lun_assigned: h->dev[n] = device; h->ndevices++; - device->offload_to_be_enabled = device->offload_enabled; - device->offload_enabled = 0; added[*nadded] = device; (*nadded)++; hpsa_show_dev_msg(KERN_INFO, h, device, device->expose_state & HPSA_SCSI_ADD ? "added" : "masked"); + device->offload_to_be_enabled = device->offload_enabled; + device->offload_enabled = 0; return 0; } @@ -1073,6 +1073,7 @@ lun_assigned: static void hpsa_scsi_update_entry(struct ctlr_info *h, int hostno, int entry, struct hpsa_scsi_dev_t *new_entry) { + int offload_enabled; /* assumes h->devlock is held */ BUG_ON(entry < 0 || entry >= HPSA_MAX_DEVICES); @@ -1105,7 +1106,10 @@ static void hpsa_scsi_update_entry(struct ctlr_info *h, int hostno, if (!new_entry->offload_enabled) h->dev[entry]->offload_enabled = 0; + offload_enabled = h->dev[entry]->offload_enabled; + h->dev[entry]->offload_enabled = h->dev[entry]->offload_to_be_enabled; hpsa_show_dev_msg(KERN_INFO, h, h->dev[entry], "updated"); + h->dev[entry]->offload_enabled = offload_enabled; } /* Replace an entry from h->dev[] array. */ @@ -1128,12 +1132,12 @@ static void hpsa_scsi_replace_entry(struct ctlr_info *h, int hostno, new_entry->lun = h->dev[entry]->lun; } - new_entry->offload_to_be_enabled = new_entry->offload_enabled; - new_entry->offload_enabled = 0; h->dev[entry] = new_entry; added[*nadded] = new_entry; (*nadded)++; hpsa_show_dev_msg(KERN_INFO, h, new_entry, "replaced"); + new_entry->offload_to_be_enabled = new_entry->offload_enabled; + new_entry->offload_enabled = 0; } /* Remove an entry from h->dev[] array. */ -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 24/43] hpsa: clean up some error reporting output in abort handler
From: Robert Elliott report more useful information on aborts Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 29 ++--- 1 file changed, 14 insertions(+), 15 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index c7a5655..15c5b81 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -5110,10 +5110,10 @@ static int hpsa_eh_abort_handler(struct scsi_cmnd *sc) return FAILED; memset(msg, 0, sizeof(msg)); - ml += sprintf(msg+ml, "scsi %d:%d:%d:%llu %s", + ml += sprintf(msg+ml, "scsi %d:%d:%d:%llu %s %p", h->scsi_host->host_no, sc->device->channel, sc->device->id, sc->device->lun, - "Aborting command"); + "Aborting command", sc); /* Find the device of the command to be aborted */ dev = sc->device->hostdata; @@ -5147,12 +5147,12 @@ static int hpsa_eh_abort_handler(struct scsi_cmnd *sc) ml += sprintf(msg+ml, "Tag:0x%08x:%08x ", tagupper, taglower); as = abort->scsi_cmd; if (as != NULL) - ml += sprintf(msg+ml, "Command:0x%x SN:0x%lx ", - as->cmnd[0], as->serial_number); - dev_dbg(&h->pdev->dev, "%s\n", msg); - dev_warn(&h->pdev->dev, "scsi %d:%d:%d:%d %s\n", - h->scsi_host->host_no, dev->bus, dev->target, dev->lun, - "Aborting command"); + ml += sprintf(msg+ml, + "CDBLen: %d CDB: 0x%02x%02x... SN: 0x%lx ", + as->cmd_len, as->cmnd[0], as->cmnd[1], + as->serial_number); + dev_warn(&h->pdev->dev, "%s BEING SENT\n", msg); + /* * Command is in flight, or possibly already completed * by the firmware (but not to the scsi mid layer) but we can't @@ -5160,7 +5160,8 @@ static int hpsa_eh_abort_handler(struct scsi_cmnd *sc) */ if (wait_for_available_abort_cmd(h)) { dev_warn(&h->pdev->dev, - "Timed out waiting for an abort command to become available.\n"); + "%s FAILED, timeout waiting for an abort command to become available.\n", + msg); cmd_free(h, abort); return FAILED; } @@ -5168,16 +5169,14 @@ static int hpsa_eh_abort_handler(struct scsi_cmnd *sc) atomic_inc(&h->abort_cmds_available); wake_up_all(&h->abort_cmd_wait_queue); if (rc != 0) { - dev_warn(&h->pdev->dev, "scsi %d:%d:%d:%d %s\n", - h->scsi_host->host_no, - dev->bus, dev->target, dev->lun, - "FAILED to abort command"); + dev_warn(&h->pdev->dev, "%s SENT, FAILED\n", msg); cmd_free(h, abort); return FAILED; } - dev_info(&h->pdev->dev, "%s REQUEST SUCCEEDED.\n", msg); + dev_info(&h->pdev->dev, "%s SENT, SUCCESS\n", msg); - /* If the abort(s) above completed and actually aborted the + /* +* If the abort(s) above completed and actually aborted the * command, then the command to be aborted should already be * completed. If not, wait around a bit more to see if they * manage to complete normally. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 02/43] hpsa: clean up host, channel, target, lun prints
From: Webb Scales We had a mix of formats used for specifying controller, bus, target, and lun address of devices. change to the format used by the scsi midlayer and upper layer (2:3:0:0) so you can easily follow the information from hpsa to scsi midlayer to sd upper layer. Also add this information: - product ID - vendor ID - RAID level - SSD Smath Path capable and enabled - exposure level (sg-only) Example: hpsa :04:00.0: added scsi 2:0:0:0: Direct-Access HP LOGICAL VOLUME RAID-0 SSDSmartPathCap+ En+ Exp=4 scsi 2:0:0:0: Direct-Access HP LOGICAL VOLUME 10.0 PQ: 0 ANSI: 5 sd 2:0:0:0: [sdr] 12501713072 512-byte logical blocks: (6.40 TB/5.82 TiB) sd 2:0:0:0: [sdr] 4096-byte physical blocks sd 2:0:0:0: [sdr] Attached SCSI disk sd 2:0:0:0: Attached scsi generic sg20 type 0 Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 73 +-- 1 file changed, 41 insertions(+), 32 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 3417b8b..20a3aa3 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -886,6 +886,23 @@ static int hpsa_find_target_lun(struct ctlr_info *h, return !found; } +static inline void hpsa_show_dev_msg(const char *level, struct ctlr_info *h, + struct hpsa_scsi_dev_t *dev, char *description) +{ + dev_printk(level, &h->pdev->dev, + "scsi %d:%d:%d:%d: %s %s %.8s %.16s RAID-%s SSDSmartPathCap%c En%c Exp=%d\n", + h->scsi_host->host_no, dev->bus, dev->target, dev->lun, + description, + scsi_device_type(dev->devtype), + dev->vendor, + dev->model, + dev->raid_level > RAID_UNKNOWN ? + "RAID-?" : raid_label[dev->raid_level], + dev->offload_config ? '+' : '-', + dev->offload_enabled ? '+' : '-', + dev->expose_state); +} + /* Add an entry into h->dev[] array. */ static int hpsa_scsi_add_entry(struct ctlr_info *h, int hostno, struct hpsa_scsi_dev_t *device, @@ -955,15 +972,8 @@ lun_assigned: device->offload_enabled = 0; added[*nadded] = device; (*nadded)++; - - /* initially, (before registering with scsi layer) we don't -* know our hostno and we don't want to print anything first -* time anyway (the scsi layer's inquiries will show that info) -*/ - /* if (hostno != -1) */ - dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d added.\n", - scsi_device_type(device->devtype), hostno, - device->bus, device->target, device->lun); + hpsa_show_dev_msg(KERN_INFO, h, device, + device->expose_state & HPSA_SCSI_ADD ? "added" : "masked"); return 0; } @@ -1003,6 +1013,7 @@ static void hpsa_scsi_update_entry(struct ctlr_info *h, int hostno, if (!new_entry->offload_enabled) h->dev[entry]->offload_enabled = 0; + hpsa_show_dev_msg(KERN_INFO, h, h->dev[entry], "updated"); } /* Replace an entry from h->dev[] array. */ @@ -1030,9 +1041,7 @@ static void hpsa_scsi_replace_entry(struct ctlr_info *h, int hostno, h->dev[entry] = new_entry; added[*nadded] = new_entry; (*nadded)++; - dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d changed.\n", - scsi_device_type(new_entry->devtype), hostno, new_entry->bus, - new_entry->target, new_entry->lun); + hpsa_show_dev_msg(KERN_INFO, h, new_entry, "replaced"); } /* Remove an entry from h->dev[] array. */ @@ -1052,9 +1061,7 @@ static void hpsa_scsi_remove_entry(struct ctlr_info *h, int hostno, int entry, for (i = entry; i < h->ndevices-1; i++) h->dev[i] = h->dev[i+1]; h->ndevices--; - dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d removed.\n", - scsi_device_type(sd->devtype), hostno, sd->bus, sd->target, - sd->lun); + hpsa_show_dev_msg(KERN_INFO, h, sd, "removed"); } #define SCSI3ADDR_EQ(a, b) ( \ @@ -1435,9 +1442,7 @@ static void adjust_hpsa_scsi_table(struct ctlr_info *h, int hostno, */ if (sd[i]->volume_offline) { hpsa_show_volume_status(h, sd[i]); - dev_info(&h->pdev->dev, "c%db%dt%dl%d: temporarily offline\n", - h->scsi_host->host_no, - sd[i]->bus, sd[i]->target, sd[i]->lun); + hpsa_show_dev_msg(KERN_INFO, h, sd[i], "offline"); continue; } @@ -1501,10 +1506,11 @@ static void adjust_hpsa_scsi_table(struct ctlr_info *h, int hostno, * future cmds to this de
[PATCH v4 14/43] hpsa: use ioaccel2 path to submit IOs to physical drives in HBA mode.
From: Joe Handzik use ioaccel2 path to submit I/O to physical drives in HBA mode Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Joe Handzik Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 10 +- drivers/scsi/hpsa.h |1 + 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 9ab6af8..9049133 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1093,6 +1093,11 @@ static void hpsa_scsi_update_entry(struct ctlr_info *h, int hostno, h->dev[entry]->raid_map = new_entry->raid_map; h->dev[entry]->ioaccel_handle = new_entry->ioaccel_handle; } + if (new_entry->hba_ioaccel_enabled) { + h->dev[entry]->ioaccel_handle = new_entry->ioaccel_handle; + wmb(); /* set ioaccel_handle *before* hba_ioaccel_enabled */ + } + h->dev[entry]->hba_ioaccel_enabled = new_entry->hba_ioaccel_enabled; h->dev[entry]->offload_config = new_entry->offload_config; h->dev[entry]->offload_to_mirror = new_entry->offload_to_mirror; h->dev[entry]->queue_depth = new_entry->queue_depth; @@ -3009,6 +3014,7 @@ static int hpsa_update_device_info(struct ctlr_info *h, this_device->offload_config = 0; this_device->offload_enabled = 0; this_device->offload_to_be_enabled = 0; + this_device->hba_ioaccel_enabled = 0; this_device->volume_offline = 0; this_device->queue_depth = h->nr_cmds; } @@ -3297,6 +3303,8 @@ static void hpsa_get_ioaccel_drive_info(struct ctlr_info *h, (struct ext_report_lun_entry *) lunaddrbytes; dev->ioaccel_handle = rle->ioaccel_handle; + if (PHYS_IOACCEL(lunaddrbytes) && dev->ioaccel_handle) + dev->hba_ioaccel_enabled = 1; memset(id_phys, 0, sizeof(*id_phys)); rc = hpsa_bmic_id_physical_device(h, lunaddrbytes, GET_BMIC_DRIVE_NUMBER(lunaddrbytes), id_phys, @@ -4398,7 +4406,7 @@ static int hpsa_ioaccel_submit(struct ctlr_info *h, rc = hpsa_scsi_ioaccel_raid_map(h, c); if (rc < 0) /* scsi_dma_map failed. */ rc = SCSI_MLQUEUE_HOST_BUSY; - } else if (dev->ioaccel_handle) { + } else if (dev->hba_ioaccel_enabled) { hpsa_cmd_init(h, c->cmdindex, c); c->cmd_type = CMD_SCSI; c->scsi_cmd = cmd; diff --git a/drivers/scsi/hpsa.h b/drivers/scsi/hpsa.h index df2468c..87a70b5 100644 --- a/drivers/scsi/hpsa.h +++ b/drivers/scsi/hpsa.h @@ -55,6 +55,7 @@ struct hpsa_scsi_dev_t { int offload_config; /* I/O accel RAID offload configured */ int offload_enabled;/* I/O accel RAID offload enabled */ int offload_to_be_enabled; + int hba_ioaccel_enabled; int offload_to_mirror; /* Send next I/O accelerator RAID * offload request to mirror drive */ -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 09/43] hpsa: factor out hpsa_init_cmd function
From: Stephen Cameron Factor out hpsa_cmd_init from cmd_alloc(). We also need this for resubmitting commands down the default RAID path when they have returned from the ioaccel paths with errors. In particular, reinitialize the cmd_type and busaddr fields as these will not be correct for submitting down the RAID stack path after ioaccel command completion. This saves time when submitting commands. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 77 --- drivers/scsi/hpsa_cmd.h |2 + 2 files changed, 53 insertions(+), 26 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index a9a301c..037b549 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -4287,7 +4287,6 @@ static int hpsa_ciss_submit(struct ctlr_info *h, /* Fill in the request block... */ c->Request.Timeout = 0; - memset(c->Request.CDB, 0, sizeof(c->Request.CDB)); BUG_ON(cmd->cmd_len > sizeof(c->Request.CDB)); c->Request.CDBLen = cmd->cmd_len; memcpy(c->Request.CDB, cmd->cmnd, cmd->cmd_len); @@ -4338,6 +4337,48 @@ static int hpsa_ciss_submit(struct ctlr_info *h, return 0; } +static void hpsa_cmd_init(struct ctlr_info *h, int index, + struct CommandList *c) +{ + dma_addr_t cmd_dma_handle, err_dma_handle; + + /* Zero out all of commandlist except the last field, refcount */ + memset(c, 0, offsetof(struct CommandList, refcount)); + c->Header.tag = cpu_to_le64((u64) (index << DIRECT_LOOKUP_SHIFT)); + cmd_dma_handle = h->cmd_pool_dhandle + index * sizeof(*c); + c->err_info = h->errinfo_pool + index; + memset(c->err_info, 0, sizeof(*c->err_info)); + err_dma_handle = h->errinfo_pool_dhandle + + index * sizeof(*c->err_info); + c->cmdindex = index; + c->busaddr = (u32) cmd_dma_handle; + c->ErrDesc.Addr = cpu_to_le64((u64) err_dma_handle); + c->ErrDesc.Len = cpu_to_le32((u32) sizeof(*c->err_info)); + c->h = h; +} + +static void hpsa_preinitialize_commands(struct ctlr_info *h) +{ + int i; + + for (i = 0; i < h->nr_cmds; i++) { + struct CommandList *c = h->cmd_pool + i; + + hpsa_cmd_init(h, i, c); + atomic_set(&c->refcount, 0); + } +} + +static inline void hpsa_cmd_partial_init(struct ctlr_info *h, int index, + struct CommandList *c) +{ + dma_addr_t cmd_dma_handle = h->cmd_pool_dhandle + index * sizeof(*c); + + memset(c->Request.CDB, 0, sizeof(c->Request.CDB)); + memset(c->err_info, 0, sizeof(*c->err_info)); + c->busaddr = (u32) cmd_dma_handle; +} + static void hpsa_command_resubmit_worker(struct work_struct *work) { struct scsi_cmnd *cmd; @@ -4352,6 +4393,7 @@ static void hpsa_command_resubmit_worker(struct work_struct *work) cmd->scsi_done(cmd); return; } + hpsa_cmd_partial_init(c->h, c->cmdindex, c); if (hpsa_ciss_submit(c->h, c, cmd, dev->scsi3addr)) { /* * If we get here, it means dma mapping failed. Try @@ -4408,10 +4450,11 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) h->acciopath_status)) { cmd->host_scribble = (unsigned char *) c; - c->cmd_type = CMD_SCSI; - c->scsi_cmd = cmd; if (dev->offload_enabled) { + hpsa_cmd_init(h, c->cmdindex, c); + c->cmd_type = CMD_SCSI; + c->scsi_cmd = cmd; rc = hpsa_scsi_ioaccel_raid_map(h, c); if (rc == 0) return 0; /* Sent on ioaccel path */ @@ -4420,6 +4463,9 @@ static int hpsa_scsi_queue_command(struct Scsi_Host *sh, struct scsi_cmnd *cmd) return SCSI_MLQUEUE_HOST_BUSY; } } else if (dev->ioaccel_handle) { + hpsa_cmd_init(h, c->cmdindex, c); + c->cmd_type = CMD_SCSI; + c->scsi_cmd = cmd; rc = hpsa_scsi_ioaccel_direct_map(h, c); if (rc == 0) return 0; /* Sent on direct map path */ @@ -5031,10 +5077,7 @@ static int hpsa_eh_abort_handler(struct scsi_cmnd *sc) static struct CommandList *cmd_alloc(struct ctlr_info *h) { struct CommandList *c; - int i; - union u64bit temp64; - dma_addr_t cmd_dma_handle, err_dma_handle; - int refcount; + int refcount, i; unsigned long offset; /* @@ -5068,24 +5111,7 @@ static struct CommandList *cmd_alloc(struct ctlr_info *h) break; /* it's ours now. */ } h->last_allocation = i; /* benignly racy */ - - /
[PATCH v4 10/43] hpsa: do not ignore return value of hpsa_register_scsi
From: Stephen Cameron add error handling for failure when registering with SCSI subsystem. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 037b549..292b8bd 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -7427,7 +7427,9 @@ reinit_after_soft_reset: h->access.set_intr_mask(h, HPSA_INTR_ON); hpsa_hba_inquiry(h); - hpsa_register_scsi(h); /* hook ourselves into SCSI subsystem */ + rc = hpsa_register_scsi(h); /* hook ourselves into SCSI subsystem */ + if (rc) + goto clean4; /* Monitor the controller for firmware lockups */ h->heartbeat_sample_interval = HEARTBEAT_SAMPLE_INTERVAL; -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 06/43] hpsa: hpsa decode sense data for io and tmf
From: Stephen Cameron In hba mode, we could get sense data in descriptor format so we need to handle that. It's possible for CommandStatus to have value 0x0D "TMF Function Status", which we should handle. We will get this from a P1224 when aborting a non-existent tag, for example. The "ScsiStatus" field of the errinfo field will contain the TMF function status value. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 143 +++ drivers/scsi/hpsa_cmd.h |9 +++ 2 files changed, 117 insertions(+), 35 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 6ee92af..68238dd 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -43,6 +43,7 @@ #include #include #include +#include #include #include #include @@ -268,16 +269,49 @@ static inline struct ctlr_info *shost_to_hba(struct Scsi_Host *sh) return (struct ctlr_info *) *priv; } +/* extract sense key, asc, and ascq from sense data. -1 means invalid. */ +static void decode_sense_data(const u8 *sense_data, int sense_data_len, + int *sense_key, int *asc, int *ascq) +{ + struct scsi_sense_hdr sshdr; + bool rc; + + *sense_key = -1; + *asc = -1; + *ascq = -1; + + if (sense_data_len < 1) + return; + + rc = scsi_normalize_sense(sense_data, sense_data_len, &sshdr); + if (rc) { + *sense_key = sshdr.sense_key; + *asc = sshdr.asc; + *ascq = sshdr.ascq; + } +} + static int check_for_unit_attention(struct ctlr_info *h, struct CommandList *c) { - if (c->err_info->SenseInfo[2] != UNIT_ATTENTION) + int sense_key, asc, ascq; + int sense_len; + + if (c->err_info->SenseLen > sizeof(c->err_info->SenseInfo)) + sense_len = sizeof(c->err_info->SenseInfo); + else + sense_len = c->err_info->SenseLen; + + decode_sense_data(c->err_info->SenseInfo, sense_len, + &sense_key, &asc, &ascq); + if (sense_key != UNIT_ATTENTION || asc == -1) return 0; - switch (c->err_info->SenseInfo[12]) { + switch (asc) { case STATE_CHANGED: - dev_warn(&h->pdev->dev, HPSA "%d: a state change " - "detected, command retried\n", h->ctlr); + dev_warn(&h->pdev->dev, + HPSA "%d: a state change detected, command retried\n", + h->ctlr); break; case LUN_FAILED: dev_warn(&h->pdev->dev, @@ -1860,6 +1894,34 @@ retry_cmd: queue_work_on(raw_smp_processor_id(), h->resubmit_wq, &c->work); } +/* Returns 0 on success, < 0 otherwise. */ +static int hpsa_evaluate_tmf_status(struct ctlr_info *h, + struct CommandList *cp) +{ + u8 tmf_status = cp->err_info->ScsiStatus; + + switch (tmf_status) { + case CISS_TMF_COMPLETE: + /* +* CISS_TMF_COMPLETE never happens, instead, +* ei->CommandStatus == 0 for this case. +*/ + case CISS_TMF_SUCCESS: + return 0; + case CISS_TMF_INVALID_FRAME: + case CISS_TMF_NOT_SUPPORTED: + case CISS_TMF_FAILED: + case CISS_TMF_WRONG_LUN: + case CISS_TMF_OVERLAPPED_TAG: + break; + default: + dev_warn(&h->pdev->dev, "Unknown TMF status: 0x%02x\n", + tmf_status); + break; + } + return -tmf_status; +} + static void complete_scsi_command(struct CommandList *cp) { struct scsi_cmnd *cmd; @@ -1867,9 +1929,9 @@ static void complete_scsi_command(struct CommandList *cp) struct ErrorInfo *ei; struct hpsa_scsi_dev_t *dev; - unsigned char sense_key; - unsigned char asc; /* additional sense code */ - unsigned char ascq; /* additional sense code qualifier */ + int sense_key; + int asc; /* additional sense code */ + int ascq; /* additional sense code qualifier */ unsigned long sense_data_size; ei = cp->err_info; @@ -1904,8 +1966,6 @@ static void complete_scsi_command(struct CommandList *cp) if (cp->cmd_type == CMD_IOACCEL2) return process_ioaccel2_completion(h, cp, cmd, dev); - cmd->result |= ei->ScsiStatus; - scsi_set_resid(cmd, ei->ResidualCnt); if (ei->CommandStatus == 0) { if (cp->cmd_type == CMD_IOACCEL1) @@ -1915,16 +1975,6 @@ static void complete_scsi_command(struct CommandList *cp) return; } - /* copy the sense data */ - if (SCSI_SENSE_BUFFERSIZE < sizeof(ei->SenseInfo)) - sense_data_size = SCSI_SENSE_BUFFERSIZE; - else - sense_data_size = sizeof(ei->SenseInf
[PATCH v4 01/43] hpsa: add masked physical devices into h->dev[] array
From: Stephen Cameron Cache the ioaccel handle so that when we need to abort commands sent down the ioaccel2 path, we can look up the LUN ID in h->dev[] instead of having to do I/O to the controller. Add a field to elements in h->dev[] to keep track of how the device is exposed to the SCSI mid layer: Not at all, without an upper level driver (no_uld_attach) or normally exposed. Since masked physical devices are now present in h->dev[] array it would be perfectly possible to do echo scsi add-single-device 2 2 0 0 > /proc/scsi/scsi and bring them online. This was previously not allowed for masked physical devices. Ensure that the mapping of physical disks to logical drives gets updated in a consistent way when a RAID migration occurs and is not touched until updates to it are complete. now instead of doing CISS_REPORT_PHYSICAL to get the LUNID for the physical disk in hpsa_get_pdisk_of_ioaccel2(), just get it out of h->dev[] where we already have it cached. do not touch phys_disk[] for ioaccel enabled logical drives during rescan Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 253 +-- drivers/scsi/hpsa.h |6 + drivers/scsi/hpsa_cmd.h |3 + 3 files changed, 141 insertions(+), 121 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index a1cfbd3..3417b8b 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -222,6 +222,7 @@ static int hpsa_change_queue_depth(struct scsi_device *sdev, int qdepth); static int hpsa_eh_device_reset_handler(struct scsi_cmnd *scsicmd); static int hpsa_eh_abort_handler(struct scsi_cmnd *scsicmd); static int hpsa_slave_alloc(struct scsi_device *sdev); +static int hpsa_slave_configure(struct scsi_device *sdev); static void hpsa_slave_destroy(struct scsi_device *sdev); static void hpsa_update_scsi_devices(struct ctlr_info *h, int hostno); @@ -667,6 +668,9 @@ static struct device_attribute *hpsa_shost_attrs[] = { NULL, }; +#define HPSA_NRESERVED_CMDS(HPSA_CMDS_RESERVED_FOR_ABORTS + \ + HPSA_CMDS_RESERVED_FOR_DRIVER + HPSA_MAX_CONCURRENT_PASSTHRUS) + static struct scsi_host_template hpsa_driver_template = { .module = THIS_MODULE, .name = HPSA, @@ -681,6 +685,7 @@ static struct scsi_host_template hpsa_driver_template = { .eh_device_reset_handler = hpsa_eh_device_reset_handler, .ioctl = hpsa_ioctl, .slave_alloc= hpsa_slave_alloc, + .slave_configure= hpsa_slave_configure, .slave_destroy = hpsa_slave_destroy, #ifdef CONFIG_COMPAT .compat_ioctl = hpsa_compat_ioctl, @@ -946,6 +951,8 @@ lun_assigned: h->dev[n] = device; h->ndevices++; + device->offload_to_be_enabled = device->offload_enabled; + device->offload_enabled = 0; added[*nadded] = device; (*nadded)++; @@ -982,16 +989,20 @@ static void hpsa_scsi_update_entry(struct ctlr_info *h, int hostno, */ h->dev[entry]->raid_map = new_entry->raid_map; h->dev[entry]->ioaccel_handle = new_entry->ioaccel_handle; - wmb(); /* ensure raid map updated prior to ->offload_enabled */ } h->dev[entry]->offload_config = new_entry->offload_config; h->dev[entry]->offload_to_mirror = new_entry->offload_to_mirror; - h->dev[entry]->offload_enabled = new_entry->offload_enabled; h->dev[entry]->queue_depth = new_entry->queue_depth; - dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d updated.\n", - scsi_device_type(new_entry->devtype), hostno, new_entry->bus, - new_entry->target, new_entry->lun); + /* +* We can turn off ioaccel offload now, but need to delay turning +* it on until we can update h->dev[entry]->phys_disk[], but we +* can't do that until all the devices are updated. +*/ + h->dev[entry]->offload_to_be_enabled = new_entry->offload_enabled; + if (!new_entry->offload_enabled) + h->dev[entry]->offload_enabled = 0; + } /* Replace an entry from h->dev[] array. */ @@ -1014,6 +1025,8 @@ static void hpsa_scsi_replace_entry(struct ctlr_info *h, int hostno, new_entry->lun = h->dev[entry]->lun; } + new_entry->offload_to_be_enabled = new_entry->offload_enabled; + new_entry->offload_enabled = 0; h->dev[entry] = new_entry; added[*nadded] = new_entry; (*nadded)++; @@ -1312,7 +1325,8 @@ static void hpsa_figure_phys_disk_ptrs(struct ctlr_info *h, */ if (!logical_drive->phys_disk[i]) { logical_drive->offload_enabled = 0; - logical_drive->queue_depth = h->nr_cmds; + logical_drive->offload_to_be_enabled = 0; +
[PATCH v4 18/43] hpsa: refactor freeing of resources into more logical functions
From: Robert Elliott refactor freeing of resources into more logical functions Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 104 +++ 1 file changed, 56 insertions(+), 48 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 9e26eb0..c9c42e9 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -235,6 +235,8 @@ static void check_ioctl_unit_attention(struct ctlr_info *h, static void calc_bucket_map(int *bucket, int num_buckets, int nsgs, int min_blocks, u32 *bucket_map); static void hpsa_put_ctlr_into_performant_mode(struct ctlr_info *h); +static void hpsa_free_ioaccel1_cmd_and_bft(struct ctlr_info *h); +static void hpsa_free_ioaccel2_cmd_and_bft(struct ctlr_info *h); static inline u32 next_command(struct ctlr_info *h, u8 q); static int hpsa_find_cfg_addrs(struct pci_dev *pdev, void __iomem *vaddr, u32 *cfg_base_addr, u64 *cfg_base_addr_index, @@ -6897,6 +6899,21 @@ out_disable: return rc; } +static void hpsa_free_cmd_pool(struct ctlr_info *h) +{ + kfree(h->cmd_pool_bits); + if (h->cmd_pool) + pci_free_consistent(h->pdev, + h->nr_cmds * sizeof(struct CommandList), + h->cmd_pool, + h->cmd_pool_dhandle); + if (h->errinfo_pool) + pci_free_consistent(h->pdev, + h->nr_cmds * sizeof(struct ErrorInfo), + h->errinfo_pool, + h->errinfo_pool_dhandle); +} + static int hpsa_alloc_cmd_pool(struct ctlr_info *h) { h->cmd_pool_bits = kzalloc( @@ -6921,28 +6938,6 @@ clean_up: return -ENOMEM; } -static void hpsa_free_cmd_pool(struct ctlr_info *h) -{ - kfree(h->cmd_pool_bits); - if (h->cmd_pool) - pci_free_consistent(h->pdev, - h->nr_cmds * sizeof(struct CommandList), - h->cmd_pool, h->cmd_pool_dhandle); - if (h->ioaccel2_cmd_pool) - pci_free_consistent(h->pdev, - h->nr_cmds * sizeof(*h->ioaccel2_cmd_pool), - h->ioaccel2_cmd_pool, h->ioaccel2_cmd_pool_dhandle); - if (h->errinfo_pool) - pci_free_consistent(h->pdev, - h->nr_cmds * sizeof(struct ErrorInfo), - h->errinfo_pool, - h->errinfo_pool_dhandle); - if (h->ioaccel_cmd_pool) - pci_free_consistent(h->pdev, - h->nr_cmds * sizeof(struct io_accel1_cmd), - h->ioaccel_cmd_pool, h->ioaccel_cmd_pool_dhandle); -} - static void hpsa_irq_affinity_hints(struct ctlr_info *h) { int i, cpu; @@ -7063,8 +7058,10 @@ static void hpsa_free_reply_queues(struct ctlr_info *h) for (i = 0; i < h->nreply_queues; i++) { if (!h->reply_queue[i].head) continue; - pci_free_consistent(h->pdev, h->reply_queue_size, - h->reply_queue[i].head, h->reply_queue[i].busaddr); + pci_free_consistent(h->pdev, + h->reply_queue_size, + h->reply_queue[i].head, + h->reply_queue[i].busaddr); h->reply_queue[i].head = NULL; h->reply_queue[i].busaddr = 0; } @@ -7075,9 +7072,10 @@ static void hpsa_undo_allocations_after_kdump_soft_reset(struct ctlr_info *h) hpsa_free_irqs(h); hpsa_free_sg_chain_blocks(h); hpsa_free_cmd_pool(h); - kfree(h->ioaccel1_blockFetchTable); - kfree(h->blockFetchTable); - hpsa_free_reply_queues(h); + kfree(h->blockFetchTable); /* perf 2 */ + hpsa_free_reply_queues(h); /* perf 1 */ + hpsa_free_ioaccel1_cmd_and_bft(h); /* perf 1 */ + hpsa_free_ioaccel2_cmd_and_bft(h); /* perf 1 */ hpsa_free_cfgtables(h); /* pci_init 4 */ iounmap(h->vaddr); /* pci_init 3 */ hpsa_disable_interrupt_mode(h); /* pci_init 2 */ @@ -7509,6 +7507,8 @@ reinit_after_soft_reset: clean4: hpsa_free_sg_chain_blocks(h); hpsa_free_cmd_pool(h); + hpsa_free_ioaccel1_cmd_and_bft(h); + hpsa_free_ioaccel2_cmd_and_bft(h); clean2_and_free_irqs: hpsa_free_irqs(h); clean2: @@ -7610,17 +7610,11 @@ static void hpsa_remove_one(struct pci_dev *pdev) hpsa_free_device_info(h); hpsa_free_sg_chain_blocks(h); - pci_free_consistent(h->pdev, - h->nr_cmds * sizeof(struct CommandList), - h->cmd_pool, h->cmd_pool_dhandle); - pci_free_consistent(h->pdev, - h->nr_cm
[PATCH v4 22/43] hpsa: correct return values from driver functions.
From: Robert Elliott correct return codes for error conditions Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 10 +- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 2da5306..5274e3e 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -2661,9 +2661,9 @@ static int hpsa_get_raid_map(struct ctlr_info *h, if (fill_cmd(c, HPSA_GET_RAID_MAP, h, &this_device->raid_map, sizeof(this_device->raid_map), 0, scsi3addr, TYPE_CMD)) { - dev_warn(&h->pdev->dev, "Out of memory in hpsa_get_raid_map()\n"); - rc = -ENOMEM; - goto out; + dev_warn(&h->pdev->dev, "hpsa_get_raid_map fill_cmd failed\n"); + cmd_free(h, c); + return -1; } rc = hpsa_scsi_do_simple_cmd_with_retry(h, c, PCI_DMA_FROMDEVICE, NO_TIMEOUT); @@ -5425,7 +5425,7 @@ static int hpsa_passthru_ioctl(struct ctlr_info *h, void __user *argp) if (iocommand.buf_size > 0) { buff = kmalloc(iocommand.buf_size, GFP_KERNEL); if (buff == NULL) - return -EFAULT; + return -ENOMEM; if (iocommand.Request.Type.Direction & XFER_WRITE) { /* Copy the data into the buffer we created */ if (copy_from_user(buff, iocommand.buf, @@ -7976,7 +7976,7 @@ static int hpsa_alloc_ioaccel1_cmd_and_bft(struct ctlr_info *h) clean_up: hpsa_free_ioaccel1_cmd_and_bft(h); - return 1; + return -ENOMEM; } /* Free ioaccel2 mode command blocks and block fetch table */ -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 15/43] hpsa: Get queue depth from identify physical bmic for physical disks.
From: Joe Handzik get drive queue depth to help avoid task set full conditions. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Joe Handzik Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 33 + 1 file changed, 13 insertions(+), 20 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 9049133..ad2b44c 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -3467,29 +3467,22 @@ static void hpsa_update_scsi_devices(struct ctlr_info *h, int hostno) ncurrent++; break; case TYPE_DISK: - if (h->hba_mode_enabled) { - /* never use raid mapper in HBA mode */ - this_device->offload_enabled = 0; - ncurrent++; - break; - } else if (h->acciopath_status) { - if (i >= nphysicals) { - ncurrent++; - break; - } - } else { - if (i < nphysicals) - break; + if (i >= nphysicals) { ncurrent++; break; } - if (h->transMethod & CFGTBL_Trans_io_accel1 || - h->transMethod & CFGTBL_Trans_io_accel2) { - hpsa_get_ioaccel_drive_info(h, this_device, - lunaddrbytes, id_phys); - atomic_set(&this_device->ioaccel_cmds_out, 0); - ncurrent++; - } + + if (h->hba_mode_enabled) + /* never use raid mapper in HBA mode */ + this_device->offload_enabled = 0; + else if (!(h->transMethod & CFGTBL_Trans_io_accel1 || + h->transMethod & CFGTBL_Trans_io_accel2)) + break; + + hpsa_get_ioaccel_drive_info(h, this_device, + lunaddrbytes, id_phys); + atomic_set(&this_device->ioaccel_cmds_out, 0); + ncurrent++; break; case TYPE_TAPE: case TYPE_MEDIUM_CHANGER: -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 23/43] hpsa: clean up driver init
From: Robert Elliott Improve initialization error handling in hpsa_init_one Clean up style and indent issues Rename functions for consistency Improve error messaging on allocations Fix return status from hpsa_put_ctlr_into_performant_mode Correct free order in hpsa_init_one using new function hpsa_free_performant_mode Prevent inadvertent use of null pointers by nulling out the parent structures and zeroing out associated size variables. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 243 +-- 1 file changed, 157 insertions(+), 86 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 5274e3e..c7a5655 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -234,9 +234,8 @@ static void check_ioctl_unit_attention(struct ctlr_info *h, /* performant mode helper functions */ static void calc_bucket_map(int *bucket, int num_buckets, int nsgs, int min_blocks, u32 *bucket_map); -static void hpsa_put_ctlr_into_performant_mode(struct ctlr_info *h); -static void hpsa_free_ioaccel1_cmd_and_bft(struct ctlr_info *h); -static void hpsa_free_ioaccel2_cmd_and_bft(struct ctlr_info *h); +static void hpsa_free_performant_mode(struct ctlr_info *h); +static int hpsa_put_ctlr_into_performant_mode(struct ctlr_info *h); static inline u32 next_command(struct ctlr_info *h, u8 q); static int hpsa_find_cfg_addrs(struct pci_dev *pdev, void __iomem *vaddr, u32 *cfg_base_addr, u64 *cfg_base_addr_index, @@ -1635,6 +1634,7 @@ static void adjust_hpsa_scsi_table(struct ctlr_info *h, int hostno, * since it didn't get added to scsi mid layer */ fixup_botched_add(h, added[i]); + added[i] = NULL; } free_and_out: @@ -1758,7 +1758,7 @@ static void hpsa_free_sg_chain_blocks(struct ctlr_info *h) h->cmd_sg_list = NULL; } -static int hpsa_allocate_sg_chain_blocks(struct ctlr_info *h) +static int hpsa_alloc_sg_chain_blocks(struct ctlr_info *h) { int i; @@ -6461,9 +6461,11 @@ static void hpsa_disable_interrupt_mode(struct ctlr_info *h) if (h->msix_vector) { if (h->pdev->msix_enabled) pci_disable_msix(h->pdev); + h->msix_vector = 0; } else if (h->msi_vector) { if (h->pdev->msi_enabled) pci_disable_msi(h->pdev); + h->msi_vector = 0; } } @@ -6602,10 +6604,14 @@ static int hpsa_find_cfg_addrs(struct pci_dev *pdev, void __iomem *vaddr, static void hpsa_free_cfgtables(struct ctlr_info *h) { - if (h->transtable) + if (h->transtable) { iounmap(h->transtable); - if (h->cfgtable) + h->transtable = NULL; + } + if (h->cfgtable) { iounmap(h->cfgtable); + h->cfgtable = NULL; + } } /* Find and map CISS config table and transfer table @@ -6822,6 +6828,7 @@ static void hpsa_free_pci_init(struct ctlr_info *h) { hpsa_free_cfgtables(h); /* pci_init 4 */ iounmap(h->vaddr); /* pci_init 3 */ + h->vaddr = NULL; hpsa_disable_interrupt_mode(h); /* pci_init 2 */ pci_release_regions(h->pdev); /* pci_init 2 */ pci_disable_device(h->pdev);/* pci_init 1 */ @@ -6892,6 +6899,7 @@ clean4: /* cfgtables, vaddr, intmode+region, pci */ hpsa_free_cfgtables(h); clean3:/* vaddr, intmode+region, pci */ iounmap(h->vaddr); + h->vaddr = NULL; clean2:/* intmode+region, pci */ hpsa_disable_interrupt_mode(h); pci_release_regions(h->pdev); @@ -6981,16 +6989,23 @@ out_disable: static void hpsa_free_cmd_pool(struct ctlr_info *h) { kfree(h->cmd_pool_bits); - if (h->cmd_pool) + h->cmd_pool_bits = NULL; + if (h->cmd_pool) { pci_free_consistent(h->pdev, h->nr_cmds * sizeof(struct CommandList), h->cmd_pool, h->cmd_pool_dhandle); - if (h->errinfo_pool) + h->cmd_pool = NULL; + h->cmd_pool_dhandle = 0; + } + if (h->errinfo_pool) { pci_free_consistent(h->pdev, h->nr_cmds * sizeof(struct ErrorInfo), h->errinfo_pool, h->errinfo_pool_dhandle); + h->errinfo_pool = NULL; + h->errinfo_pool_dhandle = 0; + } } static int hpsa_alloc_cmd_pool(struct ctlr_info *h) @@ -7038,12 +7053,14 @@ static void hpsa_free_irqs(struct ctlr_info *h) i = h->intr_mode; irq_set_affinity_hint(h->intr[i], NULL); free_irq(h->intr[i], &h->q[i]); +
[PATCH v4 03/43] hpsa: rework controller command submission
From: Webb Scales Allow driver initiated commands to have a timeout. It does not yet try to do anything with timeouts on such commands. We are sending a reset in order to get rid of a command we want to abort. If we make it return on the same reply queue as the command we want to abort, the completion of the aborted command will not race with the completion of the reset command. Rename hpsa_scsi_do_simple_cmd_core() to hpsa_scsi_do_simple_cmd(), since this function is the interface for issuing commands to the controller and not the "core" of that implementation. Add a parameter to it which allows the caller to specify the reply queue to be used. Modify existing callers to specify the default reply queue. Rename __hpsa_scsi_do_simple_cmd_core() to hpsa_scsi_do_simple_cmd_core(), since this routine is the "core" implementation of the "do simple command" function and there is no longer any other function with a similar name. Modify the existing callers of this routine (other than hpsa_scsi_do_simple_cmd()) to instead call hpsa_scsi_do_simple_cmd(), since it will now accept the reply_queue paramenter, and it provides a controller lock-up check. (Also, tweak two related message strings to make them distinct from each other.) Submitting a command to a locked up controller always results in a timeout, so check for controller lock-up before submitting. This is to enable fixing a race between command completions and abort completions on different reply queues in a subsequent patch. We want to be able to specify which reply queue an abort completion should occur on so that it cannot race the completion of the command it is trying to abort. The following race was possible in theory: 1. Abort command is sent to hardware. 2. Command to be aborted simultaneously completes on another reply queue. 3. Hardware receives abort command, decides command has already completed and indicates this to the driver via another different reply queue. 4. driver processes abort completion finds that the hardware does not know about the command, concludes that therefore the command cannot complete, returns SUCCESS indicating to the mid-layer that the scsi_cmnd may be re-used. 5. Command from step 2 is processed and completed back to scsi mid layer (after we already promised that would never happen.) Fix by forcing aborts to complete on the same reply queue as the command they are aborting. Piggybacking device rescanning functionality onto the lockup detection thread is not a good idea because if the controller locks up during device rescanning, then the thread could get stuck, then the lockup isn't detected. Use separate work queues for device rescanning and lockup detection. Detect controller lockup in abort handler. After a lockup is detected, return DO_NO_CONNECT which results in immediate termination of commands rather than DID_ERR which results in retries. Modify detect_controller_lockup() to return the result, to remove the need for a separate check. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Webb Scales Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 329 --- drivers/scsi/hpsa_cmd.h |5 + 2 files changed, 257 insertions(+), 77 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 20a3aa3..b81e5e4 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -253,6 +253,8 @@ static int hpsa_scsi_ioaccel_queue_command(struct ctlr_info *h, struct CommandList *c, u32 ioaccel_handle, u8 *cdb, int cdb_len, u8 *scsi3addr, struct hpsa_scsi_dev_t *phys_disk); static void hpsa_command_resubmit_worker(struct work_struct *work); +static u32 lockup_detected(struct ctlr_info *h); +static int detect_controller_lockup(struct ctlr_info *h); static inline struct ctlr_info *sdev_to_hba(struct scsi_device *sdev) { @@ -748,30 +750,43 @@ static inline u32 next_command(struct ctlr_info *h, u8 q) * a separate special register for submitting commands. */ -/* set_performant_mode: Modify the tag for cciss performant +/* + * set_performant_mode: Modify the tag for cciss performant * set bit 0 for pull model, bits 3-1 for block fetch * register number */ -static void set_performant_mode(struct ctlr_info *h, struct CommandList *c) +#define DEFAULT_REPLY_QUEUE (-1) +static void set_performant_mode(struct ctlr_info *h, struct CommandList *c, + int reply_queue) { if (likely(h->transMethod & CFGTBL_Trans_Performant)) { c->busaddr |= 1 | (h->blockFetchTable[c->Header.SGList] << 1); - if (likely(h->msix_vector > 0)) + if (unlikely(!h->msix_vector)) + return; + if (likely(reply_queue == DEFAULT_REPLY_QUEUE)) c->Header.ReplyQueue = raw_smp_processor_id() % h->nreply_queues; +
[PATCH v4 05/43] hpsa: decrement h->commands_outstanding in fail_all_outstanding_cmds
From: Stephen Cameron make tracking of outstanding commands more robust Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |1 + 1 file changed, 1 insertion(+) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 2ac700b..6ee92af 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -6918,6 +6918,7 @@ static void fail_all_outstanding_cmds(struct ctlr_info *h) if (refcount > 1) { c->err_info->CommandStatus = CMD_CTLR_LOCKUP; finish_cmd(c); + atomic_dec(&h->commands_outstanding); failcount++; } cmd_free(h, c); -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 16/43] hpsa: break hpsa_free_irqs_and_disable_msix into two functions
From: Robert Elliott replace calls to hpsa_free_irqs_and_disable_msix with hpsa_free_irqs and hpsa_disable_interrupt_mode Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Robert Elliott Signed-off-by: Don Brace --- drivers/scsi/hpsa.c | 35 ++- 1 file changed, 18 insertions(+), 17 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index ad2b44c..b743f1a 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -6375,10 +6375,20 @@ static int find_PCI_BAR_index(struct pci_dev *pdev, unsigned long pci_bar_addr) return -1; } +static void hpsa_disable_interrupt_mode(struct ctlr_info *h) +{ + if (h->msix_vector) { + if (h->pdev->msix_enabled) + pci_disable_msix(h->pdev); + } else if (h->msi_vector) { + if (h->pdev->msi_enabled) + pci_disable_msi(h->pdev); + } +} + /* If MSI/MSI-X is supported by the kernel we will try to enable it on * controllers that are capable. If not, we use legacy INTx mode. */ - static void hpsa_interrupt_mode(struct ctlr_info *h) { #ifdef CONFIG_PCI_MSI @@ -7019,20 +7029,6 @@ static int hpsa_kdump_soft_reset(struct ctlr_info *h) return 0; } -static void hpsa_free_irqs_and_disable_msix(struct ctlr_info *h) -{ - hpsa_free_irqs(h); -#ifdef CONFIG_PCI_MSI - if (h->msix_vector) { - if (h->pdev->msix_enabled) - pci_disable_msix(h->pdev); - } else if (h->msi_vector) { - if (h->pdev->msi_enabled) - pci_disable_msi(h->pdev); - } -#endif /* CONFIG_PCI_MSI */ -} - static void hpsa_free_reply_queues(struct ctlr_info *h) { int i; @@ -7049,7 +7045,7 @@ static void hpsa_free_reply_queues(struct ctlr_info *h) static void hpsa_undo_allocations_after_kdump_soft_reset(struct ctlr_info *h) { - hpsa_free_irqs_and_disable_msix(h); + hpsa_free_irqs(h); hpsa_free_sg_chain_blocks(h); hpsa_free_cmd_pool(h); kfree(h->ioaccel1_blockFetchTable); @@ -7061,6 +7057,7 @@ static void hpsa_undo_allocations_after_kdump_soft_reset(struct ctlr_info *h) iounmap(h->transtable); if (h->cfgtable) iounmap(h->cfgtable); + hpsa_disable_interrupt_mode(h); pci_disable_device(h->pdev); pci_release_regions(h->pdev); kfree(h); @@ -7550,7 +7547,8 @@ static void hpsa_shutdown(struct pci_dev *pdev) */ hpsa_flush_cache(h); h->access.set_intr_mask(h, HPSA_INTR_OFF); - hpsa_free_irqs_and_disable_msix(h); + hpsa_free_irqs(h); + hpsa_disable_interrupt_mode(h); /* pci_init 2 */ } static void hpsa_free_device_info(struct ctlr_info *h) @@ -7581,7 +7579,10 @@ static void hpsa_remove_one(struct pci_dev *pdev) destroy_workqueue(h->rescan_ctlr_wq); destroy_workqueue(h->resubmit_wq); hpsa_unregister_scsi(h);/* unhook from SCSI subsystem */ + + /* includes hpsa_free_irqs and hpsa_disable_interrupt_mode */ hpsa_shutdown(pdev); + iounmap(h->vaddr); iounmap(h->transtable); iounmap(h->cfgtable); -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 11/43] hpsa: try resubmitting down raid path on task set full
From: Stephen Cameron allow the controller firmware to queue up commands when the ioaccel device queue is full. Reviewed-by: Scott Teel Reviewed-by: Kevin Barnett Signed-off-by: Don Brace --- drivers/scsi/hpsa.c |3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c index 292b8bd..9c184d1 100644 --- a/drivers/scsi/hpsa.c +++ b/drivers/scsi/hpsa.c @@ -1825,8 +1825,7 @@ static int handle_ioaccel_mode2_error(struct ctlr_info *h, retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_SET_FULL: - /* Make scsi midlayer do unlimited retries */ - cmd->result = DID_IMM_RETRY << 16; + retry = 1; break; case IOACCEL2_STATUS_SR_TASK_COMP_ABORTED: dev_warn(&h->pdev->dev, -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v4 00/43] hpsa update
These patches are based on Linus's tree The changes are: - make function names consistent - refactor functions - cleanup driver messages - cleanup error handling - clean up abort management - enhance sense data reporting - enhance ioaccel command support - add in block layer tag support - clean up resets - update copyright - add in new controller id --- Don Brace (3): hpsa: change driver version hpsa: add PMC to copyright hpsa: add in new controller id Joe Handzik (3): hpsa: use ioaccel2 path to submit IOs to physical drives in HBA mode. hpsa: Get queue depth from identify physical bmic for physical disks. hpsa: add more ioaccel2 error handling, including underrun statuses. Robert Elliott (18): hpsa: make function names consistent hpsa: print accurate SSD Smart Path Enabled status hpsa: break hpsa_free_irqs_and_disable_msix into two functions hpsa: clean up error handling hpsa: refactor freeing of resources into more logical functions hpsa: do not check cmd_alloc return value - it cannnot return NULL hpsa: correct return values from driver functions. hpsa: clean up driver init hpsa: clean up some error reporting output in abort handler hpsa: do not print ioaccel2 warning messages about unusual completions. hpsa: call pci_release_regions after pci_disable_device hpsa: skip free_irq calls if irqs are not allocated hpsa: cleanup for init_one step 2 in kdump hpsa: fix try_soft_reset error handling hpsa: create workqueue after the driver is ready for use hpsa: add interrupt number to /proc/interrupts interrupt name hpsa: use scsi host_no as hpsa controller number hpsa: propagate the error code in hpsa_kdump_soft_reset Stephen Cameron (9): hpsa: add masked physical devices into h->dev[] array hpsa: clean up aborts hpsa: decrement h->commands_outstanding in fail_all_outstanding_cmds hpsa: hpsa decode sense data for io and tmf hpsa: allow lockup detected to be viewed via sysfs hpsa: factor out hpsa_init_cmd function hpsa: do not ignore return value of hpsa_register_scsi hpsa: try resubmitting down raid path on task set full hpsa: add support sending aborts to physical devices via the ioaccel2 path Webb Scales (10): hpsa: clean up host, channel, target, lun prints hpsa: rework controller command submission hpsa: factor out hpsa_ioaccel_submit function hpsa: add ioaccel sg chaining for the ioaccel2 path hpsa: use helper routines for finishing commands hpsa: don't return abort request until target is complete hpsa: refactor and rework support for sending TEST_UNIT_READY hpsa: performance tweak for hpsa_scatter_gather() hpsa: use block layer tag for command allocation hpsa: cleanup reset drivers/scsi/hpsa.c | 2782 +-- drivers/scsi/hpsa.h | 22 drivers/scsi/hpsa_cmd.h | 37 + 3 files changed, 2035 insertions(+), 806 deletions(-) -- Signature -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [RFC] Simlify dif_verify routines and fixup fileio protection information code.
2015-04-16 17:52 GMT+09:00 Sagi Grimberg : > On 4/15/2015 7:10 PM, Martin K. Petersen wrote: >>> >>> "Sagi" == Sagi Grimberg writes: >> >> > By the commit 436f4a0a ("loopback: Add fabric_prot_type attribute > support"), When WRITE_SAME command with WRPROTECT=0 is executed, > sbc_dif_generate() is called but cmd->t_prot_sg is NULL as block > layer didn't allocate it for WRITE_SAME. >> >> >> Sagi> Actually this is a bug. Why didn't the initiator allocate >> Sagi> integrity meta-data for WRITE_SAME? Looking at the code it looks >> Sagi> like it should. >> >> We don't issue WRITE SAME with PI so there is no prot SGL. >> > > Is there a specific reason why we don't? It is not only for the WRITE SAME requests from block device but also for READ/WRITE with PROTECT=0 requests by SG_IO. So isn't is appropreate to allocate prot SGL in target_write_prot_action() (and mark se_cmd->se_cmd_flags to release it at deallocation time)? -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [patch] sd: fix an error return in probe()
On 01/19/2015 03:41 PM, Dan Carpenter wrote: > If device_add() fails then it should return the error code but instead > the current code returns success. > > Signed-off-by: Dan Carpenter > > diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c > index ebf35cb6..75a0b55 100644 > --- a/drivers/scsi/sd.c > +++ b/drivers/scsi/sd.c > @@ -3019,7 +3019,8 @@ static int sd_probe(struct device *dev) > sdkp->dev.class = &sd_disk_class; > dev_set_name(&sdkp->dev, "%s", dev_name(dev)); > > - if (device_add(&sdkp->dev)) > + error = device_add(&sdkp->dev); > + if (error) > goto out_free_index; > > get_device(dev); > -- > To unsubscribe from this list: send the line "unsubscribe linux-scsi" in > the body of a message to majord...@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html Reviewed-by: Tomas Henzl Tomas -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [patch] csiostor: fix an error code in csio_hw_init()
On 04/14/2015 04:32 PM, Dan Carpenter wrote: > We should return -ENOMEM if kzalloc() fails here instead of returning > success. > > Signed-off-by: Dan Carpenter > > diff --git a/drivers/scsi/csiostor/csio_hw.c b/drivers/scsi/csiostor/csio_hw.c > index 2e66f34..622bdab 100644 > --- a/drivers/scsi/csiostor/csio_hw.c > +++ b/drivers/scsi/csiostor/csio_hw.c > @@ -3928,6 +3928,7 @@ csio_hw_init(struct csio_hw *hw) > > evt_entry = kzalloc(sizeof(struct csio_evt_msg), GFP_KERNEL); > if (!evt_entry) { > + rv = -ENOMEM; > csio_err(hw, "Failed to initialize eventq"); > goto err_evtq_cleanup; > } > -- > To unsubscribe from this list: send the line "unsubscribe linux-scsi" in > the body of a message to majord...@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html Reviewed-by: Tomas Henzl Tomas -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 3/3] uas: Set max_sectors_240 quirk for ASM1053 devices
Testing has shown that ASM1053 devices do not work properly with transfers larger than 240 sectors, so set max_sectors to 240 on these. Reported-by: Steve Bangert Signed-off-by: Hans de Goede --- drivers/usb/storage/uas-detect.h | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/usb/storage/uas-detect.h b/drivers/usb/storage/uas-detect.h index 63ae161..f58caa9 100644 --- a/drivers/usb/storage/uas-detect.h +++ b/drivers/usb/storage/uas-detect.h @@ -74,7 +74,7 @@ static int uas_use_uas_driver(struct usb_interface *intf, * this writing the following versions exist: * ASM1051 - no uas support version * ASM1051 - with broken (*) uas support -* ASM1053 - with working uas support +* ASM1053 - with working uas support, but problems with large xfers * ASM1153 - with working uas support * * Devices with these chips re-use a number of device-ids over the @@ -104,6 +104,9 @@ static int uas_use_uas_driver(struct usb_interface *intf, } else if (usb_ss_max_streams(&eps[1]->ss_ep_comp) == 32) { /* Possibly an ASM1051, disable uas */ flags |= US_FL_IGNORE_UAS; + } else { + /* ASM1053, these have issues with large transfers */ + flags |= US_FL_MAX_SECTORS_240; } } -- 2.3.5 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/3] uas: Add US_FL_MAX_SECTORS_240 flag
The usb-storage driver sets max_sectors = 240 in its scsi-host template, for uas we do not want to do that for all devices, but testing has shown that some devices need it. This commit adds a US_FL_MAX_SECTORS_240 flag for such devices, and implements support for it in uas.c, while at it it also adds support for US_FL_MAX_SECTORS_64 to uas.c. Signed-off-by: Hans de Goede --- drivers/usb/storage/uas.c | 10 +- drivers/usb/storage/usb.c | 6 +- include/linux/usb_usual.h | 2 ++ 3 files changed, 16 insertions(+), 2 deletions(-) diff --git a/drivers/usb/storage/uas.c b/drivers/usb/storage/uas.c index c6109c1..6d3122a 100644 --- a/drivers/usb/storage/uas.c +++ b/drivers/usb/storage/uas.c @@ -759,7 +759,10 @@ static int uas_eh_bus_reset_handler(struct scsi_cmnd *cmnd) static int uas_slave_alloc(struct scsi_device *sdev) { - sdev->hostdata = (void *)sdev->host->hostdata; + struct uas_dev_info *devinfo = + (struct uas_dev_info *)sdev->host->hostdata; + + sdev->hostdata = devinfo; /* USB has unusual DMA-alignment requirements: Although the * starting address of each scatter-gather element doesn't matter, @@ -778,6 +781,11 @@ static int uas_slave_alloc(struct scsi_device *sdev) */ blk_queue_update_dma_alignment(sdev->request_queue, (512 - 1)); + if (devinfo->flags & US_FL_MAX_SECTORS_64) + blk_queue_max_hw_sectors(sdev->request_queue, 64); + else if (devinfo->flags & US_FL_MAX_SECTORS_240) + blk_queue_max_hw_sectors(sdev->request_queue, 240); + return 0; } diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c index db6f6b5..6c10c88 100644 --- a/drivers/usb/storage/usb.c +++ b/drivers/usb/storage/usb.c @@ -479,7 +479,8 @@ void usb_stor_adjust_quirks(struct usb_device *udev, unsigned long *fflags) US_FL_SINGLE_LUN | US_FL_NO_WP_DETECT | US_FL_NO_READ_DISC_INFO | US_FL_NO_READ_CAPACITY_16 | US_FL_INITIAL_READ10 | US_FL_WRITE_CACHE | - US_FL_NO_ATA_1X | US_FL_NO_REPORT_OPCODES); + US_FL_NO_ATA_1X | US_FL_NO_REPORT_OPCODES | + US_FL_MAX_SECTORS_240); p = quirks; while (*p) { @@ -520,6 +521,9 @@ void usb_stor_adjust_quirks(struct usb_device *udev, unsigned long *fflags) case 'f': f |= US_FL_NO_REPORT_OPCODES; break; + case 'g': + f |= US_FL_MAX_SECTORS_240; + break; case 'h': f |= US_FL_CAPACITY_HEURISTICS; break; diff --git a/include/linux/usb_usual.h b/include/linux/usb_usual.h index a7f2604..7f5f78b 100644 --- a/include/linux/usb_usual.h +++ b/include/linux/usb_usual.h @@ -77,6 +77,8 @@ /* Cannot handle ATA_12 or ATA_16 CDBs */ \ US_FLAG(NO_REPORT_OPCODES, 0x0400) \ /* Cannot handle MI_REPORT_SUPPORTED_OPERATION_CODES */ \ + US_FLAG(MAX_SECTORS_240,0x0800) \ + /* Sets max_sectors to 240 */ \ #define US_FLAG(name, value) US_FL_##name = value , enum { US_DO_ALL_FLAGS }; -- 2.3.5 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 1/3] uas: Allow uas_use_uas_driver to return usb-storage flags
uas_use_uas_driver may set some US_FL_foo flags during detection, currently these are stored in a local variable and then throw away, but these may be of interest to the caller, so add an extra parameter to (optionally) return the detected flags, and use this in the uas driver. Signed-off-by: Hans de Goede --- drivers/usb/storage/uas-detect.h | 6 +- drivers/usb/storage/uas.c| 6 +++--- drivers/usb/storage/usb.c| 2 +- 3 files changed, 9 insertions(+), 5 deletions(-) diff --git a/drivers/usb/storage/uas-detect.h b/drivers/usb/storage/uas-detect.h index 9893d69..63ae161 100644 --- a/drivers/usb/storage/uas-detect.h +++ b/drivers/usb/storage/uas-detect.h @@ -51,7 +51,8 @@ static int uas_find_endpoints(struct usb_host_interface *alt, } static int uas_use_uas_driver(struct usb_interface *intf, - const struct usb_device_id *id) + const struct usb_device_id *id, + unsigned long *flags_ret) { struct usb_host_endpoint *eps[4] = { }; struct usb_device *udev = interface_to_usbdev(intf); @@ -132,5 +133,8 @@ static int uas_use_uas_driver(struct usb_interface *intf, return 0; } + if (flags_ret) + *flags_ret = flags; + return 1; } diff --git a/drivers/usb/storage/uas.c b/drivers/usb/storage/uas.c index 6cdabdc..c6109c1 100644 --- a/drivers/usb/storage/uas.c +++ b/drivers/usb/storage/uas.c @@ -887,8 +887,9 @@ static int uas_probe(struct usb_interface *intf, const struct usb_device_id *id) struct Scsi_Host *shost = NULL; struct uas_dev_info *devinfo; struct usb_device *udev = interface_to_usbdev(intf); + unsigned long dev_flags; - if (!uas_use_uas_driver(intf, id)) + if (!uas_use_uas_driver(intf, id, &dev_flags)) return -ENODEV; if (uas_switch_interface(udev, intf)) @@ -910,8 +911,7 @@ static int uas_probe(struct usb_interface *intf, const struct usb_device_id *id) devinfo->udev = udev; devinfo->resetting = 0; devinfo->shutdown = 0; - devinfo->flags = id->driver_info; - usb_stor_adjust_quirks(udev, &devinfo->flags); + devinfo->flags = dev_flags; init_usb_anchor(&devinfo->cmd_urbs); init_usb_anchor(&devinfo->sense_urbs); init_usb_anchor(&devinfo->data_urbs); diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c index 5600c33..db6f6b5 100644 --- a/drivers/usb/storage/usb.c +++ b/drivers/usb/storage/usb.c @@ -1080,7 +1080,7 @@ static int storage_probe(struct usb_interface *intf, /* If uas is enabled and this device can do uas then ignore it. */ #if IS_ENABLED(CONFIG_USB_UAS) - if (uas_use_uas_driver(intf, id)) + if (uas_use_uas_driver(intf, id, NULL)) return -ENXIO; #endif -- 2.3.5 -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[Bug 90601] panic on write to 3ware raid array
https://bugzilla.kernel.org/show_bug.cgi?id=90601 mer...@liao.homelinux.org changed: What|Removed |Added Attachment #162291|0 |1 is obsolete|| -- You are receiving this mail because: You are the assignee for the bug. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[Bug 90601] panic on write to 3ware raid array
https://bugzilla.kernel.org/show_bug.cgi?id=90601 --- Comment #19 from mer...@liao.homelinux.org --- Created attachment 174181 --> https://bugzilla.kernel.org/attachment.cgi?id=174181&action=edit crash-backtrace -- You are receiving this mail because: You are the assignee for the bug. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[Bug 90601] panic on write to 3ware raid array
https://bugzilla.kernel.org/show_bug.cgi?id=90601 --- Comment #18 from mer...@liao.homelinux.org --- Created attachment 174171 --> https://bugzilla.kernel.org/attachment.cgi?id=174171&action=edit dmesg I finally managed to get a dmesg output with the crashing kernel. Especially this part might indicate the root of the problem? [Thu Apr 16 13:02:10 2015] [ cut here ] [Thu Apr 16 13:02:10 2015] WARNING: CPU: 6 PID: 1736 at lib/dma-debug.c:601 debug_dma_assert_idle+0x17c/0x1e0() [Thu Apr 16 13:02:10 2015] 3w-sas :03:00.0: DMA-API: cpu touching an active dma mapped cacheline [cln=0x000101ff8e00] [Thu Apr 16 13:02:10 2015] Modules linked in: [Thu Apr 16 13:02:10 2015] CPU: 6 PID: 1736 Comm: mount Not tainted 4.0.0-gentoo #1 [Thu Apr 16 13:02:11 2015] Hardware name: Supermicro X9DR7/E-(J)LN4F/X9DR7/E-(J)LN4F, BIOS 3.0a 09/10/2013 [Thu Apr 16 13:02:11 2015] 8170e0f5 88406050fcb8 814c8778 009a [Thu Apr 16 13:02:11 2015] 88406050fd08 88406050fcf8 8107c250 884060422e08 [Thu Apr 16 13:02:11 2015] 8840647fe5e0 0206 ea00e1bf9ce8 884060422e08 [Thu Apr 16 13:02:11 2015] Call Trace: [Thu Apr 16 13:02:11 2015] [] dump_stack+0x45/0x57 [Thu Apr 16 13:02:11 2015] [] warn_slowpath_common+0x80/0xc0 [Thu Apr 16 13:02:11 2015] [] warn_slowpath_fmt+0x41/0x50 [Thu Apr 16 13:02:11 2015] [] debug_dma_assert_idle+0x17c/0x1e0 [Thu Apr 16 13:02:11 2015] [] do_wp_page+0xc4/0x810 [Thu Apr 16 13:02:11 2015] [] handle_mm_fault+0xb3c/0x10f0 [Thu Apr 16 13:02:11 2015] [] ? do_mmap_pgoff+0x34d/0x400 [Thu Apr 16 13:02:11 2015] [] __do_page_fault+0x146/0x390 [Thu Apr 16 13:02:11 2015] [] do_page_fault+0xc/0x10 [Thu Apr 16 13:02:11 2015] [] page_fault+0x22/0x30 [Thu Apr 16 13:02:11 2015] ---[ end trace 326b0530baa65706 ]--- I was still able to login with root after that and reproduce the crash with another backtrace. See the next attachment. -- You are receiving this mail because: You are the assignee for the bug. -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [RFC] Simlify dif_verify routines and fixup fileio protection information code.
On 4/15/2015 7:10 PM, Martin K. Petersen wrote: "Sagi" == Sagi Grimberg writes: By the commit 436f4a0a ("loopback: Add fabric_prot_type attribute support"), When WRITE_SAME command with WRPROTECT=0 is executed, sbc_dif_generate() is called but cmd->t_prot_sg is NULL as block layer didn't allocate it for WRITE_SAME. Sagi> Actually this is a bug. Why didn't the initiator allocate Sagi> integrity meta-data for WRITE_SAME? Looking at the code it looks Sagi> like it should. We don't issue WRITE SAME with PI so there is no prot SGL. Is there a specific reason why we don't? -- To unsubscribe from this list: send the line "unsubscribe linux-scsi" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html