diff --git a/Documentation/devicetree/bindings/phy/qcom,sc8280xp-qmp-ufs-phy.yaml b/Documentation/devicetree/bindings/phy/qcom,sc8280xp-qmp-ufs-phy.yaml
index 4efe40c0dc97..a7eda537e716 100644
--- a/Documentation/devicetree/bindings/phy/qcom,sc8280xp-qmp-ufs-phy.yaml
+++ b/Documentation/devicetree/bindings/phy/qcom,sc8280xp-qmp-ufs-phy.yaml
@@ -38,6 +38,7 @@ properties:
               - qcom,kaanapali-qmp-ufs-phy
           - const: qcom,sm8750-qmp-ufs-phy
       - enum:
+          - qcom,glymur-qmp-ufs-phy
           - qcom,hawi-qmp-ufs-phy
           - qcom,milos-qmp-ufs-phy
           - qcom,msm8996-qmp-ufs-phy
@@ -109,6 +110,7 @@ allOf:
         compatible:
           contains:
             enum:
+              - qcom,glymur-qmp-ufs-phy
               - qcom,hawi-qmp-ufs-phy
               - qcom,milos-qmp-ufs-phy
               - qcom,msm8998-qmp-ufs-phy
@@ -162,6 +164,7 @@ allOf:
         compatible:
           contains:
             enum:
+              - qcom,glymur-qmp-ufs-phy
               - qcom,msm8996-qmp-ufs-phy
               - qcom,msm8998-qmp-ufs-phy
     then:
diff --git a/Documentation/devicetree/bindings/ufs/qcom,sm8650-ufshc.yaml b/Documentation/devicetree/bindings/ufs/qcom,sm8650-ufshc.yaml
index d03295806657..f132b1a9ebc2 100644
--- a/Documentation/devicetree/bindings/ufs/qcom,sm8650-ufshc.yaml
+++ b/Documentation/devicetree/bindings/ufs/qcom,sm8650-ufshc.yaml
@@ -16,6 +16,7 @@ select:
       contains:
         enum:
           - qcom,eliza-ufshc
+          - qcom,glymur-ufshc
           - qcom,hawi-ufshc
           - qcom,kaanapali-ufshc
           - qcom,maili-ufshc
@@ -30,6 +31,7 @@ properties:
     items:
       - enum:
           - qcom,eliza-ufshc
+          - qcom,glymur-ufshc
           - qcom,hawi-ufshc
           - qcom,kaanapali-ufshc
           - qcom,maili-ufshc
@@ -80,6 +82,7 @@ allOf:
           contains:
             enum:
               - qcom,eliza-ufshc
+              - qcom,glymur-ufshc
               - qcom,maili-ufshc
               - qcom,nord-ufshc
     then:
diff --git a/Documentation/scsi/ufs.rst b/Documentation/scsi/ufs.rst
index a7b2b2ed1c3a..06f1b9b4e8dd 100644
--- a/Documentation/scsi/ufs.rst
+++ b/Documentation/scsi/ufs.rst
@@ -19,6 +19,7 @@ Universal Flash Storage
      3.4 SCSI Error handling
    4. BSG Support
    5. UFS Reference Clock Frequency configuration
+   6. Testing with QEMU
 
 
 1. Overview
@@ -208,3 +209,40 @@ the UFS specification. UFS subsystem will attempt to read the value when
 executing common controller initialization. If the value is available, UFS
 subsystem will ensure the bRefClkFreq attribute of the UFS storage device is
 set accordingly and will modify it if there is a mismatch.
+
+6. Testing with QEMU
+====================
+
+QEMU emulates a UFS host controller as a PCI device named "ufs" and
+logical units named "ufs-lu". This can be used to test changes to the
+UFS core and to ufshcd-pci without UFS hardware.
+
+The "ufs" and "ufs-lu" devices are available since QEMU 8.2, and the
+"mcq" property since QEMU 9.1.
+
+Enable the following kernel options on top of the architecture
+defconfig::
+
+	CONFIG_SCSI_UFSHCD=y
+	CONFIG_SCSI_UFSHCD_PCI=y
+	CONFIG_BLK_DEV_SD=y
+
+Example for an arm64 guest with one 1 GiB logical unit::
+
+	qemu-img create -f raw ufs.img 1G
+	qemu-system-aarch64 -M virt -cpu max -smp 4 -m 2G -nographic \
+		-kernel arch/arm64/boot/Image -initrd rootfs.cpio.gz \
+		-append "console=ttyAMA0" \
+		-drive file=ufs.img,if=none,id=lu0,format=raw \
+		-device ufs,id=ufs0,serial=0001,mcq=on \
+		-device ufs-lu,drive=lu0,bus=ufs0,lun=0
+
+The logical unit appears as a SCSI disk (for example /dev/sda). Drop
+"mcq=on" to test the single doorbell mode instead of MCQ. The same
+-device options work with qemu-system-x86_64.
+
+The emulation accepts the link startup and hibernate enter/exit UIC
+commands and, since QEMU 11.1, DME get/set and the power mode change
+sequence, but it does not model UniPro, M-PHY or the resulting link
+state. Clock gating hardware and vendor host drivers are not exercised
+either. Changes in those areas still need testing on real hardware.
diff --git a/MAINTAINERS b/MAINTAINERS
index 7b5c27c68e5d..34ecc8cfc4ab 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -5327,9 +5327,9 @@ F:	drivers/net/ethernet/broadcom/bnx2.*
 F:	drivers/net/ethernet/broadcom/bnx2_*
 
 BROADCOM BNX2FC 10 GIGABIT FCOE DRIVER
-M:	Saurav Kashyap <skashyap@marvell.com>
-M:	Javed Hasan <jhasan@marvell.com>
-M:	GR-QLogic-Storage-Upstream@marvell.com
+M:	Nilesh Javali <njavali@marvell.com>
+M:	Manish Rangankar <mrangankar@marvell.com>
+M:	GR-ETH-Storage-Upstream@marvell.com
 L:	linux-scsi@vger.kernel.org
 S:	Supported
 F:	drivers/scsi/bnx2fc/
@@ -5337,7 +5337,7 @@ F:	drivers/scsi/bnx2fc/
 BROADCOM BNX2I 1/10 GIGABIT iSCSI DRIVER
 M:	Nilesh Javali <njavali@marvell.com>
 M:	Manish Rangankar <mrangankar@marvell.com>
-M:	GR-QLogic-Storage-Upstream@marvell.com
+M:	GR-ETH-Storage-Upstream@marvell.com
 L:	linux-scsi@vger.kernel.org
 S:	Supported
 F:	drivers/scsi/bnx2i/
@@ -22145,9 +22145,9 @@ S:	Maintained
 F:	drivers/power/reset/qemu-virt-ctrl.c
 
 QLOGIC QL41xxx FCOE DRIVER
-M:	Saurav Kashyap <skashyap@marvell.com>
-M:	Javed Hasan <jhasan@marvell.com>
-M:	GR-QLogic-Storage-Upstream@marvell.com
+M:	Nilesh Javali <njavali@marvell.com>
+M:	Manish Rangankar <mrangankar@marvell.com>
+M:	GR-ETH-Storage-Upstream@marvell.com
 L:	linux-scsi@vger.kernel.org
 S:	Supported
 F:	drivers/scsi/qedf/
@@ -22155,7 +22155,7 @@ F:	drivers/scsi/qedf/
 QLOGIC QL41xxx ISCSI DRIVER
 M:	Nilesh Javali <njavali@marvell.com>
 M:	Manish Rangankar <mrangankar@marvell.com>
-M:	GR-QLogic-Storage-Upstream@marvell.com
+M:	GR-ETH-Storage-Upstream@marvell.com
 L:	linux-scsi@vger.kernel.org
 S:	Supported
 F:	drivers/scsi/qedi/
@@ -24576,8 +24576,11 @@ F:	include/uapi/scsi/
 F:	include/ufs/
 
 SCSI TAPE DRIVER
+M:	Laurence Oberman <loberman@redhat.com>
+M:	John Meneghini <jmeneghi@redhat.com>
 L:	linux-scsi@vger.kernel.org
-S:	Orphan
+S:	Maintained
+W:	https://github.com/johnmeneghini/tape_tests
 F:	Documentation/scsi/st.rst
 F:	drivers/scsi/st.*
 F:	drivers/scsi/st_*.h
@@ -28042,6 +28045,8 @@ F:	lib/union_find.c
 UNIVERSAL FLASH STORAGE HOST CONTROLLER DRIVER
 R:	Alim Akhtar <alim.akhtar@samsung.com>
 R:	Bart Van Assche <bvanassche@acm.org>
+R:	Bean Huo <beanhuo@micron.com>
+R:	Stanley Jhu <stanleyjhu@google.com>
 L:	linux-scsi@vger.kernel.org
 S:	Supported
 F:	Documentation/devicetree/bindings/ufs/
diff --git a/block/blk-zoned.c b/block/blk-zoned.c
index a5afb842bf35..475aa16bc41a 100644
--- a/block/blk-zoned.c
+++ b/block/blk-zoned.c
@@ -2018,12 +2018,17 @@ static int disk_revalidate_zone_resources(struct gendisk *disk,
 				struct blk_revalidate_zone_args *args)
 {
 	struct queue_limits *lim = &disk->queue->limits;
+	unsigned long long nr_zones;
 	unsigned int pool_size;
 	int ret = 0;
 
 	args->disk = disk;
-	args->nr_zones =
-		DIV_ROUND_UP_ULL(get_capacity(disk), lim->chunk_sectors);
+	nr_zones = DIV_ROUND_UP_ULL(get_capacity(disk), lim->chunk_sectors);
+	if (nr_zones > UINT_MAX) {
+		pr_warn("%s: Too many zones (%llu)\n", disk->disk_name, nr_zones);
+		return -EINVAL;
+	}
+	args->nr_zones = nr_zones;
 
 	/* Cached zone conditions: 1 byte per zone */
 	args->zones_cond = kzalloc(args->nr_zones, GFP_NOIO);
@@ -2131,6 +2136,12 @@ static int blk_revalidate_zone_cond(struct blk_zone *zone, unsigned int idx,
 {
 	enum blk_zone_cond cond = zone->cond;
 
+	if (idx >= args->nr_zones) {
+		pr_warn("%s: Zone report index %u exceeds zone count %u\n",
+			args->disk->disk_name, idx, args->nr_zones);
+		return -EINVAL;
+	}
+
 	/* Check that the zone condition is consistent with the zone type. */
 	switch (cond) {
 	case BLK_ZONE_COND_NOT_WP:
diff --git a/block/bsg-lib.c b/block/bsg-lib.c
index 895db30a7033..536cee4430a7 100644
--- a/block/bsg-lib.c
+++ b/block/bsg-lib.c
@@ -23,11 +23,14 @@ struct bsg_set {
 	struct bsg_device	*bd;
 	bsg_job_fn		*job_fn;
 	bsg_timeout_fn		*timeout_fn;
+	unsigned int		reply_len;
 };
 
 static int bsg_transport_sg_io_fn(struct request_queue *q, struct sg_io_v4 *hdr,
 		bool open_for_write, unsigned int timeout)
 {
+	struct bsg_set *bset =
+		container_of(q->tag_set, struct bsg_set, tag_set);
 	struct bsg_job *job;
 	struct request *rq;
 	struct bio *bio;
@@ -50,7 +53,7 @@ static int bsg_transport_sg_io_fn(struct request_queue *q, struct sg_io_v4 *hdr,
 	reply = job->reply;
 	memset(job, 0, sizeof(*job));
 	job->reply = reply;
-	job->reply_len = SCSI_SENSE_BUFFERSIZE;
+	job->reply_len = bset->reply_len;
 	job->dd_data = job + 1;
 
 	job->request_len = hdr->request_len;
@@ -301,9 +304,10 @@ static blk_status_t bsg_queue_rq(struct blk_mq_hw_ctx *hctx,
 static int bsg_init_rq(struct blk_mq_tag_set *set, struct request *req,
 		       unsigned int hctx_idx, int numa_node)
 {
+	struct bsg_set *bset = container_of(set, struct bsg_set, tag_set);
 	struct bsg_job *job = blk_mq_rq_to_pdu(req);
 
-	job->reply = kzalloc(SCSI_SENSE_BUFFERSIZE, GFP_KERNEL);
+	job->reply = kzalloc(bset->reply_len, GFP_KERNEL);
 	if (!job->reply)
 		return -ENOMEM;
 	return 0;
@@ -358,10 +362,12 @@ static const struct blk_mq_ops bsg_mq_ops = {
  * @job_fn: bsg job handler
  * @timeout: timeout handler function pointer
  * @dd_job_size: size of LLD data needed for each job
+ * @reply_len: size of the reply buffer needed for each job
  */
 struct request_queue *bsg_setup_queue(struct device *dev, const char *name,
 		struct queue_limits *lim, bsg_job_fn *job_fn,
-		bsg_timeout_fn *timeout, int dd_job_size)
+		bsg_timeout_fn *timeout, int dd_job_size,
+		unsigned int reply_len)
 {
 	struct bsg_set *bset;
 	struct blk_mq_tag_set *set;
@@ -374,6 +380,7 @@ struct request_queue *bsg_setup_queue(struct device *dev, const char *name,
 
 	bset->job_fn = job_fn;
 	bset->timeout_fn = timeout;
+	bset->reply_len = reply_len;
 
 	set = &bset->tag_set;
 	set->ops = &bsg_mq_ops;
diff --git a/block/bsg.c b/block/bsg.c
index 82aaf3cee582..b296fa373292 100644
--- a/block/bsg.c
+++ b/block/bsg.c
@@ -132,7 +132,10 @@ static long bsg_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
 	case SG_SET_TIMEOUT:
 		if (get_user(val, intp))
 			return -EFAULT;
-		bd->timeout = clock_t_to_jiffies(val);
+		if (val < 0)
+			return -EIO;
+		bd->timeout = min(clock_t_to_jiffies(val),
+				  min(UINT_MAX, MAX_JIFFY_OFFSET));
 		return 0;
 	case SG_GET_TIMEOUT:
 		return jiffies_to_clock_t(bd->timeout);
diff --git a/drivers/infiniband/ulp/iser/iser_initiator.c b/drivers/infiniband/ulp/iser/iser_initiator.c
index 12a2d12fef07..d8e732425e77 100644
--- a/drivers/infiniband/ulp/iser/iser_initiator.c
+++ b/drivers/infiniband/ulp/iser/iser_initiator.c
@@ -604,7 +604,8 @@ static int iser_check_remote_inv(struct iser_conn *iser_conn, struct ib_wc *wc,
 			return -EPROTO;
 		}
 
-		task = iscsi_itt_to_ctask(iser_conn->iscsi_conn, hdr->itt);
+		task = iscsi_itt_to_ctask(iser_conn->iscsi_conn->session,
+					  iser_conn->iscsi_conn, hdr->itt);
 		if (likely(task)) {
 			struct iscsi_iser_task *iser_task = task->dd_data;
 			struct iser_fr_desc *desc;
diff --git a/drivers/scsi/Kconfig b/drivers/scsi/Kconfig
index 4a2af0f702e1..1eec66195cf4 100644
--- a/drivers/scsi/Kconfig
+++ b/drivers/scsi/Kconfig
@@ -753,6 +753,7 @@ config SCSI_IBMVFC
 	tristate "IBM Virtual FC support"
 	depends on PPC_PSERIES && SCSI
 	depends on SCSI_FC_ATTRS
+	depends on NVME_FC || NVME_FC=n
 	help
 	  This is the IBM POWER Virtual FC Client
 
diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile
index 533623382eca..5b9328dc3b62 100644
--- a/drivers/scsi/Makefile
+++ b/drivers/scsi/Makefile
@@ -14,29 +14,8 @@
 # satisfy certain initialization assumptions in the SCSI layer.
 # *!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!*!
 
-CONTEXT_ANALYSIS_constants.o := y
-CONTEXT_ANALYSIS_hosts.o := y
-CONTEXT_ANALYSIS_scsi.o := y
-CONTEXT_ANALYSIS_scsi_common.o := y
-CONTEXT_ANALYSIS_scsi_devinfo.o := y
-CONTEXT_ANALYSIS_scsi_dh.o := y
-CONTEXT_ANALYSIS_scsi_error.o := y
-CONTEXT_ANALYSIS_scsi_ioctl.o := y
-CONTEXT_ANALYSIS_scsi_lib.o := y
-CONTEXT_ANALYSIS_scsi_lib_dma.o := y
-CONTEXT_ANALYSIS_scsi_logging.o := y
-CONTEXT_ANALYSIS_scsi_netlink.o := y
-CONTEXT_ANALYSIS_scsi_pm.o := y
-CONTEXT_ANALYSIS_scsi_proc.o := y
-CONTEXT_ANALYSIS_scsi_scan.o := y
-CONTEXT_ANALYSIS_scsi_sysfs.o := y
-CONTEXT_ANALYSIS_scsi_trace.o := y
-CONTEXT_ANALYSIS_scsicam.o := y
-CONTEXT_ANALYSIS_sd.o := y
-CONTEXT_ANALYSIS_sd_dif.o := y
-CONTEXT_ANALYSIS_sd_zbc.o := y
-CONTEXT_ANALYSIS_sr.o := y
-CONTEXT_ANALYSIS_sr_ioctl.o := y
+CONTEXT_ANALYSIS := y
+CONTEXT_ANALYSIS_BusLogic.o := n
 
 CFLAGS_aha152x.o =   -DAHA152X_STAT -DAUTOCONF
 
diff --git a/drivers/scsi/NCR5380.c b/drivers/scsi/NCR5380.c
index 006dcf981218..6afbd5936892 100644
--- a/drivers/scsi/NCR5380.c
+++ b/drivers/scsi/NCR5380.c
@@ -718,7 +718,7 @@ static void NCR5380_main(struct work_struct *work)
 			 * entire unit.
 			 */
 
-			if (!NCR5380_select(instance, cmd)) {
+			if (!NCR5380_select(hostdata, cmd)) {
 				dsprintk(NDEBUG_MAIN, instance, "main: select complete\n");
 			} else {
 				dsprintk(NDEBUG_MAIN | NDEBUG_QUEUES, instance,
@@ -728,7 +728,7 @@ static void NCR5380_main(struct work_struct *work)
 		}
 		if (hostdata->connected && !hostdata->dma_len) {
 			dsprintk(NDEBUG_MAIN, instance, "main: performing information transfer\n");
-			NCR5380_information_transfer(instance);
+			NCR5380_information_transfer(hostdata);
 			done = 0;
 		}
 		if (!hostdata->connected) {
@@ -937,7 +937,7 @@ static irqreturn_t __maybe_unused NCR5380_intr(int irq, void *dev_id)
 
 /**
  * NCR5380_select - attempt arbitration and selection for a given command
- * @instance: the Scsi_Host instance
+ * @hostdata: host private data
  * @cmd: the scsi_cmnd to execute
  *
  * This routine establishes an I_T_L nexus for a SCSI command. This involves
@@ -960,10 +960,11 @@ static irqreturn_t __maybe_unused NCR5380_intr(int irq, void *dev_id)
  * cmd->result host byte set to DID_BAD_TARGET.
  */
 
-static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
+static bool NCR5380_select(struct NCR5380_hostdata *hostdata,
+			   struct scsi_cmnd *cmd)
 	__releases(&hostdata->lock) __acquires(&hostdata->lock)
 {
-	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+	struct Scsi_Host *instance = hostdata->host;
 	unsigned char tmp[3], phase;
 	unsigned char *data;
 	int len;
@@ -1643,23 +1644,23 @@ static int NCR5380_transfer_dma(struct Scsi_Host *instance,
 }
 
 /*
- * Function : NCR5380_information_transfer (struct Scsi_Host *instance)
+ * Function : NCR5380_information_transfer(struct NCR5380_hostdata *hostdata)
  *
  * Purpose : run through the various SCSI phases and do as the target
  * directs us to.  Operates on the currently connected command,
  * instance->connected.
  *
- * Inputs : instance, instance for which we are doing commands
+ * Inputs : hostdata, the private host data
  *
  * Side effects : SCSI things happen, the disconnected queue will be
  * modified if a command disconnects, *instance->connected will
  * change.
  */
 
-static void NCR5380_information_transfer(struct Scsi_Host *instance)
+static void NCR5380_information_transfer(struct NCR5380_hostdata *hostdata)
 	__releases(&hostdata->lock) __acquires(&hostdata->lock)
 {
-	struct NCR5380_hostdata *hostdata = shost_priv(instance);
+	struct Scsi_Host *instance = hostdata->host;
 	unsigned char msgout = NOP;
 	int sink = 0;
 	int len;
diff --git a/drivers/scsi/NCR5380.h b/drivers/scsi/NCR5380.h
index d402d4bffcb2..450b08da5858 100644
--- a/drivers/scsi/NCR5380.h
+++ b/drivers/scsi/NCR5380.h
@@ -278,12 +278,13 @@ static void NCR5380_print(struct Scsi_Host *instance);
 static int NCR5380_init(struct Scsi_Host *instance, int flags);
 static int NCR5380_maybe_reset_bus(struct Scsi_Host *);
 static void NCR5380_exit(struct Scsi_Host *instance);
-static void NCR5380_information_transfer(struct Scsi_Host *instance);
+static void NCR5380_information_transfer(struct NCR5380_hostdata *hostdata);
 static irqreturn_t NCR5380_intr(int irq, void *dev_id);
 static void NCR5380_main(struct work_struct *work);
 static const char *NCR5380_info(struct Scsi_Host *instance);
 static void NCR5380_reselect(struct Scsi_Host *instance);
-static bool NCR5380_select(struct Scsi_Host *, struct scsi_cmnd *);
+static bool NCR5380_select(struct NCR5380_hostdata *hostdata,
+			   struct scsi_cmnd *);
 static int NCR5380_transfer_dma(struct Scsi_Host *instance, unsigned char *phase, int *count, unsigned char **data);
 static void NCR5380_transfer_pio(struct Scsi_Host *instance,
 				 unsigned char *phase, int *count,
diff --git a/drivers/scsi/aacraid/Makefile b/drivers/scsi/aacraid/Makefile
index 8f0eec682bb6..415e0ed5ad24 100644
--- a/drivers/scsi/aacraid/Makefile
+++ b/drivers/scsi/aacraid/Makefile
@@ -1,6 +1,8 @@
 # SPDX-License-Identifier: GPL-2.0-only
 # Adaptec aacraid
 
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_AACRAID) := aacraid.o
 
 aacraid-objs	:= linit.o aachba.o commctrl.o comminit.o commsup.o \
diff --git a/drivers/scsi/aacraid/commctrl.c b/drivers/scsi/aacraid/commctrl.c
index bd82aeb679ae..ac73c7b6d7be 100644
--- a/drivers/scsi/aacraid/commctrl.c
+++ b/drivers/scsi/aacraid/commctrl.c
@@ -1043,6 +1043,7 @@ struct aac_reset_iop {
 };
 
 static int aac_send_reset_adapter(struct aac_dev *dev, void __user *arg)
+	__must_hold(&dev->ioctl_mutex)
 {
 	struct aac_reset_iop reset;
 	int retval;
diff --git a/drivers/scsi/aacraid/commsup.c b/drivers/scsi/aacraid/commsup.c
index 347d480a39b0..0dba4406494a 100644
--- a/drivers/scsi/aacraid/commsup.c
+++ b/drivers/scsi/aacraid/commsup.c
@@ -475,6 +475,7 @@ int aac_queue_get(struct aac_dev * dev, u32 * index, u32 qid, struct hw_fib * hw
 int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
 		int priority, int wait, int reply, fib_callback callback,
 		void *callback_data)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct aac_dev * dev = fibptr->dev;
 	struct hw_fib * hw_fib = fibptr->hw_fib_va;
@@ -698,6 +699,7 @@ int aac_fib_send(u16 command, struct fib *fibptr, unsigned long size,
 
 int aac_hba_send(u8 command, struct fib *fibptr, fib_callback callback,
 		void *callback_data)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct aac_dev *dev = fibptr->dev;
 	int wait;
@@ -1466,6 +1468,7 @@ static void aac_schedule_bus_scan(struct aac_dev *aac)
 }
 
 static int _aac_reset_adapter(struct aac_dev *aac, int forced, u8 reset_type)
+	__context_unsafe(/*conditional locking*/)
 {
 	int index, quirks;
 	int retval;
diff --git a/drivers/scsi/aha152x.c b/drivers/scsi/aha152x.c
index e3ccb6bb62c0..d751dc8093cc 100644
--- a/drivers/scsi/aha152x.c
+++ b/drivers/scsi/aha152x.c
@@ -636,7 +636,7 @@ static struct {
 /* setup & interrupt */
 static irqreturn_t intr(int irq, void *dev_id);
 static void reset_ports(struct Scsi_Host *shpnt);
-static void aha152x_error(struct Scsi_Host *shpnt, char *msg);
+static void __noreturn aha152x_error(struct Scsi_Host *shpnt, char *msg);
 static void done(struct Scsi_Host *shpnt, unsigned char status_byte,
 		 unsigned char host_byte);
 
@@ -2441,7 +2441,7 @@ static void is_complete(struct Scsi_Host *shpnt)
 /*
  * Dump the current driver status and panic
  */
-static void aha152x_error(struct Scsi_Host *shpnt, char *msg)
+static void __noreturn aha152x_error(struct Scsi_Host *shpnt, char *msg)
 {
 	shost_printk(KERN_EMERG, shpnt, "%s\n", msg);
 	show_queues(shpnt);
diff --git a/drivers/scsi/aic7xxx/Makefile b/drivers/scsi/aic7xxx/Makefile
index 853c72a81ae0..2da370d3d904 100644
--- a/drivers/scsi/aic7xxx/Makefile
+++ b/drivers/scsi/aic7xxx/Makefile
@@ -5,6 +5,8 @@
 # $Id: //depot/linux-aic79xx-2.5.0/drivers/scsi/aic7xxx/Makefile#8 $
 #
 
+CONTEXT_ANALYSIS := y
+
 # Let kbuild descend into aicasm when cleaning
 subdir-				+= aicasm
 
diff --git a/drivers/scsi/aic7xxx/aic79xx_osm.h b/drivers/scsi/aic7xxx/aic79xx_osm.h
index 793fe19993a9..c6eb2b97e929 100644
--- a/drivers/scsi/aic7xxx/aic79xx_osm.h
+++ b/drivers/scsi/aic7xxx/aic79xx_osm.h
@@ -376,12 +376,14 @@ ahd_lockinit(struct ahd_softc *ahd)
 
 static inline void
 ahd_lock(struct ahd_softc *ahd, unsigned long *flags)
+	__acquires(&ahd->platform_data->spin_lock)
 {
 	spin_lock_irqsave(&ahd->platform_data->spin_lock, *flags);
 }
 
 static inline void
 ahd_unlock(struct ahd_softc *ahd, unsigned long *flags)
+	__releases(&ahd->platform_data->spin_lock)
 {
 	spin_unlock_irqrestore(&ahd->platform_data->spin_lock, *flags);
 }
diff --git a/drivers/scsi/aic7xxx/aic7xxx_osm.h b/drivers/scsi/aic7xxx/aic7xxx_osm.h
index 51d9f4de0734..5e78fe7d3f32 100644
--- a/drivers/scsi/aic7xxx/aic7xxx_osm.h
+++ b/drivers/scsi/aic7xxx/aic7xxx_osm.h
@@ -389,12 +389,14 @@ ahc_lockinit(struct ahc_softc *ahc)
 
 static inline void
 ahc_lock(struct ahc_softc *ahc, unsigned long *flags)
+	__acquires(&ahc->platform_data->spin_lock)
 {
 	spin_lock_irqsave(&ahc->platform_data->spin_lock, *flags);
 }
 
 static inline void
 ahc_unlock(struct ahc_softc *ahc, unsigned long *flags)
+	__releases(&ahc->platform_data->spin_lock)
 {
 	spin_unlock_irqrestore(&ahc->platform_data->spin_lock, *flags);
 }
diff --git a/drivers/scsi/aic94xx/Makefile b/drivers/scsi/aic94xx/Makefile
index db9fbe3a8e4c..4ab04ce6edf2 100644
--- a/drivers/scsi/aic94xx/Makefile
+++ b/drivers/scsi/aic94xx/Makefile
@@ -6,6 +6,8 @@
 # Copyright (C) 2005 Luben Tuikov <luben_tuikov@adaptec.com>
 #
 
+CONTEXT_ANALYSIS := y
+
 ccflags-$(CONFIG_AIC94XX_DEBUG) := -DASD_DEBUG -DASD_ENTER_EXIT
 
 obj-$(CONFIG_SCSI_AIC94XX) += aic94xx.o
diff --git a/drivers/scsi/arcmsr/Makefile b/drivers/scsi/arcmsr/Makefile
index 9051f66cae36..6c12d36994da 100644
--- a/drivers/scsi/arcmsr/Makefile
+++ b/drivers/scsi/arcmsr/Makefile
@@ -2,6 +2,8 @@
 # File: drivers/arcmsr/Makefile
 # Makefile for the ARECA PCI-X PCI-EXPRESS SATA RAID controllers SCSI driver.
 
+CONTEXT_ANALYSIS := y
+
 arcmsr-objs := arcmsr_attr.o arcmsr_hba.o
 
 obj-$(CONFIG_SCSI_ARCMSR) := arcmsr.o
diff --git a/drivers/scsi/be2iscsi/Makefile b/drivers/scsi/be2iscsi/Makefile
index 910885343a75..73d47c687007 100644
--- a/drivers/scsi/be2iscsi/Makefile
+++ b/drivers/scsi/be2iscsi/Makefile
@@ -4,6 +4,8 @@
 #
 #
 
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_BE2ISCSI) += be2iscsi.o
 
 be2iscsi-y := be_iscsi.o be_main.o be_mgmt.o be_cmds.o
diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c
index fd18d4d3d219..356ab9c0fb7c 100644
--- a/drivers/scsi/be2iscsi/be_main.c
+++ b/drivers/scsi/be2iscsi/be_main.c
@@ -1117,6 +1117,7 @@ static void
 be_complete_io(struct beiscsi_conn *beiscsi_conn,
 		struct iscsi_task *task,
 		struct common_sol_cqe *csol_cqe)
+	__must_hold(&beiscsi_conn->conn->session->back_lock)
 {
 	struct beiscsi_io_task *io_task = task->dd_data;
 	struct be_status_bhs *sts_bhs =
@@ -1178,13 +1179,14 @@ be_complete_io(struct beiscsi_conn *beiscsi_conn,
 		scsi_dma_unmap(io_task->scsi_cmnd);
 		io_task->scsi_cmnd = NULL;
 	}
-	iscsi_complete_scsi_task(task, exp_cmdsn, max_cmdsn);
+	iscsi_complete_scsi_task(conn->session, task, exp_cmdsn, max_cmdsn);
 }
 
 static void
 be_complete_logout(struct beiscsi_conn *beiscsi_conn,
 		    struct iscsi_task *task,
 		    struct common_sol_cqe *csol_cqe)
+	__must_hold(&beiscsi_conn->conn->session->back_lock)
 {
 	struct iscsi_logout_rsp *hdr;
 	struct beiscsi_io_task *io_task = task->dd_data;
@@ -1205,13 +1207,14 @@ be_complete_logout(struct beiscsi_conn *beiscsi_conn,
 	hdr->dlength[2] = 0;
 	hdr->hlength = 0;
 	hdr->itt = io_task->libiscsi_itt;
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0);
+	__iscsi_complete_pdu(conn->session, conn, (struct iscsi_hdr *)hdr, NULL, 0);
 }
 
 static void
 be_complete_tmf(struct beiscsi_conn *beiscsi_conn,
 		 struct iscsi_task *task,
 		 struct common_sol_cqe *csol_cqe)
+	__must_hold(&beiscsi_conn->conn->session->back_lock)
 {
 	struct iscsi_tm_rsp *hdr;
 	struct iscsi_conn *conn = beiscsi_conn->conn;
@@ -1226,7 +1229,7 @@ be_complete_tmf(struct beiscsi_conn *beiscsi_conn,
 				     csol_cqe->cmd_wnd - 1);
 
 	hdr->itt = io_task->libiscsi_itt;
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0);
+	__iscsi_complete_pdu(conn->session, conn, (struct iscsi_hdr *)hdr, NULL, 0);
 }
 
 static void
@@ -1260,7 +1263,7 @@ hwi_complete_drvr_msgs(struct beiscsi_conn *beiscsi_conn,
 	spin_lock_bh(&session->back_lock);
 	task = pwrb_handle->pio_handle;
 	if (task)
-		__iscsi_put_task(task);
+		__iscsi_put_task(session, task);
 	spin_unlock_bh(&session->back_lock);
 }
 
@@ -1268,6 +1271,7 @@ static void
 be_complete_nopin_resp(struct beiscsi_conn *beiscsi_conn,
 			struct iscsi_task *task,
 			struct common_sol_cqe *csol_cqe)
+	__must_hold(&beiscsi_conn->conn->session->back_lock)
 {
 	struct iscsi_nopin *hdr;
 	struct iscsi_conn *conn = beiscsi_conn->conn;
@@ -1281,7 +1285,7 @@ be_complete_nopin_resp(struct beiscsi_conn *beiscsi_conn,
 
 	hdr->opcode = ISCSI_OP_NOOP_IN;
 	hdr->itt = io_task->libiscsi_itt;
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0);
+	__iscsi_complete_pdu(conn->session, conn, (struct iscsi_hdr *)hdr, NULL, 0);
 }
 
 static void adapter_get_sol_cqe(struct beiscsi_hba *phba,
@@ -1423,6 +1427,7 @@ static void hwi_complete_cmd(struct beiscsi_conn *beiscsi_conn,
 static unsigned int
 beiscsi_complete_pdu(struct beiscsi_conn *beiscsi_conn,
 		struct pdu_base *phdr, void *pdata, unsigned int dlen)
+	__must_hold(&beiscsi_conn->conn->session->back_lock)
 {
 	struct beiscsi_hba *phba = beiscsi_conn->phba;
 	struct iscsi_conn *conn = beiscsi_conn->conn;
@@ -1460,7 +1465,8 @@ beiscsi_complete_pdu(struct beiscsi_conn *beiscsi_conn,
 			    code);
 		return 1;
 	}
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)phdr, pdata, dlen);
+	__iscsi_complete_pdu(conn->session, conn, (struct iscsi_hdr *)phdr, pdata,
+			     dlen);
 	return 0;
 }
 
diff --git a/drivers/scsi/bfa/Makefile b/drivers/scsi/bfa/Makefile
index 442fc3db8f1f..50c16fcfb01c 100644
--- a/drivers/scsi/bfa/Makefile
+++ b/drivers/scsi/bfa/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_BFA_FC) := bfa.o
 
 bfa-y := bfad.o bfad_im.o bfad_attr.o bfad_debugfs.o bfad_bsg.o
diff --git a/drivers/scsi/bnx2fc/Makefile b/drivers/scsi/bnx2fc/Makefile
index 1d72e279a97d..3feb6b4dae64 100644
--- a/drivers/scsi/bnx2fc/Makefile
+++ b/drivers/scsi/bnx2fc/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_BNX2X_FCOE) += bnx2fc.o
 
 bnx2fc-y := bnx2fc_els.o bnx2fc_fcoe.o bnx2fc_hwi.o bnx2fc_io.o bnx2fc_tgt.o \
diff --git a/drivers/scsi/bnx2fc/bnx2fc.h b/drivers/scsi/bnx2fc/bnx2fc.h
index 8c8968ec8cb4..2fc80c607437 100644
--- a/drivers/scsi/bnx2fc/bnx2fc.h
+++ b/drivers/scsi/bnx2fc/bnx2fc.h
@@ -423,7 +423,8 @@ struct bnx2fc_cmd {
 	struct scsi_cmnd *sc_cmd;
 	struct bnx2fc_cmd_mgr *cmd_mgr;
 	struct bnx2fc_mp_req mp_req;
-	void (*cb_func)(struct bnx2fc_els_cb_arg *cb_arg);
+	void (*cb_func)(struct bnx2fc_rport *tgt,
+			struct bnx2fc_els_cb_arg *cb_arg);
 	struct bnx2fc_els_cb_arg *cb_arg;
 	struct delayed_work timeout_work; /* timer for ULP timeouts */
 	struct completion abts_done;
@@ -592,9 +593,11 @@ int bnx2fc_send_stat_req(struct bnx2fc_hba *hba);
 int bnx2fc_post_io_req(struct bnx2fc_rport *tgt, struct bnx2fc_cmd *io_req);
 int bnx2fc_send_rec(struct bnx2fc_cmd *orig_io_req);
 int bnx2fc_send_srr(struct bnx2fc_cmd *orig_io_req, u32 offset, u8 r_ctl);
-void bnx2fc_process_seq_cleanup_compl(struct bnx2fc_cmd *seq_clnup_req,
+void bnx2fc_process_seq_cleanup_compl(struct bnx2fc_rport *tgt,
+				      struct bnx2fc_cmd *seq_clnp_req,
 				      struct fcoe_task_ctx_entry *task,
-				      u8 rx_state);
+				      u8 rx_state)
+	__must_hold(&tgt->tgt_lock);
 int bnx2fc_initiate_seq_cleanup(struct bnx2fc_cmd *orig_io_req, u32 offset,
 				enum fc_rctl r_ctl);
 
diff --git a/drivers/scsi/bnx2fc/bnx2fc_els.c b/drivers/scsi/bnx2fc/bnx2fc_els.c
index 749e30aaf926..bca28acaa1a2 100644
--- a/drivers/scsi/bnx2fc/bnx2fc_els.c
+++ b/drivers/scsi/bnx2fc/bnx2fc_els.c
@@ -22,10 +22,12 @@ static void bnx2fc_flogi_resp(struct fc_seq *seq, struct fc_frame *fp,
 			      void *arg);
 static int bnx2fc_initiate_els(struct bnx2fc_rport *tgt, unsigned int op,
 			void *data, u32 data_len,
-			void (*cb_func)(struct bnx2fc_els_cb_arg *cb_arg),
+			void (*cb_func)(struct bnx2fc_rport *tgt,
+					struct bnx2fc_els_cb_arg *cb_arg),
 			struct bnx2fc_els_cb_arg *cb_arg, u32 timer_msec);
 
-static void bnx2fc_rrq_compl(struct bnx2fc_els_cb_arg *cb_arg)
+static void bnx2fc_rrq_compl(struct bnx2fc_rport *tgt,
+			     struct bnx2fc_els_cb_arg *cb_arg)
 {
 	struct bnx2fc_cmd *orig_io_req;
 	struct bnx2fc_cmd *rrq_req;
@@ -119,10 +121,10 @@ int bnx2fc_send_rrq(struct bnx2fc_cmd *aborted_io_req)
 	return rc;
 }
 
-static void bnx2fc_l2_els_compl(struct bnx2fc_els_cb_arg *cb_arg)
+static void bnx2fc_l2_els_compl(struct bnx2fc_rport *tgt,
+				struct bnx2fc_els_cb_arg *cb_arg)
 {
 	struct bnx2fc_cmd *els_req;
-	struct bnx2fc_rport *tgt;
 	struct bnx2fc_mp_req *mp_req;
 	struct fc_frame_header *fc_hdr;
 	unsigned char *buf;
@@ -150,7 +152,6 @@ static void bnx2fc_l2_els_compl(struct bnx2fc_els_cb_arg *cb_arg)
 		goto free_arg;
 	}
 
-	tgt = els_req->tgt;
 	mp_req = &(els_req->mp_req);
 	fc_hdr = &(mp_req->resp_fc_hdr);
 	resp_len = mp_req->resp_len;
@@ -262,7 +263,9 @@ int bnx2fc_send_rls(struct bnx2fc_rport *tgt, struct fc_frame *fp)
 	return rc;
 }
 
-static void bnx2fc_srr_compl(struct bnx2fc_els_cb_arg *cb_arg)
+static void bnx2fc_srr_compl(struct bnx2fc_rport *tgt,
+			     struct bnx2fc_els_cb_arg *cb_arg)
+	__must_hold(&tgt->tgt_lock)
 {
 	struct bnx2fc_mp_req *mp_req;
 	struct fc_frame_header *fc_hdr, *fh;
@@ -296,7 +299,6 @@ static void bnx2fc_srr_compl(struct bnx2fc_els_cb_arg *cb_arg)
 		}
 		orig_io_req->srr_retry++;
 		if (orig_io_req->srr_retry <= SRR_RETRY_COUNT) {
-			struct bnx2fc_rport *tgt = orig_io_req->tgt;
 			spin_unlock_bh(&tgt->tgt_lock);
 			rc = bnx2fc_send_srr(orig_io_req,
 					     orig_io_req->srr_offset,
@@ -372,7 +374,9 @@ static void bnx2fc_srr_compl(struct bnx2fc_els_cb_arg *cb_arg)
 	kref_put(&orig_io_req->refcount, bnx2fc_cmd_release);
 }
 
-static void bnx2fc_rec_compl(struct bnx2fc_els_cb_arg *cb_arg)
+static void bnx2fc_rec_compl(struct bnx2fc_rport *tgt,
+			     struct bnx2fc_els_cb_arg *cb_arg)
+	__must_hold(&tgt->tgt_lock)
 {
 	struct bnx2fc_cmd *orig_io_req, *new_io_req;
 	struct bnx2fc_cmd *rec_req;
@@ -380,7 +384,6 @@ static void bnx2fc_rec_compl(struct bnx2fc_els_cb_arg *cb_arg)
 	struct fc_frame_header *fc_hdr, *fh;
 	struct fc_els_ls_rjt *rjt;
 	struct fc_els_rec_acc *acc;
-	struct bnx2fc_rport *tgt;
 	struct fcoe_err_report_entry *err_entry;
 	struct scsi_cmnd *sc_cmd;
 	enum fc_rctl r_ctl;
@@ -399,7 +402,6 @@ static void bnx2fc_rec_compl(struct bnx2fc_els_cb_arg *cb_arg)
 	rec_req = cb_arg->io_req;
 	orig_io_req = cb_arg->aborted_io_req;
 	BNX2FC_IO_DBG(rec_req, "rec_compl: orig xid = 0x%x", orig_io_req->xid);
-	tgt = orig_io_req->tgt;
 
 	/* Handle REC timeout case */
 	if (test_and_clear_bit(BNX2FC_FLAG_ELS_TIMEOUT, &rec_req->req_flags)) {
@@ -669,7 +671,8 @@ int bnx2fc_send_srr(struct bnx2fc_cmd *orig_io_req, u32 offset, u8 r_ctl)
 
 static int bnx2fc_initiate_els(struct bnx2fc_rport *tgt, unsigned int op,
 			void *data, u32 data_len,
-			void (*cb_func)(struct bnx2fc_els_cb_arg *cb_arg),
+			void (*cb_func)(struct bnx2fc_rport *tgt,
+					struct bnx2fc_els_cb_arg *cb_arg),
 			struct bnx2fc_els_cb_arg *cb_arg, u32 timer_msec)
 {
 	struct fcoe_port *port = tgt->port;
@@ -847,7 +850,7 @@ void bnx2fc_process_els_compl(struct bnx2fc_cmd *els_req,
 
 	/* Parse ELS response */
 	if ((els_req->cb_func) && (els_req->cb_arg)) {
-		els_req->cb_func(els_req->cb_arg);
+		els_req->cb_func(els_req->tgt, els_req->cb_arg);
 		els_req->cb_arg = NULL;
 	}
 
diff --git a/drivers/scsi/bnx2fc/bnx2fc_hwi.c b/drivers/scsi/bnx2fc/bnx2fc_hwi.c
index a5ecb87d5b2d..833ec0e35731 100644
--- a/drivers/scsi/bnx2fc/bnx2fc_hwi.c
+++ b/drivers/scsi/bnx2fc/bnx2fc_hwi.c
@@ -943,7 +943,7 @@ void bnx2fc_process_cq_compl(struct bnx2fc_rport *tgt, u16 wqe,
 	case BNX2FC_SEQ_CLEANUP:
 		BNX2FC_IO_DBG(io_req, "cq_compl(0x%x) - seq cleanup resp\n",
 			      io_req->xid);
-		bnx2fc_process_seq_cleanup_compl(io_req, task, rx_state);
+		bnx2fc_process_seq_cleanup_compl(tgt, io_req, task, rx_state);
 		kref_put(&io_req->refcount, bnx2fc_cmd_release);
 		break;
 
diff --git a/drivers/scsi/bnx2fc/bnx2fc_io.c b/drivers/scsi/bnx2fc/bnx2fc_io.c
index 9c7a541a4523..60346d77cb6d 100644
--- a/drivers/scsi/bnx2fc/bnx2fc_io.c
+++ b/drivers/scsi/bnx2fc/bnx2fc_io.c
@@ -142,7 +142,7 @@ static void bnx2fc_cmd_timeout(struct work_struct *work)
 			set_bit(BNX2FC_FLAG_ELS_TIMEOUT, &io_req->req_flags);
 
 			if ((io_req->cb_func) && (io_req->cb_arg)) {
-				io_req->cb_func(io_req->cb_arg);
+				io_req->cb_func(tgt, io_req->cb_arg);
 				io_req->cb_arg = NULL;
 			}
 		}
@@ -1079,10 +1079,10 @@ int bnx2fc_eh_device_reset(struct scsi_cmnd *sc_cmd)
 				   FCP_TMF_LUN_RESET);
 }
 
-static int bnx2fc_abts_cleanup(struct bnx2fc_cmd *io_req)
+static int bnx2fc_abts_cleanup(struct bnx2fc_rport *tgt,
+			       struct bnx2fc_cmd *io_req)
 	__must_hold(&tgt->tgt_lock)
 {
-	struct bnx2fc_rport *tgt = io_req->tgt;
 	unsigned int time_left;
 
 	init_completion(&io_req->cleanup_done);
@@ -1212,7 +1212,7 @@ int bnx2fc_eh_abort(struct scsi_cmnd *sc_cmd)
 		 * cleanup the command and return that I/O was successfully
 		 * aborted.
 		 */
-		bnx2fc_abts_cleanup(io_req);
+		bnx2fc_abts_cleanup(tgt, io_req);
 		/* This only occurs when an task abort was requested while ABTS
 		   is in progress.  Setting the IO_CLEANUP flag will skip the
 		   RRQ process in the case when the fw generated SCSI_CMD cmpl
@@ -1262,7 +1262,7 @@ int bnx2fc_eh_abort(struct scsi_cmnd *sc_cmd)
 		 * Cleanup firmware residuals before returning control back
 		 * to SCSI ML.
 		 */
-		rc = bnx2fc_abts_cleanup(io_req);
+		rc = bnx2fc_abts_cleanup(tgt, io_req);
 		goto done;
 	} else {
 		/*
@@ -1282,16 +1282,17 @@ int bnx2fc_eh_abort(struct scsi_cmnd *sc_cmd)
 	return rc;
 }
 
-void bnx2fc_process_seq_cleanup_compl(struct bnx2fc_cmd *seq_clnp_req,
+void bnx2fc_process_seq_cleanup_compl(struct bnx2fc_rport *tgt,
+				      struct bnx2fc_cmd *seq_clnp_req,
 				      struct fcoe_task_ctx_entry *task,
 				      u8 rx_state)
+	__must_hold(&tgt->tgt_lock)
 {
 	struct bnx2fc_els_cb_arg *cb_arg = seq_clnp_req->cb_arg;
 	struct bnx2fc_cmd *orig_io_req = cb_arg->aborted_io_req;
 	u32 offset = cb_arg->offset;
 	enum fc_rctl r_ctl = cb_arg->r_ctl;
 	int rc = 0;
-	struct bnx2fc_rport *tgt = orig_io_req->tgt;
 
 	BNX2FC_IO_DBG(orig_io_req, "Entered process_cleanup_compl xid = 0x%x"
 			      "cmd_type = %d\n",
diff --git a/drivers/scsi/bnx2fc/bnx2fc_tgt.c b/drivers/scsi/bnx2fc/bnx2fc_tgt.c
index 77dcdfc412b1..e6942cb6cae6 100644
--- a/drivers/scsi/bnx2fc/bnx2fc_tgt.c
+++ b/drivers/scsi/bnx2fc/bnx2fc_tgt.c
@@ -224,7 +224,7 @@ void bnx2fc_flush_active_ios(struct bnx2fc_rport *tgt)
 				 bnx2fc_cmd_release); /* drop timer hold */
 
 		if ((io_req->cb_func) && (io_req->cb_arg)) {
-			io_req->cb_func(io_req->cb_arg);
+			io_req->cb_func(tgt, io_req->cb_arg);
 			io_req->cb_arg = NULL;
 		}
 
diff --git a/drivers/scsi/bnx2i/Makefile b/drivers/scsi/bnx2i/Makefile
index 25378671bb1e..2d8e8f0fdd29 100644
--- a/drivers/scsi/bnx2i/Makefile
+++ b/drivers/scsi/bnx2i/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 bnx2i-y := bnx2i_init.o bnx2i_hwi.o bnx2i_iscsi.o bnx2i_sysfs.o
 
 obj-$(CONFIG_SCSI_BNX2_ISCSI) += bnx2i.o
diff --git a/drivers/scsi/bnx2i/bnx2i_hwi.c b/drivers/scsi/bnx2i/bnx2i_hwi.c
index d24cc2c795d6..c22f1c981d02 100644
--- a/drivers/scsi/bnx2i/bnx2i_hwi.c
+++ b/drivers/scsi/bnx2i/bnx2i_hwi.c
@@ -383,6 +383,7 @@ int bnx2i_send_iscsi_tmf(struct bnx2i_conn *bnx2i_conn,
 			 struct iscsi_task *mtask)
 {
 	struct iscsi_conn *conn = bnx2i_conn->cls_conn->dd_data;
+	struct iscsi_session *session = conn->session;
 	struct iscsi_tm *tmfabort_hdr;
 	struct scsi_cmnd *ref_sc;
 	struct iscsi_task *ctask;
@@ -404,7 +405,12 @@ int bnx2i_send_iscsi_tmf(struct bnx2i_conn *bnx2i_conn,
 	switch (tmfabort_hdr->flags & ISCSI_FLAG_TM_FUNC_MASK) {
 	case ISCSI_TM_FUNC_ABORT_TASK:
 	case ISCSI_TM_FUNC_TASK_REASSIGN:
-		ctask = iscsi_itt_to_task(conn, tmfabort_hdr->rtt);
+		/*
+		 * TODO: hold session->back_lock around the iscsi_itt_to_task()
+		 * call below.
+		 */
+		__assume_ctx_lock(&session->back_lock);
+		ctask = iscsi_itt_to_task(session, conn, tmfabort_hdr->rtt);
 		if (!ctask || !ctask->sc)
 			/*
 			 * the iscsi layer must have completed the cmd while
@@ -1347,7 +1353,7 @@ int bnx2i_process_scsi_cmd_resp(struct iscsi_session *session,
 
 	resp_cqe = (struct bnx2i_cmd_response *)cqe;
 	spin_lock_bh(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 				 resp_cqe->itt & ISCSI_CMD_RESPONSE_INDEX);
 	if (!task)
 		goto fail;
@@ -1414,7 +1420,7 @@ int bnx2i_process_scsi_cmd_resp(struct iscsi_session *session,
 	}
 
 done:
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr,
 			     conn->data, datalen);
 fail:
 	spin_unlock_bh(&session->back_lock);
@@ -1443,7 +1449,7 @@ static int bnx2i_process_login_resp(struct iscsi_session *session,
 
 	login = (struct bnx2i_login_response *) cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 				 login->itt & ISCSI_LOGIN_RESPONSE_INDEX);
 	if (!task)
 		goto done;
@@ -1481,7 +1487,7 @@ static int bnx2i_process_login_resp(struct iscsi_session *session,
 		}
 	}
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr,
 		bnx2i_conn->gen_pdu.resp_buf,
 		bnx2i_conn->gen_pdu.resp_wr_ptr - bnx2i_conn->gen_pdu.resp_buf);
 done:
@@ -1511,7 +1517,8 @@ static int bnx2i_process_text_resp(struct iscsi_session *session,
 
 	text = (struct bnx2i_text_response *) cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn, text->itt & ISCSI_LOGIN_RESPONSE_INDEX);
+	task = iscsi_itt_to_task(session, conn,
+				 text->itt & ISCSI_LOGIN_RESPONSE_INDEX);
 	if (!task)
 		goto done;
 
@@ -1541,7 +1548,7 @@ static int bnx2i_process_text_resp(struct iscsi_session *session,
 			bnx2i_conn->gen_pdu.resp_wr_ptr++;
 		}
 	}
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr,
 			     bnx2i_conn->gen_pdu.resp_buf,
 			     bnx2i_conn->gen_pdu.resp_wr_ptr -
 			     bnx2i_conn->gen_pdu.resp_buf);
@@ -1570,7 +1577,7 @@ static int bnx2i_process_tmf_resp(struct iscsi_session *session,
 
 	tmf_cqe = (struct bnx2i_tmf_response *)cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 				 tmf_cqe->itt & ISCSI_TMF_RESPONSE_INDEX);
 	if (!task)
 		goto done;
@@ -1583,7 +1590,7 @@ static int bnx2i_process_tmf_resp(struct iscsi_session *session,
 	resp_hdr->itt = task->hdr->itt;
 	resp_hdr->response = tmf_cqe->response;
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
 done:
 	spin_unlock(&session->back_lock);
 	return 0;
@@ -1609,7 +1616,7 @@ static int bnx2i_process_logout_resp(struct iscsi_session *session,
 
 	logout = (struct bnx2i_logout_response *) cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 				 logout->itt & ISCSI_LOGOUT_RESPONSE_INDEX);
 	if (!task)
 		goto done;
@@ -1628,7 +1635,7 @@ static int bnx2i_process_logout_resp(struct iscsi_session *session,
 	resp_hdr->t2wait = cpu_to_be32(logout->time_to_wait);
 	resp_hdr->t2retain = cpu_to_be32(logout->time_to_retain);
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
 
 	bnx2i_conn->ep->state = EP_STATE_LOGOUT_RESP_RCVD;
 done:
@@ -1654,10 +1661,10 @@ static void bnx2i_process_nopin_local_cmpl(struct iscsi_session *session,
 
 	nop_in = (struct bnx2i_nop_in_msg *)cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 				 nop_in->itt & ISCSI_NOP_IN_MSG_INDEX);
 	if (task)
-		__iscsi_put_task(task);
+		__iscsi_put_task(session, task);
 	spin_unlock(&session->back_lock);
 }
 
@@ -1713,7 +1720,7 @@ static int bnx2i_process_nopin_mesg(struct iscsi_session *session,
 	}
 
 	/* this is a response to one of our nop-outs */
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 			 (itt_t) (nop_in->itt & ISCSI_NOP_IN_MSG_INDEX));
 	if (task) {
 		hdr->flags = ISCSI_FLAG_CMD_FINAL;
@@ -1722,7 +1729,7 @@ static int bnx2i_process_nopin_mesg(struct iscsi_session *session,
 		memcpy(&hdr->lun, nop_in->lun, 8);
 	}
 done:
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr, NULL, 0);
 	spin_unlock(&session->back_lock);
 
 	return tgt_async_nop;
@@ -1773,7 +1780,7 @@ static void bnx2i_process_async_mesg(struct iscsi_session *session,
 	resp_hdr->param2 = cpu_to_be16(async_cqe->param2);
 	resp_hdr->param3 = cpu_to_be16(async_cqe->param3);
 
-	__iscsi_complete_pdu(bnx2i_conn->cls_conn->dd_data,
+	__iscsi_complete_pdu(session, bnx2i_conn->cls_conn->dd_data,
 			     (struct iscsi_hdr *)resp_hdr, NULL, 0);
 	spin_unlock(&session->back_lock);
 }
@@ -1811,7 +1818,7 @@ static void bnx2i_process_reject_mesg(struct iscsi_session *session,
 	hdr->max_cmdsn = cpu_to_be32(reject->max_cmd_sn);
 	hdr->exp_cmdsn = cpu_to_be32(reject->exp_cmd_sn);
 	hdr->ffffffff = cpu_to_be32(RESERVED_ITT);
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, conn->data,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr, conn->data,
 			     reject->data_length);
 	spin_unlock(&session->back_lock);
 }
@@ -1834,7 +1841,7 @@ static void bnx2i_process_cmd_cleanup_resp(struct iscsi_session *session,
 
 	cmd_clean_rsp = (struct bnx2i_cleanup_response *)cqe;
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(conn,
+	task = iscsi_itt_to_task(session, conn,
 			cmd_clean_rsp->itt & ISCSI_CLEANUP_RESPONSE_INDEX);
 	if (!task)
 		printk(KERN_ALERT "bnx2i: cmd clean ITT %x not active\n",
@@ -1908,7 +1915,7 @@ static int bnx2i_queue_scsi_cmd_resp(struct iscsi_session *session,
 	int rc = 0;
 
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_task(bnx2i_conn->cls_conn->dd_data,
+	task = iscsi_itt_to_task(session, bnx2i_conn->cls_conn->dd_data,
 				 cqe->itt & ISCSI_CMD_RESPONSE_INDEX);
 	if (!task || !task->sc) {
 		spin_unlock(&session->back_lock);
diff --git a/drivers/scsi/bnx2i/bnx2i_iscsi.c b/drivers/scsi/bnx2i/bnx2i_iscsi.c
index 6c80e5b514fd..c868eada72c3 100644
--- a/drivers/scsi/bnx2i/bnx2i_iscsi.c
+++ b/drivers/scsi/bnx2i/bnx2i_iscsi.c
@@ -1154,6 +1154,7 @@ static void bnx2i_cpy_scsi_cdb(struct scsi_cmnd *sc, struct bnx2i_cmd *cmd)
 }
 
 static void bnx2i_cleanup_task(struct iscsi_task *task)
+	__must_hold(&task->conn->session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
 	struct bnx2i_conn *bnx2i_conn = conn->dd_data;
diff --git a/drivers/scsi/ch.c b/drivers/scsi/ch.c
index 87e51e50a741..b2c9fb71c9e0 100644
--- a/drivers/scsi/ch.c
+++ b/drivers/scsi/ch.c
@@ -112,7 +112,6 @@ typedef struct {
 	int                 minor;
 	char                name[8];
 	struct scsi_device  *device;
-	struct scsi_device  **dt;        /* ptrs to data transfer elements */
 	u_int               firsts[CH_TYPES];
 	u_int               counts[CH_TYPES];
 	u_int		    voltags;
@@ -354,15 +353,10 @@ ch_readconfig(scsi_changer *ch)
 			vendor_labels[i]);
 	}
 
-	/* look up the devices of the data transfer elements */
-	ch->dt = kzalloc_objs(*ch->dt, ch->counts[CHET_DT]);
-
-	if (!ch->dt) {
-		kfree(buffer);
-		return -ENOMEM;
-	}
-
+	/* report the devices of the data transfer elements */
 	for (elem = 0; elem < ch->counts[CHET_DT]; elem++) {
+		struct scsi_device *sdev;
+
 		id  = -1;
 		lun = 0;
 		if (elem < CH_DT_MAX  &&  -1 != dt_id[elem]) {
@@ -378,10 +372,8 @@ ch_readconfig(scsi_changer *ch)
 			VPRINTK(KERN_INFO, "dt 0x%x: ",elem+ch->firsts[CHET_DT]);
 			if (data[6] & 0x80) {
 				VPRINTK(KERN_CONT, "not this SCSI bus\n");
-				ch->dt[elem] = NULL;
 			} else if (0 == (data[6] & 0x30)) {
 				VPRINTK(KERN_CONT, "ID/LUN unknown\n");
-				ch->dt[elem] = NULL;
 			} else {
 				id  = ch->device->id;
 				lun = 0;
@@ -391,18 +383,16 @@ ch_readconfig(scsi_changer *ch)
 		}
 		if (-1 != id) {
 			VPRINTK(KERN_CONT, "ID %i, LUN %i, ",id,lun);
-			ch->dt[elem] =
-				scsi_device_lookup(ch->device->host,
-						   ch->device->channel,
-						   id,lun);
-			if (!ch->dt[elem]) {
+			sdev = scsi_device_lookup(ch->device->host,
+						  ch->device->channel,
+						  id, lun);
+			if (!sdev) {
 				/* should not happen */
 				VPRINTK(KERN_CONT, "Huh? device not found!\n");
 			} else {
 				VPRINTK(KERN_CONT, "name: %8.8s %16.16s %4.4s\n",
-					ch->dt[elem]->vendor,
-					ch->dt[elem]->model,
-					ch->dt[elem]->rev);
+					sdev->vendor, sdev->model, sdev->rev);
+				scsi_device_put(sdev);
 			}
 		}
 	}
@@ -566,7 +556,6 @@ static void ch_destroy(struct kref *ref)
 	scsi_changer *ch = container_of(ref, scsi_changer, ref);
 
 	ch->device = NULL;
-	kfree(ch->dt);
 	kfree(ch);
 }
 
diff --git a/drivers/scsi/csiostor/Makefile b/drivers/scsi/csiostor/Makefile
index d047e22eac0d..a19031efa7c4 100644
--- a/drivers/scsi/csiostor/Makefile
+++ b/drivers/scsi/csiostor/Makefile
@@ -4,6 +4,8 @@
 #
 ##
 
+CONTEXT_ANALYSIS := y
+
 ccflags-y += -I$(srctree)/drivers/net/ethernet/chelsio/cxgb4
 
 obj-$(CONFIG_SCSI_CHELSIO_FCOE) += csiostor.o
diff --git a/drivers/scsi/csiostor/csio_attr.c b/drivers/scsi/csiostor/csio_attr.c
index 9f021a7f78bd..7fddb98e1024 100644
--- a/drivers/scsi/csiostor/csio_attr.c
+++ b/drivers/scsi/csiostor/csio_attr.c
@@ -630,7 +630,7 @@ csio_vport_delete(struct fc_vport *fc_vport)
 	/* Quiesce ios and send remove event to lnode */
 	scsi_block_requests(shost);
 	spin_lock_irq(&hw->lock);
-	csio_scsim_cleanup_io_lnode(csio_hw_to_scsim(hw), ln);
+	csio_scsim_cleanup_io_lnode(hw, ln);
 	csio_lnode_close(ln);
 	spin_unlock_irq(&hw->lock);
 	scsi_unblock_requests(shost);
@@ -655,7 +655,7 @@ csio_vport_disable(struct fc_vport *fc_vport, bool disable)
 		/* Quiesce ios and send stop event to lnode */
 		scsi_block_requests(shost);
 		spin_lock_irq(&hw->lock);
-		csio_scsim_cleanup_io_lnode(csio_hw_to_scsim(hw), ln);
+		csio_scsim_cleanup_io_lnode(hw, ln);
 		csio_lnode_stop(ln);
 		spin_unlock_irq(&hw->lock);
 		scsi_unblock_requests(shost);
diff --git a/drivers/scsi/csiostor/csio_hw.c b/drivers/scsi/csiostor/csio_hw.c
index df9f81f29950..b5a36615a22b 100644
--- a/drivers/scsi/csiostor/csio_hw.c
+++ b/drivers/scsi/csiostor/csio_hw.c
@@ -92,7 +92,8 @@ static void csio_hw_mbm_cleanup(struct csio_hw *);
 static void csio_hws_uninit(struct csio_hw *, enum csio_hw_ev);
 static void csio_hws_configuring(struct csio_hw *, enum csio_hw_ev);
 static void csio_hws_initializing(struct csio_hw *, enum csio_hw_ev);
-static void csio_hws_ready(struct csio_hw *, enum csio_hw_ev);
+static void csio_hws_ready(struct csio_hw *hw, enum csio_hw_ev)
+	__must_hold(&hw->lock);
 static void csio_hws_quiescing(struct csio_hw *, enum csio_hw_ev);
 static void csio_hws_quiesced(struct csio_hw *, enum csio_hw_ev);
 static void csio_hws_resetting(struct csio_hw *, enum csio_hw_ev);
@@ -914,6 +915,7 @@ csio_hw_dev_ready(struct csio_hw *hw)
  */
 static int
 csio_do_hello(struct csio_hw *hw, enum csio_dev_state *state)
+	__must_hold(&hw->lock)
 {
 	struct csio_mb	*mbp;
 	int	rv = 0;
@@ -2050,6 +2052,7 @@ csio_hw_flash_config(struct csio_hw *hw, u32 *fw_cfg_param, char *path)
  */
 static int
 csio_hw_use_fwconfig(struct csio_hw *hw, int reset, u32 *fw_cfg_param)
+	__must_hold(&hw->lock)
 {
 	struct csio_mb	*mbp = NULL;
 	struct fw_caps_config_cmd *caps_cmd;
@@ -2475,6 +2478,7 @@ static int csio_hw_check_fwver(struct csio_hw *hw)
  */
 static void
 csio_hw_configure(struct csio_hw *hw)
+	__must_hold(&hw->lock)
 {
 	int reset = 1;
 	int rv;
@@ -2604,6 +2608,7 @@ csio_hw_configure(struct csio_hw *hw)
  */
 static void
 csio_hw_initialize(struct csio_hw *hw)
+	__must_hold(&hw->lock)
 {
 	struct csio_mb	*mbp;
 	enum fw_retval retval;
@@ -2778,6 +2783,7 @@ csio_hw_fatal_err(struct csio_hw *hw)
  */
 static void
 csio_hws_uninit(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	hw->prev_evt = hw->cur_evt;
 	hw->cur_evt = evt;
@@ -2803,6 +2809,7 @@ csio_hws_uninit(struct csio_hw *hw, enum csio_hw_ev evt)
  */
 static void
 csio_hws_configuring(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	hw->prev_evt = hw->cur_evt;
 	hw->cur_evt = evt;
@@ -2879,6 +2886,7 @@ csio_hws_initializing(struct csio_hw *hw, enum csio_hw_ev evt)
  */
 static void
 csio_hws_ready(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	/* Remember the event */
 	hw->evtflag = evt;
@@ -2897,9 +2905,9 @@ csio_hws_ready(struct csio_hw *hw, enum csio_hw_ev evt)
 		/* cleanup all outstanding cmds */
 		if (evt == CSIO_HWE_HBA_RESET ||
 		    evt == CSIO_HWE_PCIERR_DETECTED)
-			csio_scsim_cleanup_io(csio_hw_to_scsim(hw), false);
+			csio_scsim_cleanup_io(hw, false);
 		else
-			csio_scsim_cleanup_io(csio_hw_to_scsim(hw), true);
+			csio_scsim_cleanup_io(hw, true);
 
 		csio_hw_intr_disable(hw);
 		csio_hw_mbm_cleanup(hw);
@@ -2988,6 +2996,7 @@ csio_hws_quiescing(struct csio_hw *hw, enum csio_hw_ev evt)
  */
 static void
 csio_hws_quiesced(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	hw->prev_evt = hw->cur_evt;
 	hw->cur_evt = evt;
@@ -3013,6 +3022,7 @@ csio_hws_quiesced(struct csio_hw *hw, enum csio_hw_ev evt)
  */
 static void
 csio_hws_resetting(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	hw->prev_evt = hw->cur_evt;
 	hw->cur_evt = evt;
@@ -3074,6 +3084,7 @@ csio_hws_removing(struct csio_hw *hw, enum csio_hw_ev evt)
  */
 static void
 csio_hws_pcierr(struct csio_hw *hw, enum csio_hw_ev evt)
+	__must_hold(&hw->lock)
 {
 	hw->prev_evt = hw->cur_evt;
 	hw->cur_evt = evt;
@@ -3763,6 +3774,7 @@ csio_hw_mb_timer(struct timer_list *t)
  */
 static void
 csio_hw_mbm_cleanup(struct csio_hw *hw)
+	__must_hold(&hw->lock)
 {
 	LIST_HEAD(cbfn_q);
 
@@ -3883,6 +3895,7 @@ csio_free_evt(struct csio_hw *hw, struct csio_evt_msg *evt_entry)
 
 void
 csio_evtq_flush(struct csio_hw *hw)
+	__must_hold(&hw->lock)
 {
 	uint32_t count;
 	count = 30;
@@ -4142,6 +4155,7 @@ csio_mgmt_tmo_handler(struct timer_list *t)
 
 static void
 csio_mgmtm_cleanup(struct csio_mgmtm *mgmtm)
+	__must_hold(&mgmtm->hw->lock)
 {
 	struct csio_hw *hw = mgmtm->hw;
 	struct csio_ioreq *io_req;
diff --git a/drivers/scsi/csiostor/csio_lnode.c b/drivers/scsi/csiostor/csio_lnode.c
index 78d5ecd14f65..161973957976 100644
--- a/drivers/scsi/csiostor/csio_lnode.c
+++ b/drivers/scsi/csiostor/csio_lnode.c
@@ -872,6 +872,7 @@ csio_ln_read_fcf_entry(struct csio_lnode *ln,
 static void
 csio_handle_link_up(struct csio_hw *hw, uint8_t portid, uint32_t fcfi,
 		    uint32_t vnpi)
+	__must_hold(&hw->lock)
 {
 	struct csio_lnode *ln = NULL;
 
@@ -1165,6 +1166,7 @@ csio_lns_uninit(struct csio_lnode *ln, enum csio_ln_ev evt)
  */
 static void
 csio_lns_online(struct csio_lnode *ln, enum csio_ln_ev evt)
+	__must_hold(&csio_lnode_to_hw(ln)->lock)
 {
 	struct csio_hw *hw = csio_lnode_to_hw(ln);
 
@@ -1216,6 +1218,7 @@ csio_lns_online(struct csio_lnode *ln, enum csio_ln_ev evt)
  */
 static void
 csio_lns_ready(struct csio_lnode *ln, enum csio_ln_ev evt)
+	__must_hold(&csio_lnode_to_hw(ln)->lock)
 {
 	struct csio_hw *hw = csio_lnode_to_hw(ln);
 
diff --git a/drivers/scsi/csiostor/csio_rnode.c b/drivers/scsi/csiostor/csio_rnode.c
index 713e13adf4dc..fe985836c15c 100644
--- a/drivers/scsi/csiostor/csio_rnode.c
+++ b/drivers/scsi/csiostor/csio_rnode.c
@@ -546,6 +546,7 @@ csio_rn_verify_rparams(struct csio_lnode *ln, struct csio_rnode *rn,
 
 static void
 __csio_reg_rnode(struct csio_rnode *rn)
+	__must_hold(&csio_lnode_to_hw(csio_rnode_to_lnode(rn))->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	struct csio_hw *hw = csio_lnode_to_hw(ln);
@@ -563,6 +564,7 @@ __csio_reg_rnode(struct csio_rnode *rn)
 
 static void
 __csio_unreg_rnode(struct csio_rnode *rn)
+	__must_hold(&csio_lnode_to_hw(csio_rnode_to_lnode(rn))->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	struct csio_hw *hw = csio_lnode_to_hw(ln);
@@ -586,8 +588,7 @@ __csio_unreg_rnode(struct csio_rnode *rn)
 
 	/* Cleanup I/Os that were waiting for rnode to unregister */
 	if (cmpl)
-		csio_scsi_cleanup_io_q(csio_hw_to_scsim(hw), &tmp_q);
-
+		csio_scsi_cleanup_io_q(hw, &tmp_q);
 }
 
 /*****************************************************************************/
@@ -602,6 +603,7 @@ __csio_unreg_rnode(struct csio_rnode *rn)
  */
 static void
 csio_rns_uninit(struct csio_rnode *rn, enum csio_rn_ev evt)
+	__must_hold(&csio_rnode_to_lnode(rn)->hwp->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	int ret = 0;
@@ -642,6 +644,7 @@ csio_rns_uninit(struct csio_rnode *rn, enum csio_rn_ev evt)
  */
 static void
 csio_rns_ready(struct csio_rnode *rn, enum csio_rn_ev evt)
+	__must_hold(&csio_rnode_to_lnode(rn)->hwp->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	int ret = 0;
@@ -727,6 +730,7 @@ csio_rns_ready(struct csio_rnode *rn, enum csio_rn_ev evt)
  */
 static void
 csio_rns_offline(struct csio_rnode *rn, enum csio_rn_ev evt)
+	__must_hold(&csio_rnode_to_lnode(rn)->hwp->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	int ret = 0;
@@ -786,6 +790,7 @@ csio_rns_offline(struct csio_rnode *rn, enum csio_rn_ev evt)
  */
 static void
 csio_rns_disappeared(struct csio_rnode *rn, enum csio_rn_ev evt)
+	__must_hold(&csio_rnode_to_lnode(rn)->hwp->lock)
 {
 	struct csio_lnode *ln = csio_rnode_to_lnode(rn);
 	int ret = 0;
diff --git a/drivers/scsi/csiostor/csio_scsi.c b/drivers/scsi/csiostor/csio_scsi.c
index 0114e70e9884..d81d10603fcc 100644
--- a/drivers/scsi/csiostor/csio_scsi.c
+++ b/drivers/scsi/csiostor/csio_scsi.c
@@ -1150,15 +1150,15 @@ csio_scsi_cmpl_handler(struct csio_hw *hw, void *wr, uint32_t len,
 
 /*
  * csio_scsi_cleanup_io_q - Cleanup the given queue.
- * @scm: SCSI module.
+ * @hw: HW module.
  * @q: Queue to be cleaned up.
  *
  * Called with lock held. Has to exit with lock held.
  */
-void
-csio_scsi_cleanup_io_q(struct csio_scsim *scm, struct list_head *q)
+void csio_scsi_cleanup_io_q(struct csio_hw *hw, struct list_head *q)
+	__must_hold(&hw->lock)
 {
-	struct csio_hw *hw = scm->hw;
+	struct csio_scsim *scm = csio_hw_to_scsim(hw);
 	struct csio_ioreq *ioreq;
 	struct list_head *tmp, *next;
 	struct scsi_cmnd *scmnd;
@@ -1215,7 +1215,7 @@ csio_abrt_cls(struct csio_ioreq *ioreq, struct scsi_cmnd *scmnd)
 
 /*
  * csio_scsi_abort_io_q - Abort all I/Os on given queue
- * @scm: SCSI module.
+ * @hw: HW module.
  * @q: Queue to abort.
  * @tmo: Timeout in ms
  *
@@ -1229,10 +1229,10 @@ csio_abrt_cls(struct csio_ioreq *ioreq, struct scsi_cmnd *scmnd)
  * of this function has to ensure that the number of I/os to be aborted
  * is finite enough to not cause lock-held-for-too-long issues.
  */
-static int
-csio_scsi_abort_io_q(struct csio_scsim *scm, struct list_head *q, uint32_t tmo)
+static int csio_scsi_abort_io_q(struct csio_hw *hw, struct list_head *q,
+				uint32_t tmo)
+	__must_hold(&hw->lock)
 {
-	struct csio_hw *hw = scm->hw;
 	struct list_head *tmp, *next;
 	int count = DIV_ROUND_UP(tmo, CSIO_SCSI_ABORT_Q_POLL_MS);
 	struct scsi_cmnd *scmnd;
@@ -1264,15 +1264,15 @@ csio_scsi_abort_io_q(struct csio_scsim *scm, struct list_head *q, uint32_t tmo)
 
 /*
  * csio_scsim_cleanup_io - Cleanup all I/Os in SCSI module.
- * @scm: SCSI module.
+ * @hw: HW module.
  * @abort: abort required.
  * Called with lock held, should exit with lock held.
  * Can sleep when waiting for I/Os to complete.
  */
-int
-csio_scsim_cleanup_io(struct csio_scsim *scm, bool abort)
+int csio_scsim_cleanup_io(struct csio_hw *hw, bool abort)
+	__must_hold(&hw->lock)
 {
-	struct csio_hw *hw = scm->hw;
+	struct csio_scsim *scm = csio_hw_to_scsim(hw);
 	int rv = 0;
 	int count = DIV_ROUND_UP(60 * 1000, CSIO_SCSI_ABORT_Q_POLL_MS);
 
@@ -1293,13 +1293,13 @@ csio_scsim_cleanup_io(struct csio_scsim *scm, bool abort)
 
 	/* Else abort */
 	if (abort) {
-		rv = csio_scsi_abort_io_q(scm, &scm->active_q, 30000);
+		rv = csio_scsi_abort_io_q(hw, &scm->active_q, 30000);
 		if (rv == 0)
 			return rv;
 		csio_dbg(hw, "Some I/O aborts timed out, cleaning up..\n");
 	}
 
-	csio_scsi_cleanup_io_q(scm, &scm->active_q);
+	csio_scsi_cleanup_io_q(hw, &scm->active_q);
 
 	CSIO_DB_ASSERT(list_empty(&scm->active_q));
 
@@ -1308,16 +1308,16 @@ csio_scsim_cleanup_io(struct csio_scsim *scm, bool abort)
 
 /*
  * csio_scsim_cleanup_io_lnode - Cleanup all I/Os of given lnode.
- * @scm: SCSI module.
+ * @hw: HW module
  * @lnode: lnode
  *
  * Called with lock held, should exit with lock held.
  * Can sleep (with dropped lock) when waiting for I/Os to complete.
  */
-int
-csio_scsim_cleanup_io_lnode(struct csio_scsim *scm, struct csio_lnode *ln)
+int csio_scsim_cleanup_io_lnode(struct csio_hw *hw, struct csio_lnode *ln)
+	__must_hold(&hw->lock)
 {
-	struct csio_hw *hw = scm->hw;
+	struct csio_scsim *scm = csio_hw_to_scsim(hw);
 	struct csio_scsi_level_data sld;
 	int rv;
 	int count = DIV_ROUND_UP(60 * 1000, CSIO_SCSI_ABORT_Q_POLL_MS);
@@ -1347,10 +1347,10 @@ csio_scsim_cleanup_io_lnode(struct csio_scsim *scm, struct csio_lnode *ln)
 	csio_dbg(hw, "Some I/Os pending on ln:%p, aborting them..\n", ln);
 
 	/* I/Os are pending, abort them */
-	rv = csio_scsi_abort_io_q(scm, &ln->cmpl_q, 30000);
+	rv = csio_scsi_abort_io_q(hw, &ln->cmpl_q, 30000);
 	if (rv != 0) {
 		csio_dbg(hw, "Some I/O aborts timed out, cleaning up..\n");
-		csio_scsi_cleanup_io_q(scm, &ln->cmpl_q);
+		csio_scsi_cleanup_io_q(hw, &ln->cmpl_q);
 	}
 
 	CSIO_DB_ASSERT(list_empty(&ln->cmpl_q));
@@ -2194,7 +2194,7 @@ csio_eh_lun_reset_handler(struct scsi_cmnd *cmnd)
 	spin_lock_irq(&hw->lock);
 	csio_scsi_gather_active_ios(scsim, &sld, &local_q);
 
-	retval = csio_scsi_abort_io_q(scsim, &local_q, 30000);
+	retval = csio_scsi_abort_io_q(hw, &local_q, 30000);
 	spin_unlock_irq(&hw->lock);
 
 	/* Aborts may have timed out */
diff --git a/drivers/scsi/csiostor/csio_scsi.h b/drivers/scsi/csiostor/csio_scsi.h
index 39dda3c88f0d..610aae12be8a 100644
--- a/drivers/scsi/csiostor/csio_scsi.h
+++ b/drivers/scsi/csiostor/csio_scsi.h
@@ -338,10 +338,9 @@ csio_scsi_close(struct csio_ioreq *ioreq)
 	return ioreq->drv_status;
 }
 
-void csio_scsi_cleanup_io_q(struct csio_scsim *, struct list_head *);
-int csio_scsim_cleanup_io(struct csio_scsim *, bool abort);
-int csio_scsim_cleanup_io_lnode(struct csio_scsim *,
-					  struct csio_lnode *);
+void csio_scsi_cleanup_io_q(struct csio_hw *, struct list_head *);
+int csio_scsim_cleanup_io(struct csio_hw *, bool abort);
+int csio_scsim_cleanup_io_lnode(struct csio_hw *, struct csio_lnode *);
 struct csio_ioreq *csio_scsi_cmpl_handler(struct csio_hw *, void *, uint32_t,
 					  struct csio_fl_dma_buf *,
 					  void *, uint8_t **);
diff --git a/drivers/scsi/cxgbi/Makefile b/drivers/scsi/cxgbi/Makefile
index abfd38a26fec..c614afa18a33 100644
--- a/drivers/scsi/cxgbi/Makefile
+++ b/drivers/scsi/cxgbi/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 ccflags-y += -I $(srctree)/drivers/net/ethernet/chelsio/libcxgb
 
 obj-$(CONFIG_SCSI_CXGB3_ISCSI)	+= libcxgbi.o cxgb3i/
diff --git a/drivers/scsi/cxgbi/libcxgbi.c b/drivers/scsi/cxgbi/libcxgbi.c
index ea9631bfe2e2..b0bffbc38183 100644
--- a/drivers/scsi/cxgbi/libcxgbi.c
+++ b/drivers/scsi/cxgbi/libcxgbi.c
@@ -1537,9 +1537,16 @@ skb_read_pdu_bhs(struct cxgbi_sock *csk, struct iscsi_conn *conn,
 		 * for the last pdu of a sequence.
 		 */
 		itt_t itt = ((struct iscsi_data *)skb->data)->itt;
-		struct iscsi_task *task = iscsi_itt_to_ctask(conn, itt);
-		u32 data_sn = be32_to_cpu(((struct iscsi_data *)
-							skb->data)->datasn);
+		struct iscsi_task *task;
+		u32 data_sn;
+
+		/*
+		 * TODO: hold session->back_lock around the iscsi_itt_to_task()
+		 * call below.
+		 */
+		__assume_ctx_lock(&conn->session->back_lock);
+		task = iscsi_itt_to_ctask(conn->session, conn, itt);
+		data_sn = be32_to_cpu(((struct iscsi_data *)skb->data)->datasn);
 		if (task && task->sc) {
 			struct iscsi_tcp_task *tcp_task = task->dd_data;
 
diff --git a/drivers/scsi/elx/Makefile b/drivers/scsi/elx/Makefile
index a8537d7a2a6e..0ed508e379fb 100644
--- a/drivers/scsi/elx/Makefile
+++ b/drivers/scsi/elx/Makefile
@@ -4,6 +4,7 @@
 # * “Broadcom” refers to Broadcom Inc. and/or its subsidiaries.
 # */
 
+CONTEXT_ANALYSIS := y
 
 obj-$(CONFIG_SCSI_EFCT) := efct.o
 
diff --git a/drivers/scsi/elx/libefc/efclib.c b/drivers/scsi/elx/libefc/efclib.c
index dd3e3d0a4761..ceec0e2a0266 100644
--- a/drivers/scsi/elx/libefc/efclib.c
+++ b/drivers/scsi/elx/libefc/efclib.c
@@ -50,6 +50,8 @@ int efcport_init(struct efc *efc)
 						sizeof(struct efc_els_io_req));
 	if (!efc->els_io_pool) {
 		efc_log_err(efc, "Can't allocate els io pool\n");
+		dma_pool_destroy(efc->node_dma_pool);
+		mempool_destroy(efc->node_pool);
 		return -ENOMEM;
 	}
 
diff --git a/drivers/scsi/esas2r/Makefile b/drivers/scsi/esas2r/Makefile
index 279d9cb3ca69..325fa0e634fa 100644
--- a/drivers/scsi/esas2r/Makefile
+++ b/drivers/scsi/esas2r/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_ESAS2R)	+= esas2r.o
 
 esas2r-objs := esas2r_log.o esas2r_disc.o esas2r_flash.o esas2r_init.o \
diff --git a/drivers/scsi/fcoe/Makefile b/drivers/scsi/fcoe/Makefile
index 1183e80a09e7..5e7121231801 100644
--- a/drivers/scsi/fcoe/Makefile
+++ b/drivers/scsi/fcoe/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_FCOE) += fcoe.o
 obj-$(CONFIG_LIBFCOE) += libfcoe.o
 
diff --git a/drivers/scsi/fcoe/fcoe_ctlr.c b/drivers/scsi/fcoe/fcoe_ctlr.c
index 496ddd45f74d..bf92293a0ef0 100644
--- a/drivers/scsi/fcoe/fcoe_ctlr.c
+++ b/drivers/scsi/fcoe/fcoe_ctlr.c
@@ -42,7 +42,8 @@ static void fcoe_ctlr_timer_work(struct work_struct *);
 static void fcoe_ctlr_recv_work(struct work_struct *);
 static int fcoe_ctlr_flogi_retry(struct fcoe_ctlr *);
 
-static void fcoe_ctlr_vn_start(struct fcoe_ctlr *);
+static void fcoe_ctlr_vn_start(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex);
 static int fcoe_ctlr_vn_recv(struct fcoe_ctlr *, struct sk_buff *);
 static void fcoe_ctlr_vn_timeout(struct fcoe_ctlr *);
 static int fcoe_ctlr_vn_lookup(struct fcoe_ctlr *, u32, u8 *);
@@ -154,13 +155,14 @@ EXPORT_SYMBOL(fcoe_ctlr_init);
 
 /**
  * fcoe_sysfs_fcf_add() - Add a fcoe_fcf{,_device} to a fcoe_ctlr{,_device}
+ * @fip: The FCoE controller
  * @new: The newly discovered FCF
  *
  * Called with fip->ctlr_mutex held
  */
-static int fcoe_sysfs_fcf_add(struct fcoe_fcf *new)
+static int fcoe_sysfs_fcf_add(struct fcoe_ctlr *fip, struct fcoe_fcf *new)
+	__must_hold(&fip->ctlr_mutex)
 {
-	struct fcoe_ctlr *fip = new->fip;
 	struct fcoe_ctlr_device *ctlr_dev;
 	struct fcoe_fcf_device *temp, *fcf_dev;
 	int rc = -ENOMEM;
@@ -227,13 +229,14 @@ static int fcoe_sysfs_fcf_add(struct fcoe_fcf *new)
 
 /**
  * fcoe_sysfs_fcf_del() - Remove a fcoe_fcf{,_device} to a fcoe_ctlr{,_device}
+ * @fip: The FCoE controller
  * @new: The FCF to be removed
  *
  * Called with fip->ctlr_mutex held
  */
-static void fcoe_sysfs_fcf_del(struct fcoe_fcf *new)
+static void fcoe_sysfs_fcf_del(struct fcoe_ctlr *fip, struct fcoe_fcf *new)
+	__must_hold(&fip->ctlr_mutex)
 {
-	struct fcoe_ctlr *fip = new->fip;
 	struct fcoe_ctlr_device *cdev;
 	struct fcoe_fcf_device *fcf_dev;
 
@@ -268,13 +271,14 @@ static void fcoe_sysfs_fcf_del(struct fcoe_fcf *new)
  * Called with &fcoe_ctlr lock held.
  */
 static void fcoe_ctlr_reset_fcfs(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fcoe_fcf *fcf;
 	struct fcoe_fcf *next;
 
 	fip->sel_fcf = NULL;
 	list_for_each_entry_safe(fcf, next, &fip->fcfs, list) {
-		fcoe_sysfs_fcf_del(fcf);
+		fcoe_sysfs_fcf_del(fip, fcf);
 	}
 	WARN_ON(fip->fcf_count);
 
@@ -316,6 +320,8 @@ EXPORT_SYMBOL(fcoe_ctlr_destroy);
  * Called with neither ctlr_mutex nor ctlr_lock held.
  */
 static void fcoe_ctlr_announce(struct fcoe_ctlr *fip)
+	__must_not_hold(&fip->ctlr_mutex)
+	__must_not_hold(&fip->ctlr_lock)
 {
 	struct fcoe_fcf *sel;
 	struct fcoe_fcf *fcf;
@@ -476,6 +482,7 @@ EXPORT_SYMBOL(fcoe_ctlr_link_up);
  * @fip:       The FCoE controller to reset
  */
 static void fcoe_ctlr_reset(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	fcoe_ctlr_reset_fcfs(fip);
 	timer_delete(&fip->timer);
@@ -817,6 +824,7 @@ EXPORT_SYMBOL(fcoe_ctlr_els_send);
  * Returns the time in jiffies for the next call.
  */
 static unsigned long fcoe_ctlr_age_fcfs(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fcoe_fcf *fcf;
 	struct fcoe_fcf *next;
@@ -866,7 +874,7 @@ static unsigned long fcoe_ctlr_age_fcfs(struct fcoe_ctlr *fip)
 
 	list_for_each_entry_safe(fcf, next, &del_list, list) {
 		/* Removes fcf from current list */
-		fcoe_sysfs_fcf_del(fcf);
+		fcoe_sysfs_fcf_del(fip, fcf);
 	}
 
 	if (sel_time && !fip->sel_fcf && !fip->sel_time) {
@@ -1049,7 +1057,7 @@ static void fcoe_ctlr_recv_adv(struct fcoe_ctlr *fip, struct sk_buff *skb)
 
 		memcpy(fcf, &new, sizeof(new));
 		fcf->fip = fip;
-		rc = fcoe_sysfs_fcf_add(fcf);
+		rc = fcoe_sysfs_fcf_add(fip, fcf);
 		if (rc) {
 			printk(KERN_ERR "Failed to allocate sysfs instance "
 			       "for FCF, fab %16.16llx mac %pM\n",
@@ -1612,6 +1620,7 @@ static int fcoe_ctlr_recv_handler(struct fcoe_ctlr *fip, struct sk_buff *skb)
  * Called with lock held.
  */
 static struct fcoe_fcf *fcoe_ctlr_select(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fcoe_fcf *fcf;
 	struct fcoe_fcf *best = fip->sel_fcf;
@@ -1664,6 +1673,8 @@ static struct fcoe_fcf *fcoe_ctlr_select(struct fcoe_ctlr *fip)
  * Caller must verify that fip->sel_fcf is not NULL.
  */
 static int fcoe_ctlr_flogi_send_locked(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
+	__must_hold(&fip->ctlr_lock)
 {
 	struct sk_buff *skb;
 	struct sk_buff *skb_orig;
@@ -1733,6 +1744,7 @@ static int fcoe_ctlr_flogi_retry(struct fcoe_ctlr *fip)
  * Called with ctlr_mutex held.  The caller must not hold ctlr_lock.
  */
 static void fcoe_ctlr_flogi_send(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fcoe_fcf *fcf;
 
@@ -2012,6 +2024,7 @@ static inline struct fcoe_rport *fcoe_ctlr_rport(struct fc_rport_priv *rdata)
 static void fcoe_ctlr_vn_send(struct fcoe_ctlr *fip,
 			      enum fip_vn2vn_subcode sub,
 			      const u8 *dest, size_t min_len)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct sk_buff *skb;
 	struct fip_vn2vn_probe_frame {
@@ -2152,11 +2165,14 @@ static struct fc_rport_operations fcoe_ctlr_vn_rport_ops = {
 
 /**
  * fcoe_ctlr_disc_stop_locked() - stop discovery in VN2VN mode
+ * @fip: The FCoE controller
  * @lport: The local port
  *
  * Called with ctlr_mutex held.
  */
-static void fcoe_ctlr_disc_stop_locked(struct fc_lport *lport)
+static void fcoe_ctlr_disc_stop_locked(struct fcoe_ctlr *fip,
+				       struct fc_lport *lport)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fc_rport_priv *rdata;
 
@@ -2183,7 +2199,7 @@ static void fcoe_ctlr_disc_stop(struct fc_lport *lport)
 	struct fcoe_ctlr *fip = lport->disc.priv;
 
 	mutex_lock(&fip->ctlr_mutex);
-	fcoe_ctlr_disc_stop_locked(lport);
+	fcoe_ctlr_disc_stop_locked(fip, lport);
 	mutex_unlock(&fip->ctlr_mutex);
 }
 
@@ -2208,11 +2224,12 @@ static void fcoe_ctlr_disc_stop_final(struct fc_lport *lport)
  * Called with fcoe_ctlr lock held.
  */
 static void fcoe_ctlr_vn_restart(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	unsigned long wait;
 	u32 port_id;
 
-	fcoe_ctlr_disc_stop_locked(fip->lp);
+	fcoe_ctlr_disc_stop_locked(fip, fip->lp);
 
 	/*
 	 * Get proposed port ID.
@@ -2246,6 +2263,7 @@ static void fcoe_ctlr_vn_restart(struct fcoe_ctlr *fip)
  * Called with fcoe_ctlr lock held.
  */
 static void fcoe_ctlr_vn_start(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	fip->probe_tries = 0;
 	prandom_seed_state(&fip->rnd_state, fip->lp->wwpn);
@@ -2387,6 +2405,7 @@ static int fcoe_ctlr_vn_parse(struct fcoe_ctlr *fip,
  * Called with ctlr_mutex held.
  */
 static void fcoe_ctlr_vn_send_claim(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	fcoe_ctlr_vn_send(fip, FIP_SC_VN_CLAIM_NOTIFY, fcoe_all_vn2vn, 0);
 	fip->sol_time = jiffies;
@@ -2401,6 +2420,7 @@ static void fcoe_ctlr_vn_send_claim(struct fcoe_ctlr *fip)
  */
 static void fcoe_ctlr_vn_probe_req(struct fcoe_ctlr *fip,
 				   struct fcoe_rport *frport)
+	__must_hold(&fip->ctlr_mutex)
 {
 	if (frport->rdata.ids.port_id != fip->port_id)
 		return;
@@ -2452,6 +2472,7 @@ static void fcoe_ctlr_vn_probe_req(struct fcoe_ctlr *fip,
  */
 static void fcoe_ctlr_vn_probe_reply(struct fcoe_ctlr *fip,
 				     struct fcoe_rport *frport)
+	__must_hold(&fip->ctlr_mutex)
 {
 	if (frport->rdata.ids.port_id != fip->port_id)
 		return;
@@ -2481,6 +2502,7 @@ static void fcoe_ctlr_vn_probe_reply(struct fcoe_ctlr *fip,
  * Called with ctlr_mutex held.
  */
 static void fcoe_ctlr_vn_add(struct fcoe_ctlr *fip, struct fcoe_rport *new)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fc_lport *lport = fip->lp;
 	struct fc_rport_priv *rdata;
@@ -2564,6 +2586,7 @@ static int fcoe_ctlr_vn_lookup(struct fcoe_ctlr *fip, u32 port_id, u8 *mac)
  */
 static void fcoe_ctlr_vn_claim_notify(struct fcoe_ctlr *fip,
 				      struct fcoe_rport *new)
+	__must_hold(&fip->ctlr_mutex)
 {
 	if (new->flags & FIP_FL_REC_OR_P2P) {
 		LIBFCOE_FIP_DBG(fip, "send probe req for P2P/REC\n");
@@ -2619,6 +2642,7 @@ static void fcoe_ctlr_vn_claim_notify(struct fcoe_ctlr *fip,
  */
 static void fcoe_ctlr_vn_claim_resp(struct fcoe_ctlr *fip,
 				    struct fcoe_rport *new)
+	__must_hold(&fip->ctlr_mutex)
 {
 	LIBFCOE_FIP_DBG(fip, "claim resp from from rport %x - state %s\n",
 			new->rdata.ids.port_id, fcoe_ctlr_state(fip->state));
@@ -2635,6 +2659,7 @@ static void fcoe_ctlr_vn_claim_resp(struct fcoe_ctlr *fip,
  */
 static void fcoe_ctlr_vn_beacon(struct fcoe_ctlr *fip,
 				struct fcoe_rport *new)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fc_lport *lport = fip->lp;
 	struct fc_rport_priv *rdata;
@@ -2688,6 +2713,7 @@ static void fcoe_ctlr_vn_beacon(struct fcoe_ctlr *fip,
  * Returns the soonest time for next age-out or a time far in the future.
  */
 static unsigned long fcoe_ctlr_vn_age(struct fcoe_ctlr *fip)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct fc_lport *lport = fip->lp;
 	struct fc_rport_priv *rdata;
@@ -2890,6 +2916,7 @@ static int fcoe_ctlr_vlan_parse(struct fcoe_ctlr *fip,
 static void fcoe_ctlr_vlan_send(struct fcoe_ctlr *fip,
 			      enum fip_vlan_subcode sub,
 			      const u8 *dest)
+	__must_hold(&fip->ctlr_mutex)
 {
 	struct sk_buff *skb;
 	struct fip_vlan_notify_frame {
@@ -2951,6 +2978,7 @@ static void fcoe_ctlr_vlan_send(struct fcoe_ctlr *fip,
  */
 static void fcoe_ctlr_vlan_disc_reply(struct fcoe_ctlr *fip,
 				      struct fcoe_rport *frport)
+	__must_hold(&fip->ctlr_mutex)
 {
 	enum fip_vlan_subcode sub = FIP_SC_VL_NOTE;
 
diff --git a/drivers/scsi/fnic/Makefile b/drivers/scsi/fnic/Makefile
index 48c5e0cb8ca6..22a463380dee 100644
--- a/drivers/scsi/fnic/Makefile
+++ b/drivers/scsi/fnic/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_FCOE_FNIC) += fnic.o
 
 fnic-y	:= \
diff --git a/drivers/scsi/fnic/fdls_disc.c b/drivers/scsi/fnic/fdls_disc.c
index 8cb40466872f..b04bb9a5dfa8 100644
--- a/drivers/scsi/fnic/fdls_disc.c
+++ b/drivers/scsi/fnic/fdls_disc.c
@@ -87,7 +87,8 @@ static void fnic_fdls_start_flogi(struct fnic_iport_s *iport);
 static struct fnic_tport_s *fdls_create_tport(struct fnic_iport_s *iport,
 					  uint32_t fcid,
 					  uint64_t wwpn);
-static void fdls_target_restart_nexus(struct fnic_tport_s *tport);
+static void fdls_target_restart_nexus(struct fnic_iport_s *iport,
+				      struct fnic_tport_s *tport);
 static void fdls_start_tport_timer(struct fnic_iport_s *iport,
 					struct fnic_tport_s *tport, int timeout);
 static void fdls_tport_timer_callback(struct timer_list *t);
@@ -417,6 +418,7 @@ static void fdls_reset_oxid_pool(struct fnic_iport_s *iport)
 }
 
 void fnic_del_fabric_timer_sync(struct fnic *fnic)
+	__must_hold(&fnic->fnic_lock)
 {
 	fnic->iport.fabric.del_timer_inprogress = 1;
 	spin_unlock_irqrestore(&fnic->fnic_lock, fnic->lock_flags);
@@ -425,8 +427,8 @@ void fnic_del_fabric_timer_sync(struct fnic *fnic)
 	fnic->iport.fabric.del_timer_inprogress = 0;
 }
 
-void fnic_del_tport_timer_sync(struct fnic *fnic,
-						struct fnic_tport_s *tport)
+void fnic_del_tport_timer_sync(struct fnic *fnic, struct fnic_tport_s *tport)
+	__must_hold(&fnic->fnic_lock)
 {
 	tport->del_timer_inprogress = 1;
 	spin_unlock_irqrestore(&fnic->fnic_lock, fnic->lock_flags);
@@ -437,6 +439,7 @@ void fnic_del_tport_timer_sync(struct fnic *fnic,
 
 static void
 fdls_start_fabric_timer(struct fnic_iport_s *iport, int timeout)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	u64 fabric_tov;
 	struct fnic *fnic = iport->fnic;
@@ -462,6 +465,7 @@ fdls_start_fabric_timer(struct fnic_iport_s *iport, int timeout)
 static void
 fdls_start_tport_timer(struct fnic_iport_s *iport,
 					   struct fnic_tport_s *tport, int timeout)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	u64 fabric_tov;
 	struct fnic *fnic = iport->fnic;
@@ -717,6 +721,7 @@ int fdls_send_ls_req_abts(struct fnic_iport_s *iport,
 void
 fdls_send_tport_abts(struct fnic_iport_s *iport,
 					 struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	uint8_t s_id[3];
@@ -760,7 +765,9 @@ fdls_send_tport_abts(struct fnic_iport_s *iport,
 	/* Even if fnic_send_fcoe_frame() fails we want to retry after timeout */
 	fdls_start_tport_timer(iport, tport, 2 * iport->e_d_tov);
 }
+
 static void fdls_send_fabric_abts(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	uint8_t s_id[3];
@@ -932,6 +939,7 @@ static void fdls_send_fdmi_abts(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_fabric_flogi(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_flogi *pflogi;
@@ -992,6 +1000,7 @@ static void fdls_send_fabric_flogi(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_fabric_plogi(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_flogi *pplogi;
@@ -1084,6 +1093,7 @@ static void fdls_send_fdmi_plogi(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_rpn_id(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_rpn_id *prpn_id;
@@ -1143,6 +1153,7 @@ static void fdls_send_rpn_id(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_scr(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_scr *pscr;
@@ -1198,6 +1209,7 @@ static void fdls_send_scr(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_gpn_ft(struct fnic_iport_s *iport, int fdls_state)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_gpn_ft *pgpn_ft;
@@ -1257,6 +1269,7 @@ static void fdls_send_gpn_ft(struct fnic_iport_s *iport, int fdls_state)
 
 static void
 fdls_send_tgt_adisc(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_els_adisc *padisc;
@@ -1322,6 +1335,7 @@ fdls_send_tgt_adisc(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
 }
 
 bool fdls_delete_tport(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_tport_event_s *tport_del_evt;
 	struct fnic *fnic = iport->fnic;
@@ -1387,6 +1401,7 @@ bool fdls_delete_tport(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
 
 static void
 fdls_send_tgt_plogi(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_flogi *pplogi;
@@ -1455,6 +1470,7 @@ fnic_fc_plogi_rsp_rdf(struct fnic_iport_s *iport,
 }
 
 static void fdls_send_register_fc4_types(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_rft_id *prft_id;
@@ -1522,6 +1538,7 @@ static void fdls_send_register_fc4_types(struct fnic_iport_s *iport)
 }
 
 static void fdls_send_register_fc4_features(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_rff_id *prff_id;
@@ -1581,6 +1598,7 @@ static void fdls_send_register_fc4_features(struct fnic_iport_s *iport)
 
 static void
 fdls_send_tgt_prli(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_els_prli *pprli;
@@ -1662,6 +1680,7 @@ fdls_send_tgt_prli(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
  * Currently this assumes to be called with fnic lock held.
  */
 void fdls_send_fabric_logo(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *frame;
 	struct fc_std_logo *plogo;
@@ -1761,6 +1780,7 @@ void fdls_tgt_logout(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
 }
 
 static void fdls_tgt_discovery_start(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_tport_s *tport, *next;
 	u32 old_link_down_cnt = iport->fnic->link_down_cnt;
@@ -1810,9 +1830,10 @@ static void fdls_tgt_discovery_start(struct fnic_iport_s *iport)
  * safely since the memory it is
  * pointing to it will be freed later
  */
-static void fdls_target_restart_nexus(struct fnic_tport_s *tport)
+static void fdls_target_restart_nexus(struct fnic_iport_s *iport,
+				      struct fnic_tport_s *tport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
-	struct fnic_iport_s *iport = tport->iport;
 	struct fnic_tport_s *new_tport = NULL;
 	uint32_t fcid;
 	uint64_t wwpn;
@@ -2617,6 +2638,7 @@ static void fdls_tport_timer_callback(struct timer_list *t)
 }
 
 static void fnic_fdls_start_flogi(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	iport->fabric.retry_counter = 0;
 	fdls_send_fabric_flogi(iport);
@@ -2625,6 +2647,7 @@ static void fnic_fdls_start_flogi(struct fnic_iport_s *iport)
 }
 
 static void fnic_fdls_start_plogi(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	iport->fabric.retry_counter = 0;
 	fdls_send_fabric_plogi(iport);
@@ -2643,6 +2666,7 @@ static void fnic_fdls_start_plogi(struct fnic_iport_s *iport)
 static void
 fdls_process_tgt_adisc_rsp(struct fnic_iport_s *iport,
 			   struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t tgt_fcid;
 	struct fnic_tport_s *tport;
@@ -2733,6 +2757,7 @@ fdls_process_tgt_adisc_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_tgt_plogi_rsp(struct fnic_iport_s *iport,
 			   struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t tgt_fcid;
 	struct fnic_tport_s *tport;
@@ -2767,7 +2792,7 @@ fdls_process_tgt_plogi_rsp(struct fnic_iport_s *iport,
 	if (tport->state != FDLS_TGT_STATE_PLOGI) {
 		FNIC_FCS_DBG(KERN_INFO, fnic,
 			     "PLOGI rsp recvd in wrong state. Drop the frame and restart nexus");
-		fdls_target_restart_nexus(tport);
+		fdls_target_restart_nexus(iport, tport);
 		return;
 	}
 
@@ -2854,9 +2879,11 @@ fdls_process_tgt_plogi_rsp(struct fnic_iport_s *iport,
 	fdls_set_tport_state(tport, FDLS_TGT_STATE_PRLI);
 	fdls_send_tgt_prli(iport, tport);
 }
+
 static void
 fdls_process_tgt_prli_rsp(struct fnic_iport_s *iport,
 			  struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t tgt_fcid;
 	struct fnic_tport_s *tport;
@@ -2893,7 +2920,7 @@ fdls_process_tgt_prli_rsp(struct fnic_iport_s *iport,
 	if (tport->state != FDLS_TGT_STATE_PRLI) {
 		FNIC_FCS_DBG(KERN_INFO, fnic,
 			     "PRLI rsp recvd in wrong state. Drop frame. Restarting nexus");
-		fdls_target_restart_nexus(tport);
+		fdls_target_restart_nexus(iport, tport);
 		return;
 	}
 
@@ -3025,6 +3052,7 @@ fdls_process_tgt_prli_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_rff_id_rsp(struct fnic_iport_s *iport,
 			struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic *fnic = iport->fnic;
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
@@ -3098,6 +3126,7 @@ fdls_process_rff_id_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_rft_id_rsp(struct fnic_iport_s *iport,
 			struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
 	struct fc_std_rft_id *rft_rsp = (struct fc_std_rft_id *) fchdr;
@@ -3173,6 +3202,7 @@ fdls_process_rft_id_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_rpn_id_rsp(struct fnic_iport_s *iport,
 			struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
 	struct fc_std_rpn_id *rpn_rsp = (struct fc_std_rpn_id *) fchdr;
@@ -3243,6 +3273,7 @@ fdls_process_rpn_id_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_scr_rsp(struct fnic_iport_s *iport,
 		     struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
 	struct fc_std_scr *scr_rsp = (struct fc_std_scr *) fchdr;
@@ -3315,6 +3346,7 @@ fdls_process_scr_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_gpn_ft_tgt_list(struct fnic_iport_s *iport,
 			     struct fc_frame_header *fchdr, int len)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_gpn_ft_rsp_iu *gpn_ft_tgt;
 	struct fnic_tport_s *tport, *next;
@@ -3413,6 +3445,7 @@ fdls_process_gpn_ft_tgt_list(struct fnic_iport_s *iport,
 static void
 fdls_process_gpn_ft_rsp(struct fnic_iport_s *iport,
 			struct fc_frame_header *fchdr, int len)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
 	struct fc_std_gpn_ft *gpn_ft_rsp = (struct fc_std_gpn_ft *) fchdr;
@@ -3549,6 +3582,7 @@ fdls_process_gpn_ft_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_fabric_logo_rsp(struct fnic_iport_s *iport,
 			     struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_std_flogi *flogo_rsp = (struct fc_std_flogi *) fchdr;
 	struct fnic_fdls_fabric_s *fdls = &iport->fabric;
@@ -3602,6 +3636,7 @@ fdls_process_fabric_logo_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_flogi_rsp(struct fnic_iport_s *iport,
 		       struct fc_frame_header *fchdr, void *rx_frame)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_fdls_fabric_s *fabric = &iport->fabric;
 	struct fc_std_flogi *flogi_rsp = (struct fc_std_flogi *) fchdr;
@@ -3741,6 +3776,7 @@ fdls_process_flogi_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_fabric_plogi_rsp(struct fnic_iport_s *iport,
 			      struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_std_flogi *plogi_rsp = (struct fc_std_flogi *) fchdr;
 	struct fc_std_els_rjt_rsp *els_rjt = (struct fc_std_els_rjt_rsp *) fchdr;
@@ -4002,6 +4038,7 @@ static void fdls_process_fdmi_abts_rsp(struct fnic_iport_s *iport,
 static void
 fdls_process_fabric_abts_rsp(struct fnic_iport_s *iport,
 			     struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t s_id;
 	struct fc_std_abts_ba_acc *ba_acc = (struct fc_std_abts_ba_acc *)fchdr;
@@ -4359,6 +4396,7 @@ fdls_process_els_req(struct fnic_iport_s *iport, struct fc_frame_header *fchdr,
 static void
 fdls_process_tgt_abts_rsp(struct fnic_iport_s *iport,
 			  struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t s_id;
 	struct fnic_tport_s *tport;
@@ -4548,6 +4586,7 @@ fdls_process_plogi_req(struct fnic_iport_s *iport,
 
 static void
 fdls_process_logo_req(struct fnic_iport_s *iport, struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_std_logo *logo = (struct fc_std_logo *)fchdr;
 	uint32_t nport_id;
@@ -4625,6 +4664,7 @@ fdls_process_logo_req(struct fnic_iport_s *iport, struct fc_frame_header *fchdr)
 
 static void
 fdls_process_rscn(struct fnic_iport_s *iport, struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_std_rscn *rscn;
 	struct fc_els_rscn_page *rscn_port = NULL;
@@ -4758,6 +4798,7 @@ fdls_process_rscn(struct fnic_iport_s *iport, struct fc_frame_header *fchdr)
 }
 
 void fnic_fdls_disc_start(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic *fnic = iport->fnic;
 
@@ -5102,6 +5143,7 @@ fnic_fdls_validate_and_get_frame_type(struct fnic_iport_s *iport,
 
 void fnic_fdls_recv_frame(struct fnic_iport_s *iport, void *rx_frame,
 						  int len, int fchdr_offset)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fc_frame_header *fchdr;
 	uint32_t s_id = 0;
@@ -5223,6 +5265,7 @@ void fnic_fdls_disc_init(struct fnic_iport_s *iport)
 }
 
 void fnic_fdls_link_down(struct fnic_iport_s *iport)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic_tport_s *tport, *next;
 	struct fnic *fnic = iport->fnic;
diff --git a/drivers/scsi/fnic/fip.c b/drivers/scsi/fnic/fip.c
index 231dec180675..8f44abfc01a5 100644
--- a/drivers/scsi/fnic/fip.c
+++ b/drivers/scsi/fnic/fip.c
@@ -602,6 +602,7 @@ void fnic_common_fip_cleanup(struct fnic *fnic)
  * and clean up and restart the vlan discovery.
  */
 void fnic_fcoe_process_cvl(struct fnic *fnic, struct fip_header *fiph)
+	__must_hold(&fnic->fnic_lock)
 {
 	struct fnic_iport_s *iport = &fnic->iport;
 	struct fip_cvl *cvl_msg = (struct fip_cvl *)fiph;
@@ -678,6 +679,7 @@ void fnic_fcoe_process_cvl(struct fnic *fnic, struct fip_header *fiph)
  * @frame: Received ethernet frame
  */
 int fdls_fip_recv_frame(struct fnic *fnic, void *frame)
+	__must_hold(&fnic->fnic_lock)
 {
 	struct ethhdr *eth = (struct ethhdr *)frame;
 	struct fip_header *fiph;
diff --git a/drivers/scsi/fnic/fnic.h b/drivers/scsi/fnic/fnic.h
index c576a7f5083e..c7b3dba50020 100644
--- a/drivers/scsi/fnic/fnic.h
+++ b/drivers/scsi/fnic/fnic.h
@@ -31,7 +31,7 @@
 
 #define DRV_NAME		"fnic"
 #define DRV_DESCRIPTION		"Cisco FCoE HBA Driver"
-#define DRV_VERSION		"1.9.0.0"
+#define DRV_VERSION		"1.9.0.2"
 #define PFX			DRV_NAME ": "
 #define DFX                     DRV_NAME "%d: "
 
diff --git a/drivers/scsi/fnic/fnic_fcs.c b/drivers/scsi/fnic/fnic_fcs.c
index b00672ef8b00..b5a6a2b99c4e 100644
--- a/drivers/scsi/fnic/fnic_fcs.c
+++ b/drivers/scsi/fnic/fnic_fcs.c
@@ -942,10 +942,10 @@ void fnic_free_wq_buf(struct vnic_wq *wq, struct vnic_wq_buf *buf)
 }
 
 void
-fnic_fdls_add_tport(struct fnic_iport_s *iport, struct fnic_tport_s *tport,
-					unsigned long flags)
+fnic_fdls_add_tport(struct fnic *fnic, struct fnic_tport_s *tport,
+		    unsigned long flags)
+	__must_hold(&fnic->fnic_lock)
 {
-	struct fnic *fnic = iport->fnic;
 	struct fc_rport *rport;
 	struct fc_rport_identifiers ids;
 	struct rport_dd_data_s *rdd_data;
@@ -975,18 +975,17 @@ fnic_fdls_add_tport(struct fnic_iport_s *iport, struct fnic_tport_s *tport,
 	rport->supported_classes = FC_COS_CLASS3 | FC_RPORT_ROLE_FCP_TARGET;
 	rdd_data = rport->dd_data;
 	rdd_data->tport = tport;
-	rdd_data->iport = iport;
+	rdd_data->iport = &fnic->iport;
 	tport->rport = rport;
 	tport->flags |= FNIC_FDLS_SCSI_REGISTERED;
 }
 
 void
-fnic_fdls_remove_tport(struct fnic_iport_s *iport,
-					   struct fnic_tport_s *tport, unsigned long flags)
+fnic_fdls_remove_tport(struct fnic *fnic, struct fnic_tport_s *tport,
+		       unsigned long flags)
+	__must_hold(&fnic->fnic_lock)
 {
-	struct fnic *fnic = iport->fnic;
 	struct rport_dd_data_s *rdd_data;
-
 	struct fc_rport *rport;
 
 	if (!tport)
@@ -1038,7 +1037,7 @@ void fnic_delete_fcp_tports(struct fnic *fnic)
 		fdls_set_tport_state(tport, FDLS_TGT_STATE_OFFLINING);
 		fnic_del_tport_timer_sync(fnic, tport);
 		if (IS_FNIC_FCP_INITIATOR(fnic))
-			fnic_fdls_remove_tport(&fnic->iport, tport, flags);
+			fnic_fdls_remove_tport(fnic, tport, flags);
 		else if (IS_FNIC_NVME_INITIATOR(fnic))
 			nvfnic_delete_tport(&fnic->iport, tport, flags);
 	}
@@ -1067,7 +1066,7 @@ void fnic_tport_event_handler(struct work_struct *work)
 						 "Add rport event");
 			if (tport->state == FDLS_TGT_STATE_READY) {
 				if (IS_FNIC_FCP_INITIATOR(fnic))
-					fnic_fdls_add_tport(&fnic->iport, tport, flags);
+					fnic_fdls_add_tport(fnic, tport, flags);
 				else if (IS_FNIC_NVME_INITIATOR(fnic))
 					nvfnic_add_tport(fnic, tport, flags);
 			} else {
@@ -1081,7 +1080,7 @@ void fnic_tport_event_handler(struct work_struct *work)
 						 "Remove rport event");
 			if (tport->state == FDLS_TGT_STATE_OFFLINING) {
 				if (IS_FNIC_FCP_INITIATOR(fnic))
-					fnic_fdls_remove_tport(&fnic->iport, tport, flags);
+					fnic_fdls_remove_tport(fnic, tport, flags);
 				else if (IS_FNIC_NVME_INITIATOR(fnic))
 					nvfnic_delete_tport(&fnic->iport, tport, flags);
 			} else {
diff --git a/drivers/scsi/fnic/fnic_fdls.h b/drivers/scsi/fnic/fnic_fdls.h
index ce4b3aae77e3..75f83c78aea1 100644
--- a/drivers/scsi/fnic/fnic_fdls.h
+++ b/drivers/scsi/fnic/fnic_fdls.h
@@ -433,10 +433,9 @@ int fnic_send_fip_frame(struct fnic_iport_s *iport,
 	void *frame, int frame_size);
 void fnic_fdls_learn_fcoe_macs(struct fnic_iport_s *iport, void *rx_frame,
 	uint8_t *fcid);
-void fnic_fdls_add_tport(struct fnic_iport_s *iport,
-		struct fnic_tport_s *tport, unsigned long flags);
-void fnic_fdls_remove_tport(struct fnic_iport_s *iport,
-			    struct fnic_tport_s *tport,
+void fnic_fdls_add_tport(struct fnic *fnic, struct fnic_tport_s *tport,
+			 unsigned long flags);
+void fnic_fdls_remove_tport(struct fnic *fnic, struct fnic_tport_s *tport,
 			    unsigned long flags);
 void fnic_fcpio_reset(struct fnic *fnic);
 
diff --git a/drivers/scsi/fnic/fnic_isr.c b/drivers/scsi/fnic/fnic_isr.c
index 02856745580f..43149d8312ec 100644
--- a/drivers/scsi/fnic/fnic_isr.c
+++ b/drivers/scsi/fnic/fnic_isr.c
@@ -245,7 +245,14 @@ int fnic_set_intr_mode_msix(struct fnic *fnic)
 	unsigned int m = ARRAY_SIZE(fnic->wq);
 	unsigned int o = ARRAY_SIZE(fnic->hw_copy_wq);
 	unsigned int min_irqs = n + m + 1 + 1; /*rq, raw wq, wq, err*/
-
+	/*
+	 * Make driver critical vectors unmanaged, or else it can get tied
+	 * to an offline CPU. This can happen when hyper-threading is off.
+	 */
+	struct irq_affinity affd = {
+		.pre_vectors = n + m + 1, /* rq, raw wq, 1 ioq */
+		.post_vectors = 1, /* err */
+	};
 	/*
 	 * We need n RQs, m WQs, o Copy WQs, n+m+o CQs, and n+m+o+1 INTRs
 	 * (last INTR is used for WQ/RQ errors and notification area)
@@ -263,8 +270,8 @@ int fnic_set_intr_mode_msix(struct fnic *fnic)
 		int vec_count = 0;
 		int vecs = fnic->rq_count + fnic->raw_wq_count + fnic->wq_copy_count + 1;
 
-		vec_count = pci_alloc_irq_vectors(fnic->pdev, min_irqs, vecs,
-					PCI_IRQ_MSIX | PCI_IRQ_AFFINITY);
+		vec_count = pci_alloc_irq_vectors_affinity(fnic->pdev, min_irqs,
+			    vecs, PCI_IRQ_MSIX|PCI_IRQ_AFFINITY, &affd);
 		FNIC_ISR_DBG(KERN_INFO, fnic,
 					"allocated %d MSI-X vectors\n",
 					vec_count);
diff --git a/drivers/scsi/fnic/fnic_main.c b/drivers/scsi/fnic/fnic_main.c
index 9b3025007075..a19c0b0d812d 100644
--- a/drivers/scsi/fnic/fnic_main.c
+++ b/drivers/scsi/fnic/fnic_main.c
@@ -56,8 +56,11 @@ static const struct pci_device_id fnic_id_table[] = {
 };
 
 MODULE_DESCRIPTION(DRV_DESCRIPTION);
-MODULE_AUTHOR("Abhijeet Joglekar <abjoglek@cisco.com>, "
-	      "Joseph R. Eykholt <jeykholt@cisco.com>");
+MODULE_AUTHOR("Karan Tilak Kumar <kartilak@cisco.com>");
+MODULE_AUTHOR("Arun Easi <aeasi@cisco.com>");
+MODULE_AUTHOR("Gian Carlo Boffa <gcboffa@cisco.com>");
+MODULE_AUTHOR("Arulprabhu Ponnusamy <arulponn@cisco.com>");
+MODULE_AUTHOR("Sesidhar Baddela <sebaddel@cisco.com>");
 MODULE_LICENSE("GPL v2");
 MODULE_VERSION(DRV_VERSION);
 MODULE_DEVICE_TABLE(pci, fnic_id_table);
@@ -744,8 +747,19 @@ static int fnic_nvme_drv_init(struct fnic *fnic)
 	return ret;
 }
 
+static void fnic_mq_init_queue_map(struct fnic *fnic,
+		struct blk_mq_queue_map *qmap)
+{
+	unsigned int cpu;
+
+	for_each_possible_cpu(cpu)
+		qmap->mq_map[cpu] = 0;
+}
+
 void fnic_mq_map_queues_cpus(struct Scsi_Host *host)
 {
+	const struct cpumask *mask;
+	unsigned int queue, cpu;
 	struct fnic *fnic = *((struct fnic **) shost_priv(host));
 	struct pci_dev *l_pdev = fnic->pdev;
 	int intr_mode = fnic->config.intr_mode;
@@ -766,7 +780,35 @@ void fnic_mq_map_queues_cpus(struct Scsi_Host *host)
 		return;
 	}
 
-	blk_mq_map_hw_queues(qmap, &l_pdev->dev, FNIC_PCI_OFFSET);
+	fnic_mq_init_queue_map(fnic, qmap);
+
+	/*
+	 * Setup CPU to Queue mapping for all managed MSI-X IRQs.
+	 * Q0 is driver critical and non-managed, hence start from Q1.
+	 */
+	for (queue = 1; queue < qmap->nr_queues; queue++) {
+		int irq_num = pci_irq_vector(fnic->pdev,
+					     queue + FNIC_PCI_OFFSET);
+
+		if (irq_num < 0)
+			continue;
+
+		mask = pci_irq_get_affinity(fnic->pdev,
+					    queue + FNIC_PCI_OFFSET);
+		if (!mask) {
+			shost_printk(KERN_ERR, host,
+				"failed to get irq_affinity map for queue:%d\n", irq_num);
+			continue;
+		}
+		FNIC_MAIN_DBG(KERN_INFO, fnic,
+				"got irq_affinity map for %d:\n", irq_num);
+		for_each_cpu(cpu, mask) {
+			qmap->mq_map[cpu] = qmap->queue_offset + queue;
+			FNIC_MAIN_DBG(KERN_INFO, fnic,
+				      "[Q%d] cpu:%d <=> irq:%d\n",
+				      queue, cpu, irq_num);
+		}
+	}
 }
 
 static int fnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
diff --git a/drivers/scsi/fnic/fnic_nvme.c b/drivers/scsi/fnic/fnic_nvme.c
index 00d9d5d439a3..d1b327c5c5e0 100644
--- a/drivers/scsi/fnic/fnic_nvme.c
+++ b/drivers/scsi/fnic/fnic_nvme.c
@@ -1284,6 +1284,7 @@ void nvfnic_fcpio_cmpl(struct fnic_io_req *io_req)
 
 void nvfnic_process_ls_abts_rsp(struct fnic_iport_s *iport,
 		struct fc_frame_header *fchdr)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint32_t tport_fcid;
 	struct fnic_tport_s *tport;
@@ -1348,6 +1349,7 @@ void nvfnic_process_ls_abts_rsp(struct fnic_iport_s *iport,
  */
 void nvfnic_ls_rsp_recv(struct fnic_iport_s *iport,
 		struct fc_frame_header *fchdr, int len)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	uint8_t *fcid;
 	uint32_t tport_fcid;
@@ -2086,6 +2088,7 @@ void nvfnic_exch_reset(struct fnic_iport_s *iport, struct fnic_tport_s *tport)
 void nvfnic_delete_tport(struct fnic_iport_s *iport,
 						struct fnic_tport_s *tport,
 						unsigned long flags)
+	__must_hold(&iport->fnic->fnic_lock)
 {
 	struct fnic *fnic = iport->fnic;
 	int ret;
@@ -2179,6 +2182,7 @@ void nvfnic_delete_tport(struct fnic_iport_s *iport,
 
 int nvfnic_add_tport(struct fnic *fnic, struct fnic_tport_s *tport,
 		     unsigned long flags)
+	__must_hold(&fnic->fnic_lock)
 {
 	struct fnic_iport_s *iport = &fnic->iport;
 	struct nvme_fc_port_info pinfo;
diff --git a/drivers/scsi/fnic/fnic_scsi.c b/drivers/scsi/fnic/fnic_scsi.c
index 9607684bc610..afd6bf03b02d 100644
--- a/drivers/scsi/fnic/fnic_scsi.c
+++ b/drivers/scsi/fnic/fnic_scsi.c
@@ -2641,6 +2641,8 @@ int fnic_device_reset(struct scsi_cmnd *sc)
 		 * allocated by mid layer.
 		 */
 		mutex_lock(&fnic->sgreset_mutex);
+		/* Fake __release() to keep the lock context analyzer happy. */
+		__release(&fnic->sgreset_mutex);
 		mqtag = fnic->fnic_max_tag_id;
 		new_sc = 1;
 	}  else {
@@ -2826,6 +2828,8 @@ int fnic_device_reset(struct scsi_cmnd *sc)
 
 	if (new_sc) {
 		fnic->sgreset_sc = NULL;
+		/* Fake __acquire() to keep the lock context analyzer happy. */
+		__acquire(&fnic->sgreset_mutex);
 		mutex_unlock(&fnic->sgreset_mutex);
 	}
 
diff --git a/drivers/scsi/hisi_sas/Makefile b/drivers/scsi/hisi_sas/Makefile
index 742e732cd51d..8576c78d4afe 100644
--- a/drivers/scsi/hisi_sas/Makefile
+++ b/drivers/scsi/hisi_sas/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_HISI_SAS)		+= hisi_sas_main.o
 obj-$(CONFIG_SCSI_HISI_SAS)		+= hisi_sas_v1_hw.o hisi_sas_v2_hw.o
 obj-$(CONFIG_SCSI_HISI_SAS_PCI)		+= hisi_sas_v3_hw.o
diff --git a/drivers/scsi/hisi_sas/hisi_sas.h b/drivers/scsi/hisi_sas/hisi_sas.h
index 1323ed8aa717..d48ba3747b81 100644
--- a/drivers/scsi/hisi_sas/hisi_sas.h
+++ b/drivers/scsi/hisi_sas/hisi_sas.h
@@ -163,6 +163,7 @@ enum hisi_sas_phy_event {
 	HISI_PHYE_PHY_UP   = 0U,
 	HISI_PHYE_LINK_RESET,
 	HISI_PHYE_PHY_UP_PM,
+	HISI_PHYE_SPINUP_NOTIFY,
 	HISI_PHYES_NUM,
 };
 
@@ -689,4 +690,6 @@ extern void hisi_sas_sync_cqs(struct hisi_hba *hisi_hba);
 extern void hisi_sas_sync_poll_cqs(struct hisi_hba *hisi_hba);
 extern void hisi_sas_controller_reset_prepare(struct hisi_hba *hisi_hba);
 extern void hisi_sas_controller_reset_done(struct hisi_hba *hisi_hba);
+extern void hisi_sas_spinup_notify(struct hisi_hba *hisi_hba,
+				   struct sas_task *task);
 #endif
diff --git a/drivers/scsi/hisi_sas/hisi_sas_main.c b/drivers/scsi/hisi_sas/hisi_sas_main.c
index 944ce19ae2fc..cf7aa0a699cd 100644
--- a/drivers/scsi/hisi_sas/hisi_sas_main.c
+++ b/drivers/scsi/hisi_sas/hisi_sas_main.c
@@ -996,10 +996,25 @@ static void hisi_sas_phyup_pm_work(struct work_struct *work)
 	pm_runtime_put_sync(dev);
 }
 
+static void hisi_sas_spinup_notify_work(struct work_struct *work)
+{
+	struct hisi_sas_phy *phy =
+		container_of(work, typeof(*phy), works[HISI_PHYE_SPINUP_NOTIFY]);
+	struct hisi_hba *hisi_hba = phy->hisi_hba;
+	struct device *dev = hisi_hba->dev;
+	int phy_no = phy->sas_phy.id;
+
+	hisi_hba->hw->sl_notify_ssp(hisi_hba, phy_no);
+	dev_info(dev, "spinup notify primitive on phy%d\n", phy_no);
+
+	pm_runtime_put_sync(dev);
+}
+
 static const work_func_t hisi_sas_phye_fns[HISI_PHYES_NUM] = {
 	[HISI_PHYE_PHY_UP] = hisi_sas_phyup_work,
 	[HISI_PHYE_LINK_RESET] = hisi_sas_linkreset_work,
 	[HISI_PHYE_PHY_UP_PM] = hisi_sas_phyup_pm_work,
+	[HISI_PHYE_SPINUP_NOTIFY] = hisi_sas_spinup_notify_work,
 };
 
 bool hisi_sas_notify_phy_event(struct hisi_sas_phy *phy,
@@ -1639,6 +1654,34 @@ void hisi_sas_controller_reset_done(struct hisi_hba *hisi_hba)
 }
 EXPORT_SYMBOL_GPL(hisi_sas_controller_reset_done);
 
+void hisi_sas_spinup_notify(struct hisi_hba *hisi_hba,
+			    struct sas_task *task)
+{
+	struct task_status_struct *ts = &task->task_status;
+	struct domain_device *dev = task->dev;
+	struct scsi_sense_hdr sshdr;
+	struct sas_phy *local_phy;
+	struct hisi_sas_phy *phy;
+
+	if (!scsi_normalize_sense(ts->buf, ts->buf_valid_size, &sshdr))
+		return;
+
+	if (sshdr.sense_key != NOT_READY ||
+	    sshdr.sense_code != LU_NOT_READY_NOTIFY_REQUIRED)
+		return;
+
+	if (!pm_runtime_get_if_active(hisi_hba->dev))
+		return;
+
+	local_phy = sas_get_local_phy(dev);
+	phy = &hisi_hba->phy[local_phy->number];
+	if (!hisi_sas_notify_phy_event(phy, HISI_PHYE_SPINUP_NOTIFY))
+		pm_runtime_put(hisi_hba->dev);
+
+	sas_put_local_phy(local_phy);
+}
+EXPORT_SYMBOL_GPL(hisi_sas_spinup_notify);
+
 static int hisi_sas_controller_prereset(struct hisi_hba *hisi_hba)
 {
 	if (!hisi_hba->hw->soft_reset)
diff --git a/drivers/scsi/hisi_sas/hisi_sas_v1_hw.c b/drivers/scsi/hisi_sas/hisi_sas_v1_hw.c
index fa94d7110714..5fcb8d5002f5 100644
--- a/drivers/scsi/hisi_sas/hisi_sas_v1_hw.c
+++ b/drivers/scsi/hisi_sas/hisi_sas_v1_hw.c
@@ -1272,6 +1272,10 @@ static void slot_complete_v1_hw(struct hisi_hba *hisi_hba,
 				&status_buffer->iu[0];
 
 		sas_ssp_task_response(dev, task, iu);
+		if (unlikely(ts->stat == SAS_SAM_STAT_CHECK_CONDITION &&
+			     !dev_parent_is_expander(device)))
+			hisi_sas_spinup_notify(hisi_hba, task);
+
 		break;
 	}
 	case SAS_PROTOCOL_SMP:
diff --git a/drivers/scsi/hisi_sas/hisi_sas_v2_hw.c b/drivers/scsi/hisi_sas/hisi_sas_v2_hw.c
index f3516a0611dd..f16896e962fd 100644
--- a/drivers/scsi/hisi_sas/hisi_sas_v2_hw.c
+++ b/drivers/scsi/hisi_sas/hisi_sas_v2_hw.c
@@ -2427,6 +2427,10 @@ static void slot_complete_v2_hw(struct hisi_hba *hisi_hba,
 				&status_buffer->iu[0];
 
 		sas_ssp_task_response(dev, task, iu);
+		if (unlikely(ts->stat == SAS_SAM_STAT_CHECK_CONDITION &&
+			     !dev_parent_is_expander(device)))
+			hisi_sas_spinup_notify(hisi_hba, task);
+
 		break;
 	}
 	case SAS_PROTOCOL_SMP:
diff --git a/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c b/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c
index 8a2500993e19..9391d031f5df 100644
--- a/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c
+++ b/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c
@@ -280,6 +280,9 @@
 #define CHL_INT2_RX_CODE_ERR_OFF	29
 #define CHL_INT2_RX_INVLD_DW_OFF	30
 #define CHL_INT2_STP_LINK_TIMEOUT_OFF	31
+#define CHL_INT2_RX_ERR_MSK	(BIT(CHL_INT2_RX_DISP_ERR_OFF) | \
+				 BIT(CHL_INT2_RX_CODE_ERR_OFF) | \
+				 BIT(CHL_INT2_RX_INVLD_DW_OFF))
 #define CHL_INT0_MSK			(PORT_BASE + 0x1c0)
 #define CHL_INT1_MSK			(PORT_BASE + 0x1c4)
 #define CHL_INT2_MSK			(PORT_BASE + 0x1c8)
@@ -547,6 +550,9 @@ struct hisi_sas_err_record_v3 {
 #define IRQ_AXI_INDEX 11
 
 #define DELAY_FOR_RESET_HW 100
+#define STOP_PHY_DELAY_US 50
+#define DISABLE_PHY_DELAY_MS 50
+#define DISABLE_HOST_PHY_DELAY_MS 10
 #define HDR_SG_MOD 0x2
 #define LUN_SIZE 8
 #define ATTR_PRIO_REGION 9
@@ -983,7 +989,7 @@ static int reset_hw_v3_hw(struct hisi_hba *hisi_hba)
 
 	/* Disable all of the PHYs */
 	hisi_sas_stop_phys(hisi_hba);
-	udelay(HISI_SAS_DELAY_FOR_PHY_DISABLE);
+	udelay(STOP_PHY_DELAY_US);
 
 	/* Ensure axi bus idle */
 	ret = hisi_sas_read32_poll_timeout(AXI_CFG, val, !val,
@@ -1058,21 +1064,36 @@ static void enable_phy_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
 	hisi_sas_phy_write32(hisi_hba, phy_no, PHY_CFG, cfg);
 }
 
+static void clear_phy_err_cnt_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
+{
+	u32 irq_msk = hisi_sas_phy_read32(hisi_hba, phy_no, CHL_INT2_MSK);
+
+	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2_MSK,
+			     CHL_INT2_RX_ERR_MSK | irq_msk);
+
+	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_DWS_LOST);
+	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_RESET_PROB);
+	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_INVLD_DW);
+	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_DISP_ERR);
+	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_CODE_ERR);
+
+	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2, CHL_INT2_RX_ERR_MSK);
+	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2_MSK, irq_msk);
+}
+
 static void disable_phy_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
 {
 	u32 cfg = hisi_sas_phy_read32(hisi_hba, phy_no, PHY_CFG);
 	u32 irq_msk = hisi_sas_phy_read32(hisi_hba, phy_no, CHL_INT2_MSK);
-	static const u32 msk = BIT(CHL_INT2_RX_DISP_ERR_OFF) |
-			       BIT(CHL_INT2_RX_CODE_ERR_OFF) |
-			       BIT(CHL_INT2_RX_INVLD_DW_OFF);
 	u32 state;
 
-	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2_MSK, msk | irq_msk);
+	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2_MSK,
+			     CHL_INT2_RX_ERR_MSK | irq_msk);
 
 	cfg &= ~PHY_CFG_ENA_MSK;
 	hisi_sas_phy_write32(hisi_hba, phy_no, PHY_CFG, cfg);
 
-	mdelay(HISI_SAS_DELAY_FOR_PHY_DISABLE);
+	mdelay(DISABLE_PHY_DELAY_MS);
 
 	state = hisi_sas_read32(hisi_hba, PHY_STATE);
 	if (state & BIT(phy_no)) {
@@ -1082,11 +1103,7 @@ static void disable_phy_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
 
 	udelay(1);
 
-	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_INVLD_DW);
-	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_DISP_ERR);
-	hisi_sas_phy_read32(hisi_hba, phy_no, ERR_CNT_CODE_ERR);
-
-	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2, msk);
+	clear_phy_err_cnt_v3_hw(hisi_hba, phy_no);
 	hisi_sas_phy_write32(hisi_hba, phy_no, CHL_INT2_MSK, irq_msk);
 }
 
@@ -1668,6 +1685,7 @@ static irqreturn_t phy_up_v3_hw(int phy_no, struct hisi_hba *hisi_hba)
 	/* Delete timer and set phy_attached atomically */
 	timer_delete(&phy->timer);
 	phy->phy_attached = 1;
+	clear_phy_err_cnt_v3_hw(hisi_hba, phy_no);
 	spin_unlock(&phy->lock);
 
 	/*
@@ -1891,9 +1909,6 @@ static void handle_chl_int2_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
 	struct hisi_sas_phy *phy = &hisi_hba->phy[phy_no];
 	struct pci_dev *pci_dev = hisi_hba->pci_dev;
 	struct device *dev = hisi_hba->dev;
-	static const u32 msk = BIT(CHL_INT2_RX_DISP_ERR_OFF) |
-			BIT(CHL_INT2_RX_CODE_ERR_OFF) |
-			BIT(CHL_INT2_RX_INVLD_DW_OFF);
 
 	irq_value &= ~irq_msk;
 	if (!irq_value) {
@@ -1917,7 +1932,7 @@ static void handle_chl_int2_v3_hw(struct hisi_hba *hisi_hba, int phy_no)
 			hisi_sas_notify_phy_event(phy, HISI_PHYE_LINK_RESET);
 	}
 
-	if (pci_dev->revision > 0x20 && (irq_value & msk)) {
+	if (pci_dev->revision > 0x20 && (irq_value & CHL_INT2_RX_ERR_MSK)) {
 		struct asd_sas_phy *sas_phy = &phy->sas_phy;
 		struct sas_phy *sphy = sas_phy->phy;
 
@@ -2432,6 +2447,10 @@ static void slot_complete_v3_hw(struct hisi_hba *hisi_hba,
 			sizeof(struct hisi_sas_err_record);
 
 		sas_ssp_task_response(dev, task, iu);
+		if (unlikely(ts->stat == SAS_SAM_STAT_CHECK_CONDITION &&
+			     !dev_parent_is_expander(device)))
+			hisi_sas_spinup_notify(hisi_hba, task);
+
 		break;
 	}
 	case SAS_PROTOCOL_SMP: {
@@ -2755,7 +2774,7 @@ static int disable_host_v3_hw(struct hisi_hba *hisi_hba)
 
 	hisi_sas_stop_phys(hisi_hba);
 
-	mdelay(HISI_SAS_DELAY_FOR_PHY_DISABLE);
+	mdelay(DISABLE_HOST_PHY_DELAY_MS);
 
 	reg_val = hisi_sas_read32(hisi_hba, AXI_MASTER_CFG_BASE +
 				  AM_CTRL_GLOBAL);
diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c
index 4009edcfd2b1..187505950b63 100644
--- a/drivers/scsi/hpsa.c
+++ b/drivers/scsi/hpsa.c
@@ -3166,7 +3166,7 @@ static int hpsa_do_reset(struct ctlr_info *h, struct hpsa_scsi_dev_t *dev,
 	int rc = 0;
 
 	/* We can really only handle one reset at a time */
-	if (mutex_lock_interruptible(&h->reset_mutex) == -EINTR) {
+	if (mutex_lock_interruptible(&h->reset_mutex)) {
 		dev_warn(&h->pdev->dev, "concurrent reset wait interrupted.\n");
 		return -EINTR;
 	}
diff --git a/drivers/scsi/ibmvscsi/Makefile b/drivers/scsi/ibmvscsi/Makefile
index 9408c7f4cdee..de6ed9e64b63 100644
--- a/drivers/scsi/ibmvscsi/Makefile
+++ b/drivers/scsi/ibmvscsi/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 ibmvfc-objs := ibmvfc-core.o ibmvfc-nvme.o
 
 obj-$(CONFIG_SCSI_IBMVSCSI)	+= ibmvscsi.o
diff --git a/drivers/scsi/ibmvscsi_tgt/Makefile b/drivers/scsi/ibmvscsi_tgt/Makefile
index cc7a8256dcf8..7ae12ee9a347 100644
--- a/drivers/scsi/ibmvscsi_tgt/Makefile
+++ b/drivers/scsi/ibmvscsi_tgt/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_IBMVSCSIS)	+= ibmvscsis.o
 
 ibmvscsis-y := libsrp.o ibmvscsi_tgt.o
diff --git a/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c b/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c
index e2af90b6da39..92b26f7fec50 100644
--- a/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c
+++ b/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c
@@ -219,6 +219,7 @@ static long ibmvscsis_unregister_command_q(struct scsi_info *vscsi)
  */
 static void ibmvscsis_delete_client_info(struct scsi_info *vscsi,
 					 bool client_closed)
+	__must_hold(&vscsi->intr_lock)
 {
 	vscsi->client_cap = 0;
 
@@ -251,6 +252,7 @@ static void ibmvscsis_delete_client_info(struct scsi_info *vscsi,
  *	Process level, interrupt lock is held
  */
 static long ibmvscsis_free_command_q(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	int bytes;
 	u32 flags_under_lock;
@@ -329,6 +331,7 @@ static struct viosrp_crq *ibmvscsis_cmd_q_dequeue(uint mask,
  *	Interrupt environment interrupt lock held
  */
 static long ibmvscsis_send_init_message(struct scsi_info *vscsi, u8 format)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_crq *crq;
 	u64 buffer[2] = { 0, 0 };
@@ -356,6 +359,7 @@ static long ibmvscsis_send_init_message(struct scsi_info *vscsi, u8 format)
  *	Process level only, interrupt lock held
  */
 static long ibmvscsis_check_init_msg(struct scsi_info *vscsi, uint *format)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_crq *crq;
 	long rc = ADAPT_SUCCESS;
@@ -571,6 +575,7 @@ static void ibmvscsis_disconnect(struct work_struct *work)
  */
 static void ibmvscsis_post_disconnect(struct scsi_info *vscsi, uint new_state,
 				      uint flag_bits)
+	__must_hold(&vscsi->intr_lock)
 {
 	uint state;
 
@@ -652,6 +657,7 @@ static void ibmvscsis_post_disconnect(struct scsi_info *vscsi, uint new_state,
  * Must be called with interrupt lock held.
  */
 static long ibmvscsis_handle_init_compl_msg(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 
@@ -691,6 +697,7 @@ static long ibmvscsis_handle_init_compl_msg(struct scsi_info *vscsi)
  * Must be called with interrupt lock held.
  */
 static long ibmvscsis_handle_init_msg(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 
@@ -759,6 +766,7 @@ static long ibmvscsis_handle_init_msg(struct scsi_info *vscsi)
  *	Interrupt, interrupt lock held
  */
 static long ibmvscsis_init_msg(struct scsi_info *vscsi, struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 
@@ -798,6 +806,7 @@ static long ibmvscsis_init_msg(struct scsi_info *vscsi, struct viosrp_crq *crq)
  * Must be called with interrupt lock held.
  */
 static long ibmvscsis_establish_new_q(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 	uint format;
@@ -874,6 +883,7 @@ static long ibmvscsis_establish_new_q(struct scsi_info *vscsi)
  *	Process environment, called with interrupt lock held
  */
 static void ibmvscsis_reset_queue(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	int bytes;
 	long rc = ADAPT_SUCCESS;
@@ -924,6 +934,7 @@ static void ibmvscsis_reset_queue(struct scsi_info *vscsi)
  */
 static void ibmvscsis_free_cmd_resources(struct scsi_info *vscsi,
 					 struct ibmvscsis_cmd *cmd)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 
@@ -974,6 +985,7 @@ static void ibmvscsis_free_cmd_resources(struct scsi_info *vscsi,
  *	Process or interrupt environment called with interrupt lock held
  */
 static long ibmvscsis_ready_for_suspend(struct scsi_info *vscsi, bool idle)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = 0;
 	struct viosrp_crq *crq;
@@ -1030,6 +1042,7 @@ static long ibmvscsis_ready_for_suspend(struct scsi_info *vscsi, bool idle)
  */
 static long ibmvscsis_trans_event(struct scsi_info *vscsi,
 				  struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 
@@ -1166,6 +1179,7 @@ static long ibmvscsis_trans_event(struct scsi_info *vscsi,
  *	intr_lock must be held
  */
 static void ibmvscsis_poll_cmd_q(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_crq *crq;
 	long rc;
@@ -1252,6 +1266,7 @@ static void ibmvscsis_poll_cmd_q(struct scsi_info *vscsi)
  *	Called with interrupt lock held
  */
 static void ibmvscsis_free_cmd_qs(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct ibmvscsis_cmd *cmd, *nxt;
 
@@ -1272,6 +1287,7 @@ static void ibmvscsis_free_cmd_qs(struct scsi_info *vscsi)
  * Must be called with interrupt lock held.
  */
 static struct ibmvscsis_cmd *ibmvscsis_get_free_cmd(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct ibmvscsis_cmd *cmd = NULL;
 	struct iu_entry *iue;
@@ -1310,6 +1326,7 @@ static struct ibmvscsis_cmd *ibmvscsis_get_free_cmd(struct scsi_info *vscsi)
  *	Process environment called with interrupt lock held
  */
 static void ibmvscsis_adapter_idle(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	int free_qs = false;
 	long rc = 0;
@@ -1441,6 +1458,7 @@ static void ibmvscsis_adapter_idle(struct scsi_info *vscsi)
 static long ibmvscsis_copy_crq_packet(struct scsi_info *vscsi,
 				      struct ibmvscsis_cmd *cmd,
 				      struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	long rc = 0;
@@ -1500,6 +1518,7 @@ static long ibmvscsis_copy_crq_packet(struct scsi_info *vscsi,
  */
 static long ibmvscsis_adapter_info(struct scsi_info *vscsi,
 				   struct iu_entry *iue)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_adapter_info *mad = &vio_iu(iue)->mad.adapter_info;
 	struct mad_adapter_info_data *info;
@@ -1611,6 +1630,7 @@ static long ibmvscsis_adapter_info(struct scsi_info *vscsi,
  *	Interrupt called with adapter lock held
  */
 static int ibmvscsis_cap_mad(struct scsi_info *vscsi, struct iu_entry *iue)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_capabilities *mad = &vio_iu(iue)->mad.capabilities;
 	struct capabilities *cap;
@@ -1725,6 +1745,7 @@ static int ibmvscsis_cap_mad(struct scsi_info *vscsi, struct iu_entry *iue)
  * Must be called with interrupt lock held.
  */
 static long ibmvscsis_process_mad(struct scsi_info *vscsi, struct iu_entry *iue)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct mad_common *mad = (struct mad_common *)&vio_iu(iue)->mad;
 	struct viosrp_empty_iu *empty;
@@ -1768,6 +1789,7 @@ static long ibmvscsis_process_mad(struct scsi_info *vscsi, struct iu_entry *iue)
  * Must be called with interrupt lock held.
  */
 static void srp_snd_msg_failed(struct scsi_info *vscsi, long rc)
+	__must_hold(&vscsi->intr_lock)
 {
 	ktime_t kt;
 
@@ -1871,6 +1893,7 @@ static void srp_snd_msg_failed(struct scsi_info *vscsi, long rc)
  *	Called with interrupt lock held
  */
 static void ibmvscsis_send_messages(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_crq empty_crq = { };
 	struct viosrp_crq *crq = &empty_crq;
@@ -1979,6 +2002,7 @@ static void ibmvscsis_send_messages(struct scsi_info *vscsi)
 static void ibmvscsis_send_mad_resp(struct scsi_info *vscsi,
 				    struct ibmvscsis_cmd *cmd,
 				    struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	struct mad_common *mad = (struct mad_common *)&vio_iu(iue)->mad;
@@ -2021,6 +2045,7 @@ static void ibmvscsis_send_mad_resp(struct scsi_info *vscsi,
  *	Interrupt, called with adapter lock held
  */
 static long ibmvscsis_mad(struct scsi_info *vscsi, struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue;
 	struct ibmvscsis_cmd *cmd;
@@ -2097,6 +2122,7 @@ static long ibmvscsis_mad(struct scsi_info *vscsi, struct viosrp_crq *crq)
  */
 static long ibmvscsis_login_rsp(struct scsi_info *vscsi,
 				struct ibmvscsis_cmd *cmd)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	struct srp_login_rsp *rsp = &vio_iu(iue)->srp.login_rsp;
@@ -2157,6 +2183,7 @@ static long ibmvscsis_login_rsp(struct scsi_info *vscsi,
  */
 static long ibmvscsis_srp_login_rej(struct scsi_info *vscsi,
 				    struct ibmvscsis_cmd *cmd, u32 reason)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	struct srp_login_rej *rej = &vio_iu(iue)->srp.login_rej;
@@ -2272,6 +2299,7 @@ static int ibmvscsis_drop_nexus(struct ibmvscsis_tport *tport)
 static long ibmvscsis_srp_login(struct scsi_info *vscsi,
 				struct ibmvscsis_cmd *cmd,
 				struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	struct srp_login_req *req = &vio_iu(iue)->srp.login_req;
@@ -2346,6 +2374,7 @@ static long ibmvscsis_srp_login(struct scsi_info *vscsi,
 static long ibmvscsis_srp_i_logout(struct scsi_info *vscsi,
 				   struct ibmvscsis_cmd *cmd,
 				   struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct iu_entry *iue = cmd->iue;
 	struct srp_i_logout *log_out = &vio_iu(iue)->srp.i_logout;
@@ -2367,8 +2396,8 @@ static long ibmvscsis_srp_i_logout(struct scsi_info *vscsi,
 	return ADAPT_SUCCESS;
 }
 
-/* Called with intr lock held */
 static void ibmvscsis_srp_cmd(struct scsi_info *vscsi, struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct ibmvscsis_cmd *cmd;
 	struct iu_entry *iue;
@@ -2469,6 +2498,7 @@ static void ibmvscsis_srp_cmd(struct scsi_info *vscsi, struct viosrp_crq *crq)
  *	Interrupt, interrupt lock held
  */
 static long ibmvscsis_ping_response(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	struct viosrp_crq *crq;
 	u64 buffer[2] = { 0, 0 };
@@ -2520,6 +2550,7 @@ static long ibmvscsis_ping_response(struct scsi_info *vscsi)
  */
 static long ibmvscsis_parse_command(struct scsi_info *vscsi,
 				    struct viosrp_crq *crq)
+	__must_hold(&vscsi->intr_lock)
 {
 	long rc = ADAPT_SUCCESS;
 
@@ -2961,6 +2992,7 @@ static irqreturn_t ibmvscsis_interrupt(int dummy, void *data)
  * Must be called with interrupt lock held.
  */
 static long ibmvscsis_enable_change_state(struct scsi_info *vscsi)
+	__must_hold(&vscsi->intr_lock)
 {
 	int bytes;
 	long rc = ADAPT_SUCCESS;
diff --git a/drivers/scsi/ipr.c b/drivers/scsi/ipr.c
index 1c74eec3a0c0..a68ec85a7780 100644
--- a/drivers/scsi/ipr.c
+++ b/drivers/scsi/ipr.c
@@ -1006,6 +1006,7 @@ static void ipr_init_ioadl(struct ipr_cmnd *ipr_cmd, dma_addr_t dma_addr,
 
 /**
  * ipr_send_blocking_cmd - Send command and sleep on its completion.
+ * @host:	SCSI host
  * @ipr_cmd:	ipr command struct
  * @timeout_func:	function to invoke if command times out
  * @timeout:	timeout
@@ -1013,18 +1014,17 @@ static void ipr_init_ioadl(struct ipr_cmnd *ipr_cmd, dma_addr_t dma_addr,
  * Return value:
  * 	none
  **/
-static void ipr_send_blocking_cmd(struct ipr_cmnd *ipr_cmd,
+static void ipr_send_blocking_cmd(struct Scsi_Host *host, struct ipr_cmnd *ipr_cmd,
 				  void (*timeout_func) (struct timer_list *),
 				  u32 timeout)
+	__must_hold(&host->host_lock)
 {
-	struct ipr_ioa_cfg *ioa_cfg = ipr_cmd->ioa_cfg;
-
 	init_completion(&ipr_cmd->completion);
 	ipr_do_req(ipr_cmd, ipr_internal_cmd_done, timeout_func, timeout);
 
-	spin_unlock_irq(&ioa_cfg->host->host_lock);
+	spin_unlock_irq(&host->host_lock);
 	wait_for_completion(&ipr_cmd->completion);
-	spin_lock_irq(&ioa_cfg->host->host_lock);
+	spin_lock_irq(&host->host_lock);
 }
 
 static int ipr_get_hrrq_index(struct ipr_ioa_cfg *ioa_cfg)
@@ -5000,7 +5000,8 @@ static int ipr_eh_host_reset(struct scsi_cmnd *cmd)
 /**
  * ipr_device_reset - Reset the device
  * @ioa_cfg:	ioa config struct
- * @res:		resource entry struct
+ * @host:	scsi host struct
+ * @res:	resource entry struct
  *
  * This function issues a device reset to the affected device.
  * If the device is a SCSI device, a LUN reset will be sent
@@ -5011,7 +5012,9 @@ static int ipr_eh_host_reset(struct scsi_cmnd *cmd)
  *	0 on success / non-zero on failure
  **/
 static int ipr_device_reset(struct ipr_ioa_cfg *ioa_cfg,
+			    struct Scsi_Host *host,
 			    struct ipr_resource_entry *res)
+	__must_hold(&host->host_lock)
 {
 	struct ipr_cmnd *ipr_cmd;
 	struct ipr_ioarcb *ioarcb;
@@ -5030,7 +5033,8 @@ static int ipr_device_reset(struct ipr_ioa_cfg *ioa_cfg,
 	cmd_pkt->request_type = IPR_RQTYPE_IOACMD;
 	cmd_pkt->cdb[0] = IPR_RESET_DEVICE;
 
-	ipr_send_blocking_cmd(ipr_cmd, ipr_timeout, IPR_DEVICE_RESET_TIMEOUT);
+	ipr_send_blocking_cmd(host, ipr_cmd, ipr_timeout,
+			      IPR_DEVICE_RESET_TIMEOUT);
 	ioasc = be32_to_cpu(ipr_cmd->s.ioasa.hdr.ioasc);
 	list_add_tail(&ipr_cmd->queue, &ipr_cmd->hrrq->hrrq_free_q);
 
@@ -5040,6 +5044,7 @@ static int ipr_device_reset(struct ipr_ioa_cfg *ioa_cfg,
 
 /**
  * __ipr_eh_dev_reset - Reset the device
+ * @host:	scsi host struct
  * @scsi_cmd:	scsi command struct
  *
  * This function issues a device reset to the affected device.
@@ -5049,14 +5054,15 @@ static int ipr_device_reset(struct ipr_ioa_cfg *ioa_cfg,
  * Return value:
  *	SUCCESS / FAILED
  **/
-static int __ipr_eh_dev_reset(struct scsi_cmnd *scsi_cmd)
+static int __ipr_eh_dev_reset(struct Scsi_Host *host, struct scsi_cmnd *scsi_cmd)
+	__must_hold(&host->host_lock)
 {
 	struct ipr_ioa_cfg *ioa_cfg;
 	struct ipr_resource_entry *res;
 	int rc = 0;
 
 	ENTER;
-	ioa_cfg = (struct ipr_ioa_cfg *) scsi_cmd->device->host->hostdata;
+	ioa_cfg = (struct ipr_ioa_cfg *) host->hostdata;
 	res = scsi_cmd->device->hostdata;
 
 	/*
@@ -5072,7 +5078,7 @@ static int __ipr_eh_dev_reset(struct scsi_cmnd *scsi_cmd)
 	res->resetting_device = 1;
 	scmd_printk(KERN_ERR, scsi_cmd, "Resetting device\n");
 
-	rc = ipr_device_reset(ioa_cfg, res);
+	rc = ipr_device_reset(ioa_cfg, host, res);
 	res->resetting_device = 0;
 	res->reset_occurred = 1;
 
@@ -5085,16 +5091,17 @@ static int ipr_eh_dev_reset(struct scsi_cmnd *cmd)
 	int rc;
 	struct ipr_ioa_cfg *ioa_cfg;
 	struct ipr_resource_entry *res;
+	struct Scsi_Host *host = cmd->device->host;
 
-	ioa_cfg = (struct ipr_ioa_cfg *) cmd->device->host->hostdata;
+	ioa_cfg = (struct ipr_ioa_cfg *) host->hostdata;
 	res = cmd->device->hostdata;
 
 	if (!res)
 		return FAILED;
 
-	spin_lock_irq(&cmd->device->host->host_lock);
-	rc = __ipr_eh_dev_reset(cmd);
-	spin_unlock_irq(&cmd->device->host->host_lock);
+	spin_lock_irq(&host->host_lock);
+	rc = __ipr_eh_dev_reset(host, cmd);
+	spin_unlock_irq(&host->host_lock);
 
 	if (rc == SUCCESS)
 		rc = ipr_wait_for_ops(ioa_cfg, cmd->device, ipr_match_lun);
@@ -5189,7 +5196,9 @@ static void ipr_abort_timeout(struct timer_list *t)
  *	SUCCESS / FAILED
  **/
 static int ipr_cancel_op(struct scsi_cmnd *scsi_cmd)
+	__must_hold(&scsi_cmd->device->host->host_lock)
 {
+	struct Scsi_Host *host = scsi_cmd->device->host;
 	struct ipr_cmnd *ipr_cmd;
 	struct ipr_ioa_cfg *ioa_cfg;
 	struct ipr_resource_entry *res;
@@ -5199,7 +5208,7 @@ static int ipr_cancel_op(struct scsi_cmnd *scsi_cmd)
 	struct ipr_hrr_queue *hrrq;
 
 	ENTER;
-	ioa_cfg = (struct ipr_ioa_cfg *)scsi_cmd->device->host->hostdata;
+	ioa_cfg = (struct ipr_ioa_cfg *)host->hostdata;
 	res = scsi_cmd->device->hostdata;
 
 	/* If we are currently going through reset/reload, return failed.
@@ -5247,7 +5256,8 @@ static int ipr_cancel_op(struct scsi_cmnd *scsi_cmd)
 
 	scmd_printk(KERN_ERR, scsi_cmd, "Aborting command: %02X\n",
 		    scsi_cmd->cmnd[0]);
-	ipr_send_blocking_cmd(ipr_cmd, ipr_abort_timeout, IPR_CANCEL_ALL_TIMEOUT);
+	ipr_send_blocking_cmd(host, ipr_cmd, ipr_abort_timeout,
+			      IPR_CANCEL_ALL_TIMEOUT);
 	ioasc = be32_to_cpu(ipr_cmd->s.ioasa.hdr.ioasc);
 
 	/*
@@ -5299,17 +5309,17 @@ static int ipr_scan_finished(struct Scsi_Host *shost, unsigned long elapsed_time
  **/
 static int ipr_eh_abort(struct scsi_cmnd *scsi_cmd)
 {
+	struct Scsi_Host *host = scsi_cmd->device->host;
+	struct ipr_ioa_cfg *ioa_cfg = (void *)host->hostdata;
 	unsigned long flags;
 	int rc;
-	struct ipr_ioa_cfg *ioa_cfg;
 
 	ENTER;
 
-	ioa_cfg = (struct ipr_ioa_cfg *) scsi_cmd->device->host->hostdata;
 
-	spin_lock_irqsave(&scsi_cmd->device->host->host_lock, flags);
+	spin_lock_irqsave(&host->host_lock, flags);
 	rc = ipr_cancel_op(scsi_cmd);
-	spin_unlock_irqrestore(&scsi_cmd->device->host->host_lock, flags);
+	spin_unlock_irqrestore(&host->host_lock, flags);
 
 	if (rc == SUCCESS)
 		rc = ipr_wait_for_ops(ioa_cfg, scsi_cmd->device, ipr_match_lun);
diff --git a/drivers/scsi/ips.c b/drivers/scsi/ips.c
index 45c5b9acb664..c7d6c5aae340 100644
--- a/drivers/scsi/ips.c
+++ b/drivers/scsi/ips.c
@@ -2506,6 +2506,7 @@ ips_hainit(ips_ha_t * ha)
 /****************************************************************************/
 static void
 ips_next(ips_ha_t * ha, int intr)
+	__context_unsafe(/*conditional locking*/)
 {
 	ips_scb_t *scb;
 	struct scsi_cmnd *SC;
diff --git a/drivers/scsi/isci/Makefile b/drivers/scsi/isci/Makefile
index da6f04cae272..00fd5c1a8d39 100644
--- a/drivers/scsi/isci/Makefile
+++ b/drivers/scsi/isci/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_ISCI) += isci.o
 isci-objs := init.o phy.o request.o \
 	     remote_device.o port.o \
diff --git a/drivers/scsi/leapraid/leapraid_func.h b/drivers/scsi/leapraid/leapraid_func.h
index 879d8cd5ec03..a16390a71662 100644
--- a/drivers/scsi/leapraid/leapraid_func.h
+++ b/drivers/scsi/leapraid/leapraid_func.h
@@ -547,7 +547,6 @@ struct leapraid_fw_evt_work {
 /**
  * struct leapraid_fw_evt_struct - Firmware event handling structure
  *
- * @fw_evt_name: Name of the firmware event.
  * @fw_evt_thread: Workqueue used for processing firmware events.
  * @fw_evt_lock: Spinlock protecting access to the firmware event list.
  * @fw_evt_list: Linked list of pending firmware events.
@@ -558,7 +557,6 @@ struct leapraid_fw_evt_work {
  */
 struct leapraid_fw_evt_struct {
 	u32 leapraid_evt_masks[4];
-	char fw_evt_name[48];
 	struct workqueue_struct *fw_evt_thread;
 	spinlock_t fw_evt_lock; /* protects firmware event */
 	struct list_head fw_evt_list;
diff --git a/drivers/scsi/leapraid/leapraid_os.c b/drivers/scsi/leapraid/leapraid_os.c
index eb8b11439923..da597eb99377 100644
--- a/drivers/scsi/leapraid/leapraid_os.c
+++ b/drivers/scsi/leapraid/leapraid_os.c
@@ -2053,12 +2053,10 @@ static int leapraid_probe(struct pci_dev *pdev, const struct pci_device_id *id)
 	shost->transportt = leapraid_transport_template;
 	shost->unique_id = adapter->adapter_attr.id;
 
-	snprintf(adapter->fw_evt_s.fw_evt_name,
-		 sizeof(adapter->fw_evt_s.fw_evt_name),
-		 "fw_event_%s%d", LEAPRAID_DRIVER_NAME,
-		 adapter->adapter_attr.id);
 	adapter->fw_evt_s.fw_evt_thread =
-		alloc_ordered_workqueue(adapter->fw_evt_s.fw_evt_name, 0);
+		alloc_ordered_workqueue("fw_event_%s%d", 0,
+					LEAPRAID_DRIVER_NAME,
+					adapter->adapter_attr.id);
 	if (!adapter->fw_evt_s.fw_evt_thread) {
 		dev_err(&adapter->pdev->dev,
 			"%s: Failed to create fw event workqueue\n", __func__);
diff --git a/drivers/scsi/libfc/Makefile b/drivers/scsi/libfc/Makefile
index 65396f86c307..b265cf2a84a2 100644
--- a/drivers/scsi/libfc/Makefile
+++ b/drivers/scsi/libfc/Makefile
@@ -1,6 +1,8 @@
 # SPDX-License-Identifier: GPL-2.0
 # $Id: Makefile
 
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_LIBFC) += libfc.o
 
 libfc-objs := \
diff --git a/drivers/scsi/libfc/fc_disc.c b/drivers/scsi/libfc/fc_disc.c
index 7792724d5b97..ce230a67a082 100644
--- a/drivers/scsi/libfc/fc_disc.c
+++ b/drivers/scsi/libfc/fc_disc.c
@@ -37,7 +37,7 @@
 #define FC_DISC_RETRY_LIMIT	3	/* max retries */
 #define FC_DISC_RETRY_DELAY	500UL	/* (msecs) delay */
 
-static void fc_disc_gpn_ft_req(struct fc_disc *);
+static void fc_disc_gpn_ft_req(struct fc_disc *disc) __must_hold(&disc->disc_mutex);
 static void fc_disc_gpn_ft_resp(struct fc_seq *, struct fc_frame *, void *);
 static void fc_disc_done(struct fc_disc *, enum fc_disc_event);
 static void fc_disc_timeout(struct work_struct *);
@@ -68,6 +68,7 @@ static void fc_disc_stop_rports(struct fc_disc *disc)
  * @fp:	   The RSCN frame
  */
 static void fc_disc_recv_rscn_req(struct fc_disc *disc, struct fc_frame *fp)
+	__must_hold(&disc->disc_mutex)
 {
 	struct fc_lport *lport;
 	struct fc_els_rscn *rp;
@@ -200,6 +201,7 @@ static void fc_disc_recv_req(struct fc_lport *lport, struct fc_frame *fp)
  * @disc: The discovery object to be restarted
  */
 static void fc_disc_restart(struct fc_disc *disc)
+	__must_hold(&disc->disc_mutex)
 {
 	lockdep_assert_held(&disc->disc_mutex);
 
@@ -250,6 +252,7 @@ static void fc_disc_start(void (*disc_callback)(struct fc_lport *,
  * @event: The discovery completion status
  */
 static void fc_disc_done(struct fc_disc *disc, enum fc_disc_event event)
+	__must_hold(&disc->disc_mutex)
 {
 	struct fc_lport *lport = fc_disc_lport(disc);
 	struct fc_rport_priv *rdata;
@@ -294,6 +297,7 @@ static void fc_disc_done(struct fc_disc *disc, enum fc_disc_event event)
  * @fp:	  The error code encoded as a frame pointer
  */
 static void fc_disc_error(struct fc_disc *disc, struct fc_frame *fp)
+	__must_hold(&disc->disc_mutex)
 {
 	struct fc_lport *lport = fc_disc_lport(disc);
 	unsigned long delay = 0;
@@ -374,6 +378,7 @@ static void fc_disc_gpn_ft_req(struct fc_disc *disc)
  * Goes through the list of IDs and names resulting from a request.
  */
 static int fc_disc_gpn_ft_parse(struct fc_disc *disc, void *buf, size_t len)
+	__must_hold(&disc->disc_mutex)
 {
 	struct fc_lport *lport;
 	struct fc_gpn_ft_resp *np;
diff --git a/drivers/scsi/libfc/fc_exch.c b/drivers/scsi/libfc/fc_exch.c
index 9183a0e9568a..ba2530386f97 100644
--- a/drivers/scsi/libfc/fc_exch.c
+++ b/drivers/scsi/libfc/fc_exch.c
@@ -811,6 +811,7 @@ static void fc_exch_timeout(struct work_struct *work)
  */
 static struct fc_exch *fc_exch_em_alloc(struct fc_lport *lport,
 					struct fc_exch_mgr *mp)
+	__context_unsafe(/*conditionally acquires &_res->ex_lock*/)
 {
 	struct fc_exch *ep;
 	unsigned int cpu;
@@ -904,6 +905,7 @@ static struct fc_exch *fc_exch_em_alloc(struct fc_lport *lport,
  */
 static struct fc_exch *fc_exch_alloc(struct fc_lport *lport,
 				     struct fc_frame *fp)
+	__context_unsafe(/*conditionally acquires &_res->ex_lock*/)
 {
 	struct fc_exch_mgr_anchor *ema;
 	struct fc_exch *ep;
@@ -996,6 +998,8 @@ static struct fc_exch *fc_exch_resp(struct fc_lport *lport,
 
 	ep = fc_exch_alloc(lport, fp);
 	if (ep) {
+		/* Acquired by fc_exch_alloc(). */
+		__acquire(&ep->ex_lock);
 		ep->class = fc_frame_class(fp);
 
 		/*
@@ -2191,6 +2195,8 @@ struct fc_seq *fc_exch_seq_send(struct fc_lport *lport,
 		fc_frame_free(fp);
 		return NULL;
 	}
+	/* Acquired by fc_exch_alloc(). */
+	__acquire(&ep->ex_lock);
 	ep->esb_stat |= ESB_ST_SEQ_INIT;
 	fh = fc_frame_header_get(fp);
 	fc_exch_set_addr(ep, ntoh24(fh->fh_s_id), ntoh24(fh->fh_d_id));
diff --git a/drivers/scsi/libfc/fc_fcp.c b/drivers/scsi/libfc/fc_fcp.c
index 60a675aa5a99..dbd5673e2885 100644
--- a/drivers/scsi/libfc/fc_fcp.c
+++ b/drivers/scsi/libfc/fc_fcp.c
@@ -77,7 +77,8 @@ struct fc_fcp_internal {
 static void fc_fcp_recv_data(struct fc_fcp_pkt *, struct fc_frame *);
 static void fc_fcp_recv(struct fc_seq *, struct fc_frame *, void *);
 static void fc_fcp_resp(struct fc_fcp_pkt *, struct fc_frame *);
-static void fc_fcp_complete_locked(struct fc_fcp_pkt *);
+static void fc_fcp_complete_locked(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock);
 static void fc_tm_done(struct fc_seq *, struct fc_frame *, void *);
 static void fc_fcp_error(struct fc_fcp_pkt *, struct fc_frame *);
 static void fc_fcp_recovery(struct fc_fcp_pkt *, u8 code);
@@ -207,6 +208,7 @@ static void fc_fcp_pkt_destroy(struct fc_seq *seq, void *fsp)
  * needed.
  */
 static inline int fc_fcp_lock_pkt(struct fc_fcp_pkt *fsp)
+	__cond_acquires(0, &fsp->scsi_pkt_lock)
 {
 	spin_lock_bh(&fsp->scsi_pkt_lock);
 	if (fsp->state & FC_SRB_COMPL) {
@@ -224,6 +226,7 @@ static inline int fc_fcp_lock_pkt(struct fc_fcp_pkt *fsp)
  * @fsp: The FCP packet to be unlocked and decremented
  */
 static inline void fc_fcp_unlock_pkt(struct fc_fcp_pkt *fsp)
+	__releases(&fsp->scsi_pkt_lock)
 {
 	spin_unlock_bh(&fsp->scsi_pkt_lock);
 	fc_fcp_pkt_release(fsp);
@@ -243,6 +246,7 @@ static void fc_fcp_timer_set(struct fc_fcp_pkt *fsp, unsigned long delay)
 }
 
 static void fc_fcp_abort_done(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	fsp->state |= FC_SRB_ABORTED;
 	fsp->state &= ~FC_SRB_ABORT_PENDING;
@@ -259,6 +263,7 @@ static void fc_fcp_abort_done(struct fc_fcp_pkt *fsp)
  * @fsp: The FCP packet to abort exchanges on
  */
 static int fc_fcp_send_abort(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	int rc;
 
@@ -296,6 +301,7 @@ static int fc_fcp_send_abort(struct fc_fcp_pkt *fsp)
  * The SCSI-ml will retry the command.
  */
 static void fc_fcp_retry_cmd(struct fc_fcp_pkt *fsp, int status_code)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	if (fsp->seq_ptr) {
 		fc_exch_done(fsp->seq_ptr);
@@ -470,6 +476,7 @@ static inline unsigned int get_fsp_rec_tov(struct fc_fcp_pkt *fsp)
  * @fp:	 The data frame
  */
 static void fc_fcp_recv_data(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct scsi_cmnd *sc = fsp->cmd;
 	struct fc_lport *lport = fsp->lp;
@@ -588,6 +595,7 @@ static void fc_fcp_recv_data(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
  */
 static int fc_fcp_send_data(struct fc_fcp_pkt *fsp, struct fc_seq *seq,
 			    size_t offset, size_t seq_blen)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct fc_exch *ep;
 	struct scsi_cmnd *sc;
@@ -734,6 +742,7 @@ static int fc_fcp_send_data(struct fc_fcp_pkt *fsp, struct fc_seq *seq,
  * @fp:	 The response frame
  */
 static void fc_fcp_abts_resp(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	int ba_done = 1;
 	struct fc_ba_rjt *brp;
@@ -846,6 +855,7 @@ static void fc_fcp_recv(struct fc_seq *seq, struct fc_frame *fp, void *arg)
  * @fp:	 The response frame
  */
 static void fc_fcp_resp(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct fc_frame_header *fh;
 	struct fcp_resp *fc_rp;
@@ -1242,6 +1252,7 @@ static void fc_fcp_error(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
  * Called to send an abort and then wait for abort completion
  */
 static int fc_fcp_pkt_abort(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	int rc = FAILED;
 	unsigned long ticks_left;
@@ -1453,6 +1464,7 @@ static void fc_fcp_timeout(struct timer_list *t)
  * @fsp: The FCP packet to send the REC request on
  */
 static void fc_fcp_rec(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct fc_lport *lport;
 	struct fc_frame *fp;
@@ -1690,6 +1702,7 @@ static void fc_fcp_rec_error(struct fc_fcp_pkt *fsp, struct fc_frame *fp)
  * @code: The FCP status code to set
  */
 static void fc_fcp_recovery(struct fc_fcp_pkt *fsp, u8 code)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	FC_FCP_DBG(fsp, "start recovery code %x\n", code);
 	fsp->status_code = code;
@@ -1712,6 +1725,7 @@ static void fc_fcp_recovery(struct fc_fcp_pkt *fsp, u8 code)
  * when expecting status but the request has timed out.
  */
 static void fc_fcp_srr(struct fc_fcp_pkt *fsp, enum fc_rctl r_ctl, u32 offset)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct fc_lport *lport = fsp->lp;
 	struct fc_rport *rport;
@@ -1950,6 +1964,7 @@ EXPORT_SYMBOL(fc_queuecommand);
  * The fcp packet lock must be held when calling.
  */
 static void fc_io_compl(struct fc_fcp_pkt *fsp)
+	__must_hold(&fsp->scsi_pkt_lock)
 {
 	struct fc_fcp_internal *si;
 	struct scsi_cmnd *sc_cmd;
diff --git a/drivers/scsi/libiscsi.c b/drivers/scsi/libiscsi.c
index 7637aacd6037..2d04448432a7 100644
--- a/drivers/scsi/libiscsi.c
+++ b/drivers/scsi/libiscsi.c
@@ -445,16 +445,18 @@ static int iscsi_prep_scsi_cmd_pdu(struct iscsi_task *task)
 
 /**
  * iscsi_free_task - free a task
+ * @session: iscsi session
  * @task: iscsi cmd task
  *
  * Must be called with session back_lock.
  * This function returns the scsi command to scsi-ml or cleans
  * up mgmt tasks then returns the task to the pool.
  */
-static void iscsi_free_task(struct iscsi_task *task)
+static void iscsi_free_task(struct iscsi_session *session,
+			    struct iscsi_task *task)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
-	struct iscsi_session *session = conn->session;
 	struct scsi_cmnd *sc = task->sc;
 	int oldstate = task->state;
 
@@ -492,14 +494,16 @@ EXPORT_SYMBOL_GPL(iscsi_get_task);
 
 /**
  * __iscsi_put_task - drop the refcount on a task
+ * @session: iscsi session
  * @task: iscsi_task to drop the refcount on
  *
  * The back_lock must be held when calling in case it frees the task.
  */
-void __iscsi_put_task(struct iscsi_task *task)
+void __iscsi_put_task(struct iscsi_session *session, struct iscsi_task *task)
+	__must_hold(&session->back_lock)
 {
 	if (refcount_dec_and_test(&task->refcount))
-		iscsi_free_task(task);
+		iscsi_free_task(session, task);
 }
 EXPORT_SYMBOL_GPL(__iscsi_put_task);
 
@@ -509,7 +513,7 @@ void iscsi_put_task(struct iscsi_task *task)
 
 	if (refcount_dec_and_test(&task->refcount)) {
 		spin_lock_bh(&session->back_lock);
-		iscsi_free_task(task);
+		iscsi_free_task(session, task);
 		spin_unlock_bh(&session->back_lock);
 	}
 }
@@ -517,17 +521,19 @@ EXPORT_SYMBOL_GPL(iscsi_put_task);
 
 /**
  * iscsi_complete_task - finish a task
+ * @session: iscsi session
  * @task: iscsi cmd task
  * @state: state to complete task with
  *
  * Must be called with session back_lock.
  */
-static void iscsi_complete_task(struct iscsi_task *task, int state)
+static void iscsi_complete_task(struct iscsi_session *session,
+				struct iscsi_task *task, int state)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
 
-	ISCSI_DBG_SESSION(conn->session,
-			  "complete task itt 0x%x state %d sc %p\n",
+	ISCSI_DBG_SESSION(session, "complete task itt 0x%x state %d sc %p\n",
 			  task->itt, task->state, task->sc);
 	if (task->state == ISCSI_TASK_COMPLETED ||
 	    task->state == ISCSI_TASK_ABRT_TMF ||
@@ -541,11 +547,12 @@ static void iscsi_complete_task(struct iscsi_task *task, int state)
 		WRITE_ONCE(conn->ping_task, NULL);
 
 	/* release get from queueing */
-	__iscsi_put_task(task);
+	__iscsi_put_task(session, task);
 }
 
 /**
  * iscsi_complete_scsi_task - finish scsi task normally
+ * @session: iscsi session
  * @task: iscsi task for scsi cmd
  * @exp_cmdsn: expected cmd sn in cpu format
  * @max_cmdsn: max cmd sn in cpu format
@@ -555,23 +562,28 @@ static void iscsi_complete_task(struct iscsi_task *task, int state)
  *
  * Called with session back_lock
  */
-void iscsi_complete_scsi_task(struct iscsi_task *task,
+void iscsi_complete_scsi_task(struct iscsi_session *session,
+			      struct iscsi_task *task,
 			      uint32_t exp_cmdsn, uint32_t max_cmdsn)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
 
-	ISCSI_DBG_SESSION(conn->session, "[itt 0x%x]\n", task->itt);
+	ISCSI_DBG_SESSION(session, "[itt 0x%x]\n", task->itt);
 
 	conn->last_recv = jiffies;
-	__iscsi_update_cmdsn(conn->session, exp_cmdsn, max_cmdsn);
-	iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+	__iscsi_update_cmdsn(session, exp_cmdsn, max_cmdsn);
+	iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 }
 EXPORT_SYMBOL_GPL(iscsi_complete_scsi_task);
 
 /*
  * Must be called with back and frwd lock
  */
-static bool cleanup_queued_task(struct iscsi_task *task)
+static bool cleanup_queued_task(struct iscsi_session *session,
+				struct iscsi_task *task)
+	__must_hold(&session->frwd_lock)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
 	bool early_complete = false;
@@ -592,17 +604,17 @@ static bool cleanup_queued_task(struct iscsi_task *task)
 		 */
 		if (task->state == ISCSI_TASK_RUNNING ||
 		    task->state == ISCSI_TASK_COMPLETED)
-			__iscsi_put_task(task);
+			__iscsi_put_task(session, task);
 	}
 
-	if (conn->session->running_aborted_task == task) {
-		conn->session->running_aborted_task = NULL;
-		__iscsi_put_task(task);
+	if (session->running_aborted_task == task) {
+		session->running_aborted_task = NULL;
+		__iscsi_put_task(session, task);
 	}
 
 	if (conn->task == task) {
 		conn->task = NULL;
-		__iscsi_put_task(task);
+		__iscsi_put_task(session, task);
 	}
 
 	return early_complete;
@@ -612,13 +624,15 @@ static bool cleanup_queued_task(struct iscsi_task *task)
  * session back and frwd lock must be held and if not called for a task that
  * is still pending or from the xmit thread, then xmit thread must be suspended
  */
-static void __fail_scsi_task(struct iscsi_task *task, int err)
+static void __fail_scsi_task(struct iscsi_session *session,
+			     struct iscsi_task *task, int err)
+	__must_hold(&session->frwd_lock)
+	__must_hold(&session->back_lock)
 {
-	struct iscsi_conn *conn = task->conn;
 	struct scsi_cmnd *sc;
 	int state;
 
-	if (cleanup_queued_task(task))
+	if (cleanup_queued_task(session, task))
 		return;
 
 	if (task->state == ISCSI_TASK_PENDING) {
@@ -626,7 +640,7 @@ static void __fail_scsi_task(struct iscsi_task *task, int err)
 		 * cmd never made it to the xmit thread, so we should not count
 		 * the cmd in the sequencing
 		 */
-		conn->session->queued_cmdsn--;
+		session->queued_cmdsn--;
 		/* it was never sent so just complete like normal */
 		state = ISCSI_TASK_COMPLETED;
 	} else if (err == DID_TRANSPORT_DISRUPTED)
@@ -637,15 +651,15 @@ static void __fail_scsi_task(struct iscsi_task *task, int err)
 	sc = task->sc;
 	sc->result = err << 16;
 	scsi_set_resid(sc, scsi_bufflen(sc));
-	iscsi_complete_task(task, state);
+	iscsi_complete_task(session, task, state);
 }
 
-static void fail_scsi_task(struct iscsi_task *task, int err)
+static void fail_scsi_task(struct iscsi_session *session,
+			   struct iscsi_task *task, int err)
+	__must_hold(&session->frwd_lock)
 {
-	struct iscsi_session *session = task->conn->session;
-
 	spin_lock_bh(&session->back_lock);
-	__fail_scsi_task(task, err);
+	__fail_scsi_task(session, task, err);
 	spin_unlock_bh(&session->back_lock);
 }
 
@@ -857,6 +871,7 @@ EXPORT_SYMBOL_GPL(iscsi_conn_send_pdu);
 
 /**
  * iscsi_scsi_cmd_rsp - SCSI Command Response processing
+ * @session: iscsi session
  * @conn: iscsi connection
  * @hdr: iscsi header
  * @task: scsi command task
@@ -866,12 +881,13 @@ EXPORT_SYMBOL_GPL(iscsi_conn_send_pdu);
  * iscsi_cmd_rsp sets up the scsi_cmnd fields based on the PDU and
  * then completes the command and task. called under back_lock
  **/
-static void iscsi_scsi_cmd_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
+static void iscsi_scsi_cmd_rsp(struct iscsi_session *session,
+			       struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 			       struct iscsi_task *task, char *data,
 			       int datalen)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_scsi_rsp *rhdr = (struct iscsi_scsi_rsp *)hdr;
-	struct iscsi_session *session = conn->session;
 	struct scsi_cmnd *sc = task->sc;
 
 	iscsi_update_cmdsn(session, (struct iscsi_nopin*)rhdr);
@@ -950,11 +966,12 @@ static void iscsi_scsi_cmd_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 	ISCSI_DBG_SESSION(session, "cmd rsp done [sc %p res %d itt 0x%x]\n",
 			  sc, sc->result, task->itt);
 	conn->scsirsp_pdus_cnt++;
-	iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+	iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 }
 
 /**
  * iscsi_data_in_rsp - SCSI Data-In Response processing
+ * @session: iscsi session
  * @conn: iscsi connection
  * @hdr:  iscsi pdu
  * @task: scsi command task
@@ -963,8 +980,9 @@ static void iscsi_scsi_cmd_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
  * then completes the command and task. called under back_lock
  **/
 static void
-iscsi_data_in_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
-		  struct iscsi_task *task)
+iscsi_data_in_rsp(struct iscsi_session *session, struct iscsi_conn *conn,
+		  struct iscsi_hdr *hdr, struct iscsi_task *task)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_data_rsp *rhdr = (struct iscsi_data_rsp *)hdr;
 	struct scsi_cmnd *sc = task->sc;
@@ -972,7 +990,7 @@ iscsi_data_in_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 	if (!(rhdr->flags & ISCSI_FLAG_DATA_STATUS))
 		return;
 
-	iscsi_update_cmdsn(conn->session, (struct iscsi_nopin *)hdr);
+	iscsi_update_cmdsn(session, (struct iscsi_nopin *)hdr);
 	sc->result = (DID_OK << 16) | rhdr->cmd_status;
 	conn->exp_statsn = be32_to_cpu(rhdr->statsn) + 1;
 	if (rhdr->flags & (ISCSI_FLAG_DATA_UNDERFLOW |
@@ -987,11 +1005,11 @@ iscsi_data_in_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 			sc->result = (DID_BAD_TARGET << 16) | rhdr->cmd_status;
 	}
 
-	ISCSI_DBG_SESSION(conn->session, "data in with status done "
+	ISCSI_DBG_SESSION(session, "data in with status done "
 			  "[sc %p res %d itt 0x%x]\n",
 			  sc, sc->result, task->itt);
 	conn->scsirsp_pdus_cnt++;
-	iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+	iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 }
 
 static void iscsi_tmf_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
@@ -1059,6 +1077,7 @@ static int iscsi_send_nopout(struct iscsi_conn *conn, struct iscsi_nopin *rhdr)
 
 /**
  * iscsi_nop_out_rsp - SCSI NOP Response processing
+ * @session: iscsi session
  * @task: scsi command task
  * @nop: the nop structure
  * @data: where to put the data
@@ -1067,8 +1086,10 @@ static int iscsi_send_nopout(struct iscsi_conn *conn, struct iscsi_nopin *rhdr)
  * iscsi_nop_out_rsp handles nop response from use or
  * from user space. called under back_lock
  **/
-static int iscsi_nop_out_rsp(struct iscsi_task *task,
+static int iscsi_nop_out_rsp(struct iscsi_session *session,
+			     struct iscsi_task *task,
 			     struct iscsi_nopin *nop, char *data, int datalen)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_conn *conn = task->conn;
 	int rc = 0;
@@ -1083,12 +1104,14 @@ static int iscsi_nop_out_rsp(struct iscsi_task *task,
 			rc = ISCSI_ERR_CONN_FAILED;
 	} else
 		mod_timer(&conn->transport_timer, jiffies + conn->recv_timeout);
-	iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+	iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 	return rc;
 }
 
-static int iscsi_handle_reject(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
+static int iscsi_handle_reject(struct iscsi_session *session,
+			       struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 			       char *data, int datalen)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_reject *reject = (struct iscsi_reject *)hdr;
 	struct iscsi_hdr rejected_pdu;
@@ -1136,26 +1159,29 @@ static int iscsi_handle_reject(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 			 * Just resend.
 			 */
 			/* In RX path we are under back lock */
-			spin_unlock(&conn->session->back_lock);
-			spin_lock(&conn->session->frwd_lock);
+			spin_unlock(&session->back_lock);
+			spin_lock(&session->frwd_lock);
 			iscsi_send_nopout(conn,
 					  (struct iscsi_nopin*)&rejected_pdu);
-			spin_unlock(&conn->session->frwd_lock);
-			spin_lock(&conn->session->back_lock);
+			spin_unlock(&session->frwd_lock);
+			spin_lock(&session->back_lock);
 		} else {
-			struct iscsi_task *task;
+			struct iscsi_task *task = NULL;
 			/*
 			 * Our nop as ping got dropped. We know the target
 			 * and transport are ok so just clean up
 			 */
-			task = iscsi_itt_to_task(conn, rejected_pdu.itt);
-			if (!task) {
+			if (!iscsi_verify_itt(conn, rejected_pdu.itt))
+				task = iscsi_itt_to_task(session, conn,
+							 rejected_pdu.itt);
+			if (!task || task->state == ISCSI_TASK_FREE ||
+			    task->sc) {
 				iscsi_conn_printk(KERN_ERR, conn,
 						 "Invalid pdu reject. Could "
 						 "not lookup rejected task.\n");
 				rc = ISCSI_ERR_BAD_ITT;
 			} else
-				rc = iscsi_nop_out_rsp(task,
+				rc = iscsi_nop_out_rsp(session, task,
 					(struct iscsi_nopin*)&rejected_pdu,
 					NULL, 0);
 		}
@@ -1172,6 +1198,7 @@ static int iscsi_handle_reject(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 
 /**
  * iscsi_itt_to_task - look up task by itt
+ * @session: iscsi session
  * @conn: iscsi connection
  * @itt: itt
  *
@@ -1180,9 +1207,10 @@ static int iscsi_handle_reject(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
  *
  * The session back_lock must be held.
  */
-struct iscsi_task *iscsi_itt_to_task(struct iscsi_conn *conn, itt_t itt)
+struct iscsi_task *iscsi_itt_to_task(struct iscsi_session *session,
+				     struct iscsi_conn *conn, itt_t itt)
+	__must_hold(&session->back_lock)
 {
-	struct iscsi_session *session = conn->session;
 	int i;
 
 	if (itt == RESERVED_ITT)
@@ -1192,7 +1220,7 @@ struct iscsi_task *iscsi_itt_to_task(struct iscsi_conn *conn, itt_t itt)
 		session->tt->parse_pdu_itt(conn, itt, &i, NULL);
 	else
 		i = get_itt(itt);
-	if (i >= session->cmds_max)
+	if (i < 0 || i >= session->cmds_max)
 		return NULL;
 
 	return session->cmds[i];
@@ -1201,6 +1229,7 @@ EXPORT_SYMBOL_GPL(iscsi_itt_to_task);
 
 /**
  * __iscsi_complete_pdu - complete pdu
+ * @session: iscsi session
  * @conn: iscsi conn
  * @hdr: iscsi header
  * @data: data buffer
@@ -1210,10 +1239,10 @@ EXPORT_SYMBOL_GPL(iscsi_itt_to_task);
  * queuecommand or send generic. session back_lock must be held and verify
  * itt must have been called.
  */
-int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
-			 char *data, int datalen)
+int __iscsi_complete_pdu(struct iscsi_session *session, struct iscsi_conn *conn,
+			 struct iscsi_hdr *hdr, char *data, int datalen)
+	__must_hold(&session->back_lock)
 {
-	struct iscsi_session *session = conn->session;
 	int opcode = hdr->opcode & ISCSI_OPCODE_MASK, rc = 0;
 	struct iscsi_task *task;
 	uint32_t itt;
@@ -1252,7 +1281,7 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 			spin_lock(&session->back_lock);
 			break;
 		case ISCSI_OP_REJECT:
-			rc = iscsi_handle_reject(conn, hdr, data, datalen);
+			rc = iscsi_handle_reject(session, conn, hdr, data, datalen);
 			break;
 		case ISCSI_OP_ASYNC_EVENT:
 			conn->exp_statsn = be32_to_cpu(hdr->statsn) + 1;
@@ -1269,7 +1298,7 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 	switch(opcode) {
 	case ISCSI_OP_SCSI_CMD_RSP:
 	case ISCSI_OP_SCSI_DATA_IN:
-		task = iscsi_itt_to_ctask(conn, hdr->itt);
+		task = iscsi_itt_to_ctask(session, conn, hdr->itt);
 		if (!task)
 			return ISCSI_ERR_BAD_ITT;
 		task->last_xfer = jiffies;
@@ -1284,8 +1313,8 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 	case ISCSI_OP_TEXT_RSP:
 	case ISCSI_OP_SCSI_TMFUNC_RSP:
 	case ISCSI_OP_NOOP_IN:
-		task = iscsi_itt_to_task(conn, hdr->itt);
-		if (!task)
+		task = iscsi_itt_to_task(session, conn, hdr->itt);
+		if (!task || task->state == ISCSI_TASK_FREE || task->sc)
 			return ISCSI_ERR_BAD_ITT;
 		break;
 	default:
@@ -1294,10 +1323,10 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 
 	switch(opcode) {
 	case ISCSI_OP_SCSI_CMD_RSP:
-		iscsi_scsi_cmd_rsp(conn, hdr, task, data, datalen);
+		iscsi_scsi_cmd_rsp(session, conn, hdr, task, data, datalen);
 		break;
 	case ISCSI_OP_SCSI_DATA_IN:
-		iscsi_data_in_rsp(conn, hdr, task);
+		iscsi_data_in_rsp(session, conn, hdr, task);
 		break;
 	case ISCSI_OP_LOGOUT_RSP:
 		iscsi_update_cmdsn(session, (struct iscsi_nopin*)hdr);
@@ -1323,7 +1352,7 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 		}
 
 		iscsi_tmf_rsp(conn, hdr);
-		iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+		iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 		break;
 	case ISCSI_OP_NOOP_IN:
 		iscsi_update_cmdsn(session, (struct iscsi_nopin*)hdr);
@@ -1333,7 +1362,7 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 		}
 		conn->exp_statsn = be32_to_cpu(hdr->statsn) + 1;
 
-		rc = iscsi_nop_out_rsp(task, (struct iscsi_nopin*)hdr,
+		rc = iscsi_nop_out_rsp(session, task, (struct iscsi_nopin*)hdr,
 				       data, datalen);
 		break;
 	default:
@@ -1346,7 +1375,7 @@ int __iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 recv_pdu:
 	if (iscsi_recv_pdu(conn->cls_conn, hdr, data, datalen))
 		rc = ISCSI_ERR_CONN_FAILED;
-	iscsi_complete_task(task, ISCSI_TASK_COMPLETED);
+	iscsi_complete_task(session, task, ISCSI_TASK_COMPLETED);
 	return rc;
 }
 EXPORT_SYMBOL_GPL(__iscsi_complete_pdu);
@@ -1354,11 +1383,12 @@ EXPORT_SYMBOL_GPL(__iscsi_complete_pdu);
 int iscsi_complete_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
 		       char *data, int datalen)
 {
+	struct iscsi_session *session = conn->session;
 	int rc;
 
-	spin_lock(&conn->session->back_lock);
-	rc = __iscsi_complete_pdu(conn, hdr, data, datalen);
-	spin_unlock(&conn->session->back_lock);
+	spin_lock(&session->back_lock);
+	rc = __iscsi_complete_pdu(session, conn, hdr, data, datalen);
+	spin_unlock(&session->back_lock);
 	return rc;
 }
 EXPORT_SYMBOL_GPL(iscsi_complete_pdu);
@@ -1385,7 +1415,7 @@ int iscsi_verify_itt(struct iscsi_conn *conn, itt_t itt)
 		return ISCSI_ERR_BAD_ITT;
 	}
 
-	if (i >= session->cmds_max) {
+	if (i < 0 || i >= session->cmds_max) {
 		iscsi_conn_printk(KERN_ERR, conn,
 				  "received invalid itt index %u (max cmds "
 				   "%u.\n", i, session->cmds_max);
@@ -1397,6 +1427,7 @@ EXPORT_SYMBOL_GPL(iscsi_verify_itt);
 
 /**
  * iscsi_itt_to_ctask - look up ctask by itt
+ * @session: iscsi session
  * @conn: iscsi connection
  * @itt: itt
  *
@@ -1404,21 +1435,23 @@ EXPORT_SYMBOL_GPL(iscsi_verify_itt);
  *
  * The session back_lock must be held.
  */
-struct iscsi_task *iscsi_itt_to_ctask(struct iscsi_conn *conn, itt_t itt)
+struct iscsi_task *iscsi_itt_to_ctask(struct iscsi_session *session,
+				      struct iscsi_conn *conn, itt_t itt)
+	__must_hold(&session->back_lock)
 {
 	struct iscsi_task *task;
 
 	if (iscsi_verify_itt(conn, itt))
 		return NULL;
 
-	task = iscsi_itt_to_task(conn, itt);
+	task = iscsi_itt_to_task(session, conn, itt);
 	if (!task || !task->sc)
 		return NULL;
 
-	if (iscsi_cmd(task->sc)->age != conn->session->age) {
-		iscsi_session_printk(KERN_ERR, conn->session,
+	if (iscsi_cmd(task->sc)->age != session->age) {
+		iscsi_session_printk(KERN_ERR, session,
 				  "task's session age %d, expected %d\n",
-				  iscsi_cmd(task->sc)->age, conn->session->age);
+				  iscsi_cmd(task->sc)->age, session->age);
 		return NULL;
 	}
 
@@ -1482,10 +1515,10 @@ void iscsi_conn_failure(struct iscsi_conn *conn, enum iscsi_err err)
 }
 EXPORT_SYMBOL_GPL(iscsi_conn_failure);
 
-static int iscsi_check_cmdsn_window_closed(struct iscsi_conn *conn)
+static int iscsi_check_cmdsn_window_closed(struct iscsi_session *session,
+					   struct iscsi_conn *conn)
+	__must_hold(&session->frwd_lock)
 {
-	struct iscsi_session *session = conn->session;
-
 	/*
 	 * Check for iSCSI window and take care of CmdSN wrap-around
 	 */
@@ -1499,8 +1532,9 @@ static int iscsi_check_cmdsn_window_closed(struct iscsi_conn *conn)
 	return 0;
 }
 
-static int iscsi_xmit_task(struct iscsi_conn *conn, struct iscsi_task *task,
-			   bool was_requeue)
+static int iscsi_xmit_task(struct iscsi_session *session, struct iscsi_conn *conn,
+			   struct iscsi_task *task, bool was_requeue)
+	__must_hold(&session->frwd_lock)
 {
 	int rc;
 
@@ -1540,9 +1574,9 @@ static int iscsi_xmit_task(struct iscsi_conn *conn, struct iscsi_task *task,
 		return -ENODATA;
 	}
 
-	spin_unlock_bh(&conn->session->frwd_lock);
-	rc = conn->session->tt->xmit_task(task);
-	spin_lock_bh(&conn->session->frwd_lock);
+	spin_unlock_bh(&session->frwd_lock);
+	rc = session->tt->xmit_task(task);
+	spin_lock_bh(&session->frwd_lock);
 	if (!rc) {
 		/* done with this task */
 		task->last_xfer = jiffies;
@@ -1599,18 +1633,19 @@ EXPORT_SYMBOL_GPL(iscsi_requeue_task);
  **/
 static int iscsi_data_xmit(struct iscsi_conn *conn)
 {
+	struct iscsi_session *session = conn->session;
 	struct iscsi_task *task;
 	int rc = 0;
 
-	spin_lock_bh(&conn->session->frwd_lock);
+	spin_lock_bh(&session->frwd_lock);
 	if (test_bit(ISCSI_CONN_FLAG_SUSPEND_TX, &conn->flags)) {
-		ISCSI_DBG_SESSION(conn->session, "Tx suspended!\n");
-		spin_unlock_bh(&conn->session->frwd_lock);
+		ISCSI_DBG_SESSION(session, "Tx suspended!\n");
+		spin_unlock_bh(&session->frwd_lock);
 		return -ENODATA;
 	}
 
 	if (conn->task) {
-		rc = iscsi_xmit_task(conn, conn->task, false);
+		rc = iscsi_xmit_task(session, conn, conn->task, false);
 	        if (rc)
 		        goto done;
 	}
@@ -1627,12 +1662,12 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
 		list_del_init(&task->running);
 		if (iscsi_prep_mgmt_task(conn, task)) {
 			/* regular RX path uses back_lock */
-			spin_lock_bh(&conn->session->back_lock);
-			__iscsi_put_task(task);
-			spin_unlock_bh(&conn->session->back_lock);
+			spin_lock_bh(&session->back_lock);
+			__iscsi_put_task(session, task);
+			spin_unlock_bh(&session->back_lock);
 			continue;
 		}
-		rc = iscsi_xmit_task(conn, task, false);
+		rc = iscsi_xmit_task(session, conn, task, false);
 		if (rc)
 			goto done;
 	}
@@ -1642,7 +1677,7 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
 		/*
 		 * we always do fastlogout - conn stop code will clean up.
 		 */
-		if (conn->session->state == ISCSI_STATE_LOGGING_OUT)
+		if (session->state == ISCSI_STATE_LOGGING_OUT)
 			break;
 
 		task = list_entry(conn->requeue.next, struct iscsi_task,
@@ -1652,7 +1687,7 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
 			break;
 
 		list_del_init(&task->running);
-		rc = iscsi_xmit_task(conn, task, true);
+		rc = iscsi_xmit_task(session, conn, task, true);
 		if (rc)
 			goto done;
 		if (!list_empty(&conn->mgmtqueue))
@@ -1664,19 +1699,19 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
 		task = list_entry(conn->cmdqueue.next, struct iscsi_task,
 				  running);
 		list_del_init(&task->running);
-		if (conn->session->state == ISCSI_STATE_LOGGING_OUT) {
-			fail_scsi_task(task, DID_IMM_RETRY);
+		if (session->state == ISCSI_STATE_LOGGING_OUT) {
+			fail_scsi_task(session, task, DID_IMM_RETRY);
 			continue;
 		}
 		rc = iscsi_prep_scsi_cmd_pdu(task);
 		if (rc) {
 			if (rc == -ENOMEM || rc == -EACCES)
-				fail_scsi_task(task, DID_IMM_RETRY);
+				fail_scsi_task(session, task, DID_IMM_RETRY);
 			else
-				fail_scsi_task(task, DID_ABORT);
+				fail_scsi_task(session, task, DID_ABORT);
 			continue;
 		}
-		rc = iscsi_xmit_task(conn, task, false);
+		rc = iscsi_xmit_task(session, conn, task, false);
 		if (rc)
 			goto done;
 		/*
@@ -1690,11 +1725,11 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
 			goto check_requeue;
 	}
 
-	spin_unlock_bh(&conn->session->frwd_lock);
+	spin_unlock_bh(&session->frwd_lock);
 	return -ENODATA;
 
 done:
-	spin_unlock_bh(&conn->session->frwd_lock);
+	spin_unlock_bh(&session->frwd_lock);
 	return rc;
 }
 
@@ -1828,7 +1863,7 @@ enum scsi_qc_status iscsi_queuecommand(struct Scsi_Host *host,
 		goto fault;
 	}
 
-	if (iscsi_check_cmdsn_window_closed(conn)) {
+	if (iscsi_check_cmdsn_window_closed(session, conn)) {
 		reason = FAILURE_WINDOW_CLOSED;
 		goto reject;
 	}
@@ -1866,7 +1901,7 @@ enum scsi_qc_status iscsi_queuecommand(struct Scsi_Host *host,
 
 prepd_reject:
 	spin_lock_bh(&session->back_lock);
-	iscsi_complete_task(task, ISCSI_TASK_REQUEUE_SCSIQ);
+	iscsi_complete_task(session, task, ISCSI_TASK_REQUEUE_SCSIQ);
 	spin_unlock_bh(&session->back_lock);
 reject:
 	spin_unlock_bh(&session->frwd_lock);
@@ -1876,7 +1911,7 @@ enum scsi_qc_status iscsi_queuecommand(struct Scsi_Host *host,
 
 prepd_fault:
 	spin_lock_bh(&session->back_lock);
-	iscsi_complete_task(task, ISCSI_TASK_REQUEUE_SCSIQ);
+	iscsi_complete_task(session, task, ISCSI_TASK_REQUEUE_SCSIQ);
 	spin_unlock_bh(&session->back_lock);
 fault:
 	spin_unlock_bh(&session->frwd_lock);
@@ -1913,13 +1948,13 @@ static void iscsi_tmf_timedout(struct timer_list *t)
 	spin_unlock(&session->frwd_lock);
 }
 
-static int iscsi_exec_task_mgmt_fn(struct iscsi_conn *conn,
+static int iscsi_exec_task_mgmt_fn(struct iscsi_session *session,
+				   struct iscsi_conn *conn,
 				   struct iscsi_tm *hdr, int age,
 				   int timeout)
+	__must_hold(&session->eh_mutex)
 	__must_hold(&session->frwd_lock)
 {
-	struct iscsi_session *session = conn->session;
-
 	if (__iscsi_conn_send_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0)) {
 		spin_unlock_bh(&session->frwd_lock);
 		iscsi_conn_printk(KERN_ERR, conn, "Could not send TMF.\n");
@@ -1962,9 +1997,10 @@ static int iscsi_exec_task_mgmt_fn(struct iscsi_conn *conn,
 /*
  * Fail commands. session frwd lock held and xmit thread flushed.
  */
-static void fail_scsi_tasks(struct iscsi_conn *conn, u64 lun, int error)
+static void fail_scsi_tasks(struct iscsi_session *session, struct iscsi_conn *conn,
+			    u64 lun, int error)
+	__must_hold(&session->frwd_lock)
 {
-	struct iscsi_session *session = conn->session;
 	struct iscsi_task *task;
 	int i;
 
@@ -1993,8 +2029,8 @@ static void fail_scsi_tasks(struct iscsi_conn *conn, u64 lun, int error)
 		ISCSI_DBG_SESSION(session,
 				  "failing sc %p itt 0x%x state %d\n",
 				  task->sc, task->itt, task->state);
-		__fail_scsi_task(task, error);
-		__iscsi_put_task(task);
+		__fail_scsi_task(session, task, error);
+		__iscsi_put_task(session, task);
 	}
 	spin_unlock_bh(&session->back_lock);
 }
@@ -2415,7 +2451,7 @@ int iscsi_eh_abort(struct scsi_cmnd *sc)
 	spin_unlock(&session->back_lock);
 
 	if (task->state == ISCSI_TASK_PENDING) {
-		fail_scsi_task(task, DID_ABORT);
+		fail_scsi_task(session, task, DID_ABORT);
 		goto success;
 	}
 
@@ -2427,7 +2463,8 @@ int iscsi_eh_abort(struct scsi_cmnd *sc)
 	hdr = &session->tmhdr;
 	iscsi_prep_abort_task_pdu(task, hdr);
 
-	if (iscsi_exec_task_mgmt_fn(conn, hdr, age, session->abort_timeout))
+	if (iscsi_exec_task_mgmt_fn(session, conn, hdr, age,
+				    session->abort_timeout))
 		goto failed;
 
 	switch (session->tmf_state) {
@@ -2444,7 +2481,7 @@ int iscsi_eh_abort(struct scsi_cmnd *sc)
 		 * then sent more data for the cmd.
 		 */
 		spin_lock_bh(&session->frwd_lock);
-		fail_scsi_task(task, DID_ABORT);
+		fail_scsi_task(session, task, DID_ABORT);
 		session->tmf_state = TMF_INITIAL;
 		memset(hdr, 0, sizeof(*hdr));
 		spin_unlock_bh(&session->frwd_lock);
@@ -2541,7 +2578,7 @@ int iscsi_eh_device_reset(struct scsi_cmnd *sc)
 	hdr = &session->tmhdr;
 	iscsi_prep_lun_reset_pdu(sc, hdr);
 
-	if (iscsi_exec_task_mgmt_fn(conn, hdr, session->age,
+	if (iscsi_exec_task_mgmt_fn(session, conn, hdr, session->age,
 				    session->lu_reset_timeout)) {
 		rc = FAILED;
 		goto unlock;
@@ -2566,7 +2603,7 @@ int iscsi_eh_device_reset(struct scsi_cmnd *sc)
 
 	spin_lock_bh(&session->frwd_lock);
 	memset(hdr, 0, sizeof(*hdr));
-	fail_scsi_tasks(conn, sc->device->lun, DID_ERROR);
+	fail_scsi_tasks(session, conn, sc->device->lun, DID_ERROR);
 	session->tmf_state = TMF_INITIAL;
 	spin_unlock_bh(&session->frwd_lock);
 
@@ -2703,7 +2740,7 @@ static int iscsi_eh_target_reset(struct scsi_cmnd *sc)
 	hdr = &session->tmhdr;
 	iscsi_prep_tgt_reset_pdu(sc, hdr);
 
-	if (iscsi_exec_task_mgmt_fn(conn, hdr, session->age,
+	if (iscsi_exec_task_mgmt_fn(session, conn, hdr, session->age,
 				    session->tgt_reset_timeout)) {
 		rc = FAILED;
 		goto unlock;
@@ -2728,7 +2765,7 @@ static int iscsi_eh_target_reset(struct scsi_cmnd *sc)
 
 	spin_lock_bh(&session->frwd_lock);
 	memset(hdr, 0, sizeof(*hdr));
-	fail_scsi_tasks(conn, -1, DID_ERROR);
+	fail_scsi_tasks(session, conn, -1, DID_ERROR);
 	session->tmf_state = TMF_INITIAL;
 	spin_unlock_bh(&session->frwd_lock);
 
@@ -3357,6 +3394,7 @@ EXPORT_SYMBOL_GPL(iscsi_conn_start);
 
 static void
 fail_mgmt_tasks(struct iscsi_session *session, struct iscsi_conn *conn)
+	__must_hold(&session->frwd_lock)
 {
 	struct iscsi_task *task;
 	int i, state;
@@ -3374,7 +3412,7 @@ fail_mgmt_tasks(struct iscsi_session *session, struct iscsi_conn *conn)
 				  task->itt, task->state);
 
 		spin_lock_bh(&session->back_lock);
-		if (cleanup_queued_task(task)) {
+		if (cleanup_queued_task(session, task)) {
 			spin_unlock_bh(&session->back_lock);
 			continue;
 		}
@@ -3382,7 +3420,7 @@ fail_mgmt_tasks(struct iscsi_session *session, struct iscsi_conn *conn)
 		state = ISCSI_TASK_ABRT_SESS_RECOV;
 		if (task->state == ISCSI_TASK_PENDING)
 			state = ISCSI_TASK_COMPLETED;
-		iscsi_complete_task(task, state);
+		iscsi_complete_task(session, task, state);
 		spin_unlock_bh(&session->back_lock);
 	}
 }
@@ -3442,7 +3480,7 @@ void iscsi_conn_stop(struct iscsi_cls_conn *cls_conn, int flag)
 	 * flush queues.
 	 */
 	spin_lock_bh(&session->frwd_lock);
-	fail_scsi_tasks(conn, -1, DID_TRANSPORT_DISRUPTED);
+	fail_scsi_tasks(session, conn, -1, DID_TRANSPORT_DISRUPTED);
 	fail_mgmt_tasks(session, conn);
 	memset(&session->tmhdr, 0, sizeof(session->tmhdr));
 	spin_unlock_bh(&session->frwd_lock);
diff --git a/drivers/scsi/libiscsi_tcp.c b/drivers/scsi/libiscsi_tcp.c
index 7223bb18b048..20ec3ba45067 100644
--- a/drivers/scsi/libiscsi_tcp.c
+++ b/drivers/scsi/libiscsi_tcp.c
@@ -480,6 +480,9 @@ static int iscsi_tcp_data_in(struct iscsi_conn *conn, struct iscsi_task *task)
 	int datasn = be32_to_cpu(rhdr->datasn);
 	unsigned total_in_length = task->sc->sdb.length;
 
+	if (task->sc->sc_data_direction != DMA_FROM_DEVICE)
+		return ISCSI_ERR_PROTO;
+
 	/*
 	 * lib iscsi will update this in the completion handling if there
 	 * is status.
@@ -529,7 +532,7 @@ static int iscsi_tcp_r2t_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 	int rc;
 
 	spin_lock(&session->back_lock);
-	task = iscsi_itt_to_ctask(conn, hdr->itt);
+	task = iscsi_itt_to_ctask(session, conn, hdr->itt);
 	if (!task) {
 		spin_unlock(&session->back_lock);
 		return ISCSI_ERR_BAD_ITT;
@@ -598,7 +601,8 @@ static int iscsi_tcp_r2t_rsp(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 			      data_length, session->max_burst);
 
 	data_offset = be32_to_cpu(rhdr->data_offset);
-	if (data_offset + data_length > task->sc->sdb.length) {
+	if (data_offset > task->sc->sdb.length ||
+	    data_length > task->sc->sdb.length - data_offset) {
 		iscsi_conn_printk(KERN_ERR, conn,
 				  "invalid R2T with data len %u at offset %u "
 				  "and total length %d\n", data_length,
@@ -677,6 +681,7 @@ iscsi_tcp_process_data_in(struct iscsi_tcp_conn *tcp_conn,
 static int
 iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 {
+	struct iscsi_session *session = conn->session;
 	int rc = 0, opcode, ahslen;
 	struct iscsi_tcp_conn *tcp_conn = conn->dd_data;
 	struct iscsi_task *task;
@@ -706,14 +711,14 @@ iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 
 	switch(opcode) {
 	case ISCSI_OP_SCSI_DATA_IN:
-		spin_lock(&conn->session->back_lock);
-		task = iscsi_itt_to_ctask(conn, hdr->itt);
+		spin_lock(&session->back_lock);
+		task = iscsi_itt_to_ctask(session, conn, hdr->itt);
 		if (!task)
 			rc = ISCSI_ERR_BAD_ITT;
 		else
 			rc = iscsi_tcp_data_in(conn, task);
 		if (rc) {
-			spin_unlock(&conn->session->back_lock);
+			spin_unlock(&session->back_lock);
 			break;
 		}
 
@@ -731,7 +736,7 @@ iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 			 * update the digest per-entry.
 			 */
 			if (conn->datadgst_en &&
-			    !(conn->session->tt->caps & CAP_DIGEST_OFFLOAD))
+			    !(session->tt->caps & CAP_DIGEST_OFFLOAD))
 				rx_crcp = tcp_conn->rx_crcp;
 
 			ISCSI_DBG_TCP(conn, "iscsi_tcp_begin_data_in( "
@@ -746,11 +751,11 @@ iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
 						   tcp_conn->in.datalen,
 						   iscsi_tcp_process_data_in,
 						   rx_crcp);
-			spin_unlock(&conn->session->back_lock);
+			spin_unlock(&session->back_lock);
 			return rc;
 		}
-		rc = __iscsi_complete_pdu(conn, hdr, NULL, 0);
-		spin_unlock(&conn->session->back_lock);
+		rc = __iscsi_complete_pdu(session, conn, hdr, NULL, 0);
+		spin_unlock(&session->back_lock);
 		break;
 	case ISCSI_OP_R2T:
 		if (ahslen) {
diff --git a/drivers/scsi/libsas/Makefile b/drivers/scsi/libsas/Makefile
index 9dc32736cf21..6f6f1336b438 100644
--- a/drivers/scsi/libsas/Makefile
+++ b/drivers/scsi/libsas/Makefile
@@ -6,6 +6,8 @@
 # Copyright (C) 2005 Luben Tuikov <luben_tuikov@adaptec.com>
 #
 
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_SAS_LIBSAS) += libsas.o
 libsas-y +=  sas_init.o     \
 		sas_phy.o      \
diff --git a/drivers/scsi/libsas/sas_ata.c b/drivers/scsi/libsas/sas_ata.c
index 61368e55bf86..2340790c9f6b 100644
--- a/drivers/scsi/libsas/sas_ata.c
+++ b/drivers/scsi/libsas/sas_ata.c
@@ -153,7 +153,7 @@ static void sas_ata_task_done(struct sas_task *task)
 }
 
 static unsigned int sas_ata_qc_issue(struct ata_queued_cmd *qc)
-	__must_hold(ap->lock)
+	__must_hold(qc->ap->lock)
 {
 	struct sas_task *task;
 	struct scatterlist *sg;
diff --git a/drivers/scsi/libsas/sas_expander.c b/drivers/scsi/libsas/sas_expander.c
index 811c9eb4fef1..26c2099c28b9 100644
--- a/drivers/scsi/libsas/sas_expander.c
+++ b/drivers/scsi/libsas/sas_expander.c
@@ -62,7 +62,11 @@ static int smp_execute_task_sg(struct domain_device *dev,
 		to_sas_internal(dev->port->ha->shost->transportt);
 	struct sas_ha_struct *ha = dev->port->ha;
 
-	pm_runtime_get_sync(ha->dev);
+	/*
+	 * Non-blocking: a sync resume here would deadlock against
+	 * sas_drain_work() during HA resume.
+	 */
+	pm_runtime_get_noresume(ha->dev);
 	mutex_lock(&dev->ex_dev.cmd_mutex);
 	for (retry = 0; retry < 3; retry++) {
 		if (test_bit(SAS_DEV_GONE, &dev->state)) {
@@ -135,7 +139,7 @@ static int smp_execute_task_sg(struct domain_device *dev,
 		}
 	}
 	mutex_unlock(&dev->ex_dev.cmd_mutex);
-	pm_runtime_put_sync(ha->dev);
+	pm_runtime_put(ha->dev);
 
 	BUG_ON(retry == 3 && task != NULL);
 	sas_free_task(task);
@@ -2222,6 +2226,11 @@ void sas_smp_handler(struct bsg_job *job, struct Scsi_Host *shost,
 		goto out;
 	}
 
+	/* The host may have autosuspended, resume it here. */
+	ret = pm_runtime_resume_and_get(dev->port->ha->dev);
+	if (ret)
+		goto out;
+
 	ret = smp_execute_task_sg(dev, job->request_payload.sg_list,
 			job->reply_payload.sg_list);
 	if (ret >= 0) {
@@ -2229,6 +2238,7 @@ void sas_smp_handler(struct bsg_job *job, struct Scsi_Host *shost,
 		rcvlen = job->reply_payload.payload_len - ret;
 		ret = 0;
 	}
+	pm_runtime_put(dev->port->ha->dev);
 
 out:
 	bsg_job_done(job, ret, rcvlen);
diff --git a/drivers/scsi/libsas/sas_task.c b/drivers/scsi/libsas/sas_task.c
index e9d291007817..2080e5836179 100644
--- a/drivers/scsi/libsas/sas_task.c
+++ b/drivers/scsi/libsas/sas_task.c
@@ -25,7 +25,7 @@ void sas_ssp_task_response(struct device *dev, struct sas_task *task,
 	case SAS_DATAPRES_SENSE_DATA:
 		tstat->stat = SAS_SAM_STAT_CHECK_CONDITION;
 		tstat->buf_valid_size =
-			min_t(int, SAS_STATUS_BUF_SIZE,
+			min_t(u32, SAS_STATUS_BUF_SIZE,
 			      be32_to_cpu(iu->sense_data_len));
 		memcpy(tstat->buf, iu->sense_data, tstat->buf_valid_size);
 
diff --git a/drivers/scsi/lpfc/lpfc_ct.c b/drivers/scsi/lpfc/lpfc_ct.c
index 0734ab3be3e3..f709e5087577 100644
--- a/drivers/scsi/lpfc/lpfc_ct.c
+++ b/drivers/scsi/lpfc/lpfc_ct.c
@@ -3576,8 +3576,6 @@ lpfc_cmpl_ct_cmd_vmid(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
 	int i;
 
 	cmd = be16_to_cpu(ctcmd->CommandResponse.bits.CmdRsp);
-	if (cmd == SLI_CTAS_DALLAPP_ID)
-		lpfc_ct_free_iocb(phba, cmdiocb);
 
 	if (lpfc_els_chk_latt(vport) || get_job_ulpstatus(phba, rspiocb)) {
 		if (cmd != SLI_CTAS_DALLAPP_ID)
diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c
index 6f6394a0047c..804aa7509b69 100644
--- a/drivers/scsi/lpfc/lpfc_els.c
+++ b/drivers/scsi/lpfc/lpfc_els.c
@@ -5952,11 +5952,12 @@ lpfc_els_rsp_reject(struct lpfc_vport *vport, uint32_t rejectError,
 	/* Xmit ELS RJT <err> response tag <ulpIoTag> */
 	lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
 			 "0129 Xmit ELS RJT x%x response tag x%x "
-			 "xri x%x, did x%x, nlp_flag x%lx, nlp_state x%x, "
-			 "rpi x%x\n",
+			 "xri x%x, ndlp x%px, did x%x, nlp_flag x%lx, "
+			 "nlp_state x%x, rpi x%x ref_cnt %d\n",
 			 rejectError, elsiocb->iotag,
-			 get_job_ulpcontext(phba, elsiocb), ndlp->nlp_DID,
-			 ndlp->nlp_flag, ndlp->nlp_state, ndlp->nlp_rpi);
+			 get_job_ulpcontext(phba, elsiocb), ndlp,
+			 ndlp->nlp_DID, ndlp->nlp_flag, ndlp->nlp_state,
+			 ndlp->nlp_rpi, kref_read(&ndlp->kref));
 	lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_ELS_RSP,
 		"Issue LS_RJT:    did:x%x flg:x%lx err:x%x",
 		ndlp->nlp_DID, ndlp->nlp_flag, rejectError);
@@ -8146,7 +8147,7 @@ lpfc_els_rcv_rscn(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb,
 	uint32_t payload_len, length, nportid, *cmd;
 	int rscn_cnt;
 	int rscn_id = 0, hba_id = 0;
-	int i, tmo;
+	int i;
 
 	pcmd = cmdiocb->cmd_dmabuf;
 	lp = (uint32_t *) pcmd->virt;
@@ -8225,11 +8226,8 @@ lpfc_els_rcv_rscn(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb,
 			lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb,
 				ndlp, NULL);
 			/* Restart disctmo if its already running */
-			if (test_bit(FC_DISC_TMO, &vport->fc_flag)) {
-				tmo = ((phba->fc_ratov * 3) + 3);
-				mod_timer(&vport->fc_disctmo,
-					  jiffies + secs_to_jiffies(tmo));
-			}
+			if (test_bit(FC_DISC_TMO, &vport->fc_flag))
+				lpfc_set_disctmo(vport);
 			return 0;
 		}
 	}
@@ -8260,11 +8258,9 @@ lpfc_els_rcv_rscn(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb,
 		set_bit(FC_RSCN_DEFERRED, &vport->fc_flag);
 
 		/* Restart disctmo if its already running */
-		if (test_bit(FC_DISC_TMO, &vport->fc_flag)) {
-			tmo = ((phba->fc_ratov * 3) + 3);
-			mod_timer(&vport->fc_disctmo,
-				  jiffies + secs_to_jiffies(tmo));
-		}
+		if (test_bit(FC_DISC_TMO, &vport->fc_flag))
+			lpfc_set_disctmo(vport);
+
 		if ((rscn_cnt < FC_MAX_HOLD_RSCN) &&
 		    !test_bit(FC_RSCN_DISCOVERY, &vport->fc_flag)) {
 			set_bit(FC_RSCN_MODE, &vport->fc_flag);
@@ -9597,6 +9593,7 @@ lpfc_els_timeout(struct timer_list *t)
  **/
 void
 lpfc_els_timeout_handler(struct lpfc_vport *vport)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct lpfc_hba  *phba = vport->phba;
 	struct lpfc_sli_ring *pring;
@@ -9719,6 +9716,7 @@ lpfc_els_timeout_handler(struct lpfc_vport *vport)
  **/
 void
 lpfc_els_flush_cmd(struct lpfc_vport *vport)
+	__context_unsafe(/*conditional locking*/)
 {
 	LIST_HEAD(abort_list);
 	LIST_HEAD(cancel_list);
@@ -10462,6 +10460,7 @@ lpfc_els_unsol_buffer(struct lpfc_hba *phba, struct lpfc_sli_ring *pring,
 		      struct lpfc_vport *vport, struct lpfc_iocbq *elsiocb)
 {
 	struct lpfc_nodelist *ndlp;
+	struct lpfc_nodelist *alloc_ndlp = NULL;
 	struct ls_rjt stat;
 	u32 *payload, payload_len;
 	u32 cmd = 0, did = 0, newnode, status = 0;
@@ -10560,7 +10559,9 @@ lpfc_els_unsol_buffer(struct lpfc_hba *phba, struct lpfc_sli_ring *pring,
 			did, vport->port_state, ndlp->nlp_flag);
 
 		phba->fc_stat.elsRcvPLOGI++;
+		alloc_ndlp = ndlp;
 		ndlp = lpfc_plogi_confirm_nport(phba, payload, ndlp);
+
 		if (phba->sli_rev == LPFC_SLI_REV4 &&
 		    test_bit(FC_PT2PT, &phba->pport->fc_flag)) {
 			vport->fc_prevDID = vport->fc_myDID;
@@ -10876,13 +10877,28 @@ lpfc_els_unsol_buffer(struct lpfc_hba *phba, struct lpfc_sli_ring *pring,
 		stat.un.b.lsRjtRsnCodeExp = rjt_exp;
 		lpfc_els_rsp_reject(vport, stat.un.lsRjtError, elsiocb, ndlp,
 				    NULL);
-		/* Remove the reference from above for new nodes. */
-		if (newnode)
-			lpfc_disc_state_machine(vport, ndlp, NULL,
-					NLP_EVT_DEVICE_RM);
+
+		/* Remove the safety reference from routine start. */
+		if (newnode) {
+			/* alloc_ndlp is assigned for an unsolicited PLOGI from
+			 * the ndlp allocated by this routine. The routine
+			 * lpfc_plogi_confirm_nport may have swapped the initial
+			 * ndlp to an existing ndlp. In that case, alloc_ndlp
+			 * is the pre-swap ndlp that needs a DEVICE_RM because
+			 * it is the newnode. For all other paths to lsrjt
+			 * (non-PLOGI ELS) that were rejected by the early
+			 * port_state check, alloc_ndlp is NULL and ndlp is
+			 * still the originally allocated node.
+			 */
+			lpfc_disc_state_machine(vport,
+						alloc_ndlp ? alloc_ndlp : ndlp,
+						NULL, NLP_EVT_DEVICE_RM);
+		}
 	}
 
-	/* Release the reference on this elsiocb, not the ndlp. */
+	/* This elsiocb is not the IOCB issued for a response. Remove
+	 * the safety reference allocated earlier.
+	 */
 	lpfc_nlp_put(elsiocb->ndlp);
 	elsiocb->ndlp = NULL;
 
@@ -11395,6 +11411,7 @@ lpfc_cmpl_els_fdisc(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
 	struct serv_parm *sp;
 	uint8_t fabric_param_changed;
 	u32 ulp_status, ulp_word4;
+	unsigned long flags;
 
 	ulp_status = get_job_ulpstatus(phba, rspiocb);
 	ulp_word4 = get_job_word4(phba, rspiocb);
@@ -11416,7 +11433,6 @@ lpfc_cmpl_els_fdisc(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
 		ulp_status, ulp_word4, vport->fc_prevDID);
 
 	if (ulp_status) {
-
 		if (lpfc_fabric_login_reqd(phba, cmdiocb, rspiocb)) {
 			lpfc_retry_pport_discovery(phba);
 			goto out;
@@ -11427,12 +11443,28 @@ lpfc_cmpl_els_fdisc(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
 			goto out;
 		/* Warn FDISC status */
 		lpfc_vlog_msg(vport, KERN_WARNING, LOG_ELS,
-			      "0126 FDISC cmpl status: x%x/x%x)\n",
-			      ulp_status, ulp_word4);
+			      "0126 FDISC cmpl status: (x%x/x%x) ndlp x%px "
+			      "Data: x%lx x%x x%x x%x x%x x%x x%x x%x x%x\n",
+			      ulp_status, ulp_word4, ndlp, ndlp->nlp_flag,
+			      ndlp->nlp_DID, ndlp->nlp_last_elscmd,
+			      ndlp->nlp_type, ndlp->nlp_rpi, ndlp->nlp_state,
+			      ndlp->nlp_prev_state, ndlp->fc4_xpt_flags,
+			      kref_read(&ndlp->kref));
 
-		/* drop initial reference */
-		if (!test_and_set_bit(NLP_DROPPED, &ndlp->nlp_flag))
+		/* If have not previously registered with transport layer and no
+		 * LPFC_EVT_DEV_LOSS work pending, then drop initial reference.
+		 * Otherwise, let the dev_loss_tmo_callbk drop the initial
+		 * reference.
+		 */
+		spin_lock_irqsave(&ndlp->lock, flags);
+		if (!(ndlp->fc4_xpt_flags & (SCSI_XPT_REGD | NVME_XPT_REGD)) &&
+		    !test_bit(NLP_IN_DEV_LOSS, &ndlp->nlp_flag) &&
+		    !test_and_set_bit(NLP_DROPPED, &ndlp->nlp_flag)) {
+			spin_unlock_irqrestore(&ndlp->lock, flags);
 			lpfc_nlp_put(ndlp);
+		} else {
+			spin_unlock_irqrestore(&ndlp->lock, flags);
+		}
 
 		goto fdisc_failed;
 	}
diff --git a/drivers/scsi/lpfc/lpfc_hbadisc.c b/drivers/scsi/lpfc/lpfc_hbadisc.c
index 4c673dffa671..57cdd669928c 100644
--- a/drivers/scsi/lpfc/lpfc_hbadisc.c
+++ b/drivers/scsi/lpfc/lpfc_hbadisc.c
@@ -4951,6 +4951,13 @@ lpfc_drop_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp)
 	 */
 	if (ndlp->nlp_state == NLP_STE_UNUSED_NODE)
 		return;
+
+	lpfc_printf_vlog(vport, KERN_INFO, LOG_NODE | LOG_ELS | LOG_DISCOVERY,
+			"3421 Mark ndlp x%px Dropped. DID x%06x, nflags x%lx "
+			"xflags x%x ref_cnt %d\n",
+			 ndlp, ndlp->nlp_DID, ndlp->nlp_flag,
+			 ndlp->fc4_xpt_flags, kref_read(&ndlp->kref));
+
 	lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNUSED_NODE);
 	if (vport->phba->sli_rev == LPFC_SLI_REV4) {
 		lpfc_cleanup_vports_rrqs(vport, ndlp);
diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c
index 6460127bcc7b..7352cb6e584b 100644
--- a/drivers/scsi/lpfc/lpfc_init.c
+++ b/drivers/scsi/lpfc/lpfc_init.c
@@ -13514,6 +13514,9 @@ lpfc_sli4_hba_unset(struct lpfc_hba *phba)
 	/* Stop the SLI4 device port */
 	if (phba->pport)
 		phba->pport->work_port_events = 0;
+
+	/* All IO completed and queues released. Free the IOCBs. */
+	lpfc_free_iocb_list(phba);
 }
 
 /*
@@ -14948,11 +14951,20 @@ lpfc_pci_remove_one_s4(struct pci_dev *pdev)
 
 	/* Perform scsi free before driver resource_unset since scsi
 	 * buffers are released to their corresponding pools here.
+	 * lpfc_sli4_hba_unset() issues aborts via lpfc_sli_hba_iocb_abort(),
+	 * which allocates abort IOCBs from phba->lpfc_iocb_list; the pool
+	 * must still exist, so lpfc_free_iocb_list() runs only after unset.
 	 */
 	lpfc_io_free(phba);
-	lpfc_free_iocb_list(phba);
-	lpfc_sli4_hba_unset(phba);
 
+	/* Flush the PHBA WQ - there could be a race with ELS IOs while lpfc
+	 * is unloading.  This stops a race between completions, aborts and
+	 * resource recovery.
+	 */
+	if (phba->wq)
+		flush_workqueue(phba->wq);
+
+	lpfc_sli4_hba_unset(phba);
 	lpfc_unset_driver_resource_phase2(phba);
 	lpfc_sli4_driver_resource_unset(phba);
 
diff --git a/drivers/scsi/lpfc/lpfc_nportdisc.c b/drivers/scsi/lpfc/lpfc_nportdisc.c
index 9c449055a55e..fb8844c69491 100644
--- a/drivers/scsi/lpfc/lpfc_nportdisc.c
+++ b/drivers/scsi/lpfc/lpfc_nportdisc.c
@@ -220,6 +220,7 @@ lpfc_check_elscmpl_iocb(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
  */
 void
 lpfc_els_abort(struct lpfc_hba *phba, struct lpfc_nodelist *ndlp)
+	__context_unsafe(/*conditional locking*/)
 {
 	LIST_HEAD(abort_list);
 	LIST_HEAD(drv_cmpl_list);
@@ -227,6 +228,11 @@ lpfc_els_abort(struct lpfc_hba *phba, struct lpfc_nodelist *ndlp)
 	struct lpfc_iocbq *iocb, *next_iocb;
 	int retval = 0;
 
+	/* Exit early to prevent race with queue teardown. */
+	if (unlikely(phba->sli_rev == LPFC_SLI_REV4 &&
+		     !test_bit(HBA_SETUP, &phba->hba_flag)))
+		return;
+
 	pring = lpfc_phba_elsring(phba);
 
 	/* In case of error recovery path, we might have a NULL pring here */
@@ -250,8 +256,9 @@ lpfc_els_abort(struct lpfc_hba *phba, struct lpfc_nodelist *ndlp)
 	spin_lock_irq(&phba->hbalock);
 	if (phba->sli_rev == LPFC_SLI_REV4)
 		spin_lock(&pring->ring_lock);
+
 	list_for_each_entry_safe(iocb, next_iocb, &pring->txcmplq, list) {
-	/* Add to abort_list on on NDLP match. */
+		/* Add to abort_list on NDLP match. */
 		if (lpfc_check_sli_ndlp(phba, pring, iocb, ndlp))
 			list_add_tail(&iocb->dlist, &abort_list);
 	}
@@ -266,7 +273,13 @@ lpfc_els_abort(struct lpfc_hba *phba, struct lpfc_nodelist *ndlp)
 		retval = lpfc_sli_issue_abort_iotag(phba, pring, iocb, NULL);
 		spin_unlock_irq(&phba->hbalock);
 
-		if (retval && test_bit(FC_UNLOADING, &phba->pport->load_flag)) {
+		/* An abort that fails here is just cancelled when the driver is
+		 * going offline.  However, if the abort failure is because the
+		 * IOCB is already getting aborted, don't cancel.  Just let it
+		 * complete.
+		 */
+		if (test_bit(FC_UNLOADING, &phba->pport->load_flag) &&
+		    retval && retval != IOCB_ABORTING) {
 			list_del_init(&iocb->list);
 			list_add_tail(&iocb->list, &drv_cmpl_list);
 		}
@@ -2866,6 +2879,20 @@ lpfc_device_rm_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
 		set_bit(NLP_NODEV_REMOVE, &ndlp->nlp_flag);
 		return ndlp->nlp_state;
 	}
+
+	/* It is an error to drop a node while either of its transport
+	 * registrations have not completed.
+	 */
+	if (ndlp->fc4_xpt_flags & (SCSI_XPT_REGD | NVME_XPT_REGD)) {
+		lpfc_printf_vlog(vport, KERN_WARNING,
+				 LOG_ELS | LOG_NODE | LOG_DISCOVERY,
+				 "3423 Not dropping ndlp x%px, DID x%x xflags x%x "
+				 "with dev_loss pending. ref_cnt %d\n",
+				 ndlp, ndlp->nlp_DID, ndlp->fc4_xpt_flags,
+				 kref_read(&ndlp->kref));
+		return ndlp->nlp_state;
+	}
+
 	lpfc_drop_node(vport, ndlp);
 	return NLP_STE_FREED_NODE;
 }
diff --git a/drivers/scsi/lpfc/lpfc_scsi.c b/drivers/scsi/lpfc/lpfc_scsi.c
index 8dd876a1a78d..3f39cc065029 100644
--- a/drivers/scsi/lpfc/lpfc_scsi.c
+++ b/drivers/scsi/lpfc/lpfc_scsi.c
@@ -5507,6 +5507,7 @@ void lpfc_vmid_vport_cleanup(struct lpfc_vport *vport)
  **/
 static int
 lpfc_abort_handler(struct scsi_cmnd *cmnd)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct Scsi_Host  *shost = cmnd->device->host;
 	struct fc_rport *rport = starget_to_rport(scsi_target(cmnd->device));
diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c
index cd285e87c278..84fb317a34ed 100644
--- a/drivers/scsi/lpfc/lpfc_sli.c
+++ b/drivers/scsi/lpfc/lpfc_sli.c
@@ -3722,6 +3722,7 @@ lpfc_sli_iocbq_lookup_by_tag(struct lpfc_hba *phba,
 static int
 lpfc_sli_process_sol_iocb(struct lpfc_hba *phba, struct lpfc_sli_ring *pring,
 			  struct lpfc_iocbq *saveq)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct lpfc_iocbq *cmdiocbp;
 	unsigned long iflag;
@@ -12730,8 +12731,12 @@ lpfc_sli_sum_iocb(struct lpfc_vport *vport, uint16_t tgt_id, uint64_t lun_id,
 
 		if (!iocbq || iocbq->vport != vport)
 			continue;
-		if (!(iocbq->cmd_flag & LPFC_IO_FCP) ||
-		    !(iocbq->cmd_flag & LPFC_IO_ON_TXCMPLQ))
+		/* Only count FCP i/o */
+		if (!(iocbq->cmd_flag & LPFC_IO_FCP))
+			continue;
+		/* Count i/o whilst LLDD retains an interest in the scsi_cmnd */
+		if (!(iocbq->cmd_flag &
+				(LPFC_IO_ON_TXCMPLQ | LPFC_DRIVER_ABORTED)))
 			continue;
 
 		/* Include counting outstanding aborts */
@@ -12876,6 +12881,7 @@ lpfc_sli_abort_iocb(struct lpfc_vport *vport, u16 tgt_id, u64 lun_id,
 int
 lpfc_sli_abort_taskmgmt(struct lpfc_vport *vport, struct lpfc_sli_ring *pring,
 			uint16_t tgt_id, uint64_t lun_id, lpfc_ctx_cmd cmd)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct lpfc_hba *phba = vport->phba;
 	struct lpfc_io_buf *lpfc_cmd;
diff --git a/drivers/scsi/lpfc/lpfc_version.h b/drivers/scsi/lpfc/lpfc_version.h
index d6e6e436fbfc..7df63d118234 100644
--- a/drivers/scsi/lpfc/lpfc_version.h
+++ b/drivers/scsi/lpfc/lpfc_version.h
@@ -20,7 +20,7 @@
  * included with this package.                                     *
  *******************************************************************/
 
-#define LPFC_DRIVER_VERSION "15.0.0.0"
+#define LPFC_DRIVER_VERSION "15.0.0.1"
 #define LPFC_DRIVER_NAME		"lpfc"
 
 /* Used for SLI 2/3 */
diff --git a/drivers/scsi/megaraid/megaraid_sas_base.c b/drivers/scsi/megaraid/megaraid_sas_base.c
index 46aebe52c3da..1064c5baae8e 100644
--- a/drivers/scsi/megaraid/megaraid_sas_base.c
+++ b/drivers/scsi/megaraid/megaraid_sas_base.c
@@ -7886,7 +7886,9 @@ megasas_resume(struct device *dev)
 			goto fail_init_mfi;
 	}
 
-	if (megasas_get_ctrl_info(instance) != DCMD_SUCCESS)
+	scoped_guard(mutex, &instance->reset_mutex)
+		rval = megasas_get_ctrl_info(instance);
+	if (rval != DCMD_SUCCESS)
 		goto fail_init_mfi;
 
 	tasklet_init(&instance->isr_tasklet, instance->instancet->tasklet,
diff --git a/drivers/scsi/mpi3mr/mpi3mr_app.c b/drivers/scsi/mpi3mr/mpi3mr_app.c
index 5184d9d516a8..eadad89bfcfb 100644
--- a/drivers/scsi/mpi3mr/mpi3mr_app.c
+++ b/drivers/scsi/mpi3mr/mpi3mr_app.c
@@ -3082,7 +3082,7 @@ void mpi3mr_bsg_init(struct mpi3mr_ioc *mrioc)
 	}
 
 	q = bsg_setup_queue(bsg_dev, dev_name(bsg_dev), &lim,
-			mpi3mr_bsg_request, NULL, 0);
+			mpi3mr_bsg_request, NULL, 0, SCSI_SENSE_BUFFERSIZE);
 	if (IS_ERR(q)) {
 		ioc_err(mrioc, "%s: bsg registration failed\n",
 		    dev_name(bsg_dev));
diff --git a/drivers/scsi/mpt3sas/Makefile b/drivers/scsi/mpt3sas/Makefile
index 18e2d87eb4a2..c698a106f3e3 100644
--- a/drivers/scsi/mpt3sas/Makefile
+++ b/drivers/scsi/mpt3sas/Makefile
@@ -1,5 +1,8 @@
 # SPDX-License-Identifier: GPL-2.0
 # mpt3sas makefile
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_MPT3SAS) += mpt3sas.o
 mpt3sas-y +=  mpt3sas_base.o     \
 		mpt3sas_config.o \
diff --git a/drivers/scsi/mvsas/Makefile b/drivers/scsi/mvsas/Makefile
index 75849258e898..7f45cca38127 100644
--- a/drivers/scsi/mvsas/Makefile
+++ b/drivers/scsi/mvsas/Makefile
@@ -7,6 +7,8 @@
 # Copyright 2009-2011 Marvell. <yuxiangl@marvell.com>
 #
 
+CONTEXT_ANALYSIS := y
+
 ccflags-$(CONFIG_SCSI_MVSAS_DEBUG) := -DMV_DEBUG
 
 obj-$(CONFIG_SCSI_MVSAS) += mvsas.o
diff --git a/drivers/scsi/mvsas/mv_sas.c b/drivers/scsi/mvsas/mv_sas.c
index 359226e80eae..d604aaac14a2 100644
--- a/drivers/scsi/mvsas/mv_sas.c
+++ b/drivers/scsi/mvsas/mv_sas.c
@@ -1055,6 +1055,7 @@ void mvs_update_phyinfo(struct mvs_info *mvi, int i, int get_st)
 }
 
 static void mvs_port_notify_formed(struct asd_sas_phy *sas_phy, int lock)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct sas_ha_struct *sas_ha = sas_phy->ha;
 	struct mvs_info *mvi = NULL; int i = 0, hi;
@@ -1153,6 +1154,7 @@ static void mvs_free_dev(struct mvs_device *mvi_dev)
 }
 
 static int mvs_dev_found_notify(struct domain_device *dev, int lock)
+	__context_unsafe(/*conditional locking*/)
 {
 	unsigned long flags = 0;
 	int res = 0;
@@ -1517,6 +1519,7 @@ static int mvs_slot_err(struct mvs_info *mvi, struct sas_task *task,
 }
 
 int mvs_slot_complete(struct mvs_info *mvi, u32 rx_desc, u32 flags)
+	__must_hold(&mvi->lock)
 {
 	u32 slot_idx = rx_desc & RXQ_SLOT_MASK;
 	struct mvs_slot_info *slot = &mvi->slot_info[slot_idx];
@@ -1644,6 +1647,7 @@ int mvs_slot_complete(struct mvs_info *mvi, u32 rx_desc, u32 flags)
 
 void mvs_do_release_task(struct mvs_info *mvi,
 		int phy_no, struct domain_device *dev)
+	__must_hold(&mvi->lock)
 {
 	u32 slot_idx;
 	struct mvs_phy *phy;
@@ -1677,6 +1681,7 @@ void mvs_do_release_task(struct mvs_info *mvi,
 
 void mvs_release_task(struct mvs_info *mvi,
 		      struct domain_device *dev)
+	__must_hold(&mvi->lock)
 {
 	int i, phyno[WIDE_PORT_MAX_PHY], num;
 	num = mvs_find_dev_phyno(dev, phyno);
@@ -1769,6 +1774,7 @@ static void mvs_sig_time_out(struct timer_list *t)
 }
 
 void mvs_int_port(struct mvs_info *mvi, int phy_no, u32 events)
+	__must_hold(&mvi->lock)
 {
 	u32 tmp;
 	struct mvs_phy *phy = &mvi->phy[phy_no];
@@ -1862,6 +1868,7 @@ void mvs_int_port(struct mvs_info *mvi, int phy_no, u32 events)
 }
 
 int mvs_int_rx(struct mvs_info *mvi, bool self_clear)
+	__must_hold(&mvi->lock)
 {
 	u32 rx_prod_idx, rx_desc;
 	bool attn = false;
diff --git a/drivers/scsi/pcmcia/Makefile b/drivers/scsi/pcmcia/Makefile
index 02f5b44a2685..06ea2bfcd42a 100644
--- a/drivers/scsi/pcmcia/Makefile
+++ b/drivers/scsi/pcmcia/Makefile
@@ -1,5 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
 
+CONTEXT_ANALYSIS := y
+
 ccflags-y		:= -I $(srctree)/drivers/scsi
 
 # 16-bit client drivers
diff --git a/drivers/scsi/pm8001/Makefile b/drivers/scsi/pm8001/Makefile
index bbb51b7312f1..b236359810fe 100644
--- a/drivers/scsi/pm8001/Makefile
+++ b/drivers/scsi/pm8001/Makefile
@@ -4,6 +4,7 @@
 #
 # Copyright (C) 2008-2009  USI Co., Ltd.
 
+CONTEXT_ANALYSIS := y
 
 obj-$(CONFIG_SCSI_PM8001) += pm80xx.o
 
diff --git a/drivers/scsi/pm8001/pm8001_init.c b/drivers/scsi/pm8001/pm8001_init.c
index 54b35893261a..5af81c73a8f8 100644
--- a/drivers/scsi/pm8001/pm8001_init.c
+++ b/drivers/scsi/pm8001/pm8001_init.c
@@ -58,15 +58,15 @@ MODULE_PARM_DESC(link_rate, "Enable link rate.\n"
 
 bool pm8001_use_msix = true;
 module_param_named(use_msix, pm8001_use_msix, bool, 0444);
-MODULE_PARM_DESC(zoned, "Use MSIX interrupts. Default: true");
+MODULE_PARM_DESC(use_msix, "Use MSIX interrupts. Default: true");
 
 static bool pm8001_use_tasklet = true;
 module_param_named(use_tasklet, pm8001_use_tasklet, bool, 0444);
-MODULE_PARM_DESC(zoned, "Use MSIX interrupts. Default: true");
+MODULE_PARM_DESC(use_tasklet, "Use tasklets for interrupt handling. Default: true");
 
 static bool pm8001_read_wwn = true;
 module_param_named(read_wwn, pm8001_read_wwn, bool, 0444);
-MODULE_PARM_DESC(zoned, "Get WWN from the controller. Default: true");
+MODULE_PARM_DESC(read_wwn, "Get WWN from the controller. Default: true");
 
 uint pcs_event_log_severity = 0x03;
 module_param(pcs_event_log_severity, int, 0644);
diff --git a/drivers/scsi/pm8001/pm80xx_hwi.c b/drivers/scsi/pm8001/pm80xx_hwi.c
index 659dbd603a03..d2572dd66071 100644
--- a/drivers/scsi/pm8001/pm80xx_hwi.c
+++ b/drivers/scsi/pm8001/pm80xx_hwi.c
@@ -2294,6 +2294,7 @@ static void mpi_ssp_event(struct pm8001_hba_info *pm8001_ha, void *piomb)
 static void
 mpi_sata_completion(struct pm8001_hba_info *pm8001_ha,
 		struct outbound_queue_table *circularQ, void *piomb)
+	__must_hold(&circularQ->oq_lock)
 {
 	struct sas_task *t;
 	struct pm8001_ccb_info *ccb;
@@ -3856,6 +3857,7 @@ static int ssp_coalesced_comp_resp(struct pm8001_hba_info *pm8001_ha,
  */
 static void process_one_iomb(struct pm8001_hba_info *pm8001_ha,
 		struct outbound_queue_table *circularQ, void *piomb)
+	__must_hold(&circularQ->oq_lock)
 {
 	__le32 pHeader = *(__le32 *)piomb;
 	u32 opc = (u32)((le32_to_cpu(pHeader)) & 0xFFF);
diff --git a/drivers/scsi/qedf/Makefile b/drivers/scsi/qedf/Makefile
index c46287826fb8..465982ba5dae 100644
--- a/drivers/scsi/qedf/Makefile
+++ b/drivers/scsi/qedf/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_QEDF) := qedf.o
 qedf-y = qedf_dbg.o qedf_main.o qedf_io.o qedf_fip.o \
 	 qedf_attr.o qedf_els.o drv_scsi_fw_funcs.o drv_fcoe_fw_funcs.o
diff --git a/drivers/scsi/qedi/Makefile b/drivers/scsi/qedi/Makefile
index d84eedfd031b..f081d047b6eb 100644
--- a/drivers/scsi/qedi/Makefile
+++ b/drivers/scsi/qedi/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_QEDI) := qedi.o
 qedi-y := qedi_main.o qedi_iscsi.o qedi_fw.o qedi_sysfs.o \
 	    qedi_dbg.o qedi_fw_api.o
diff --git a/drivers/scsi/qedi/qedi_fw.c b/drivers/scsi/qedi/qedi_fw.c
index 854efa4f61d8..c8af10c32653 100644
--- a/drivers/scsi/qedi/qedi_fw.c
+++ b/drivers/scsi/qedi/qedi_fw.c
@@ -73,7 +73,7 @@ static void qedi_process_logout_resp(struct qedi_ctx *qedi,
 	spin_unlock(&qedi_conn->list_lock);
 
 	cmd->state = RESPONSE_RECEIVED;
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr, NULL, 0);
 
 	spin_unlock(&session->back_lock);
 }
@@ -138,7 +138,7 @@ static void qedi_process_text_resp(struct qedi_ctx *qedi,
 
 	cmd->state = RESPONSE_RECEIVED;
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr_ptr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr_ptr,
 			     qedi_conn->gen_pdu.resp_buf,
 			     (qedi_conn->gen_pdu.resp_wr_ptr -
 			      qedi_conn->gen_pdu.resp_buf));
@@ -163,7 +163,8 @@ static void qedi_tmf_resp_work(struct work_struct *work)
 		goto exit_tmf_resp;
 
 	spin_lock(&session->back_lock);
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr_ptr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr_ptr, NULL,
+			     0);
 	spin_unlock(&session->back_lock);
 
 exit_tmf_resp:
@@ -247,7 +248,8 @@ static void qedi_process_tmf_resp(struct qedi_ctx *qedi,
 	}
 	spin_unlock(&qedi_conn->tmf_work_lock);
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr_ptr, NULL, 0);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr_ptr, NULL,
+			     0);
 	kfree(resp_hdr_ptr);
 
 unblock_sess:
@@ -304,7 +306,7 @@ static void qedi_process_login_resp(struct qedi_ctx *qedi,
 
 	memset(task_ctx, '\0', sizeof(*task_ctx));
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr_ptr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr_ptr,
 			     qedi_conn->gen_pdu.resp_buf,
 			     (qedi_conn->gen_pdu.resp_wr_ptr -
 			     qedi_conn->gen_pdu.resp_buf));
@@ -470,7 +472,8 @@ static int qedi_process_nopin_mesg(struct qedi_ctx *qedi,
 	}
 
 done:
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, bdq_data, pdu_len);
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr, bdq_data,
+			     pdu_len);
 
 	spin_unlock_bh(&session->back_lock);
 	return tgt_async_nop;
@@ -524,7 +527,7 @@ static void qedi_process_async_mesg(struct qedi_ctx *qedi,
 	resp_hdr->param2 = cpu_to_be16(cqe_async_msg->param2_rsrv);
 	resp_hdr->param3 = cpu_to_be16(cqe_async_msg->param3_rsrv);
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)resp_hdr, bdq_data,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)resp_hdr, bdq_data,
 			     pdu_len);
 
 	spin_unlock_bh(&session->back_lock);
@@ -567,7 +570,7 @@ static void qedi_process_reject_mesg(struct qedi_ctx *qedi,
 	hdr->statsn = cpu_to_be32(cqe_reject->stat_sn);
 	hdr->ffffffff = cpu_to_be32(0xffffffff);
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr,
 			     conn->data, pld_len);
 	spin_unlock_bh(&session->back_lock);
 }
@@ -664,7 +667,7 @@ static void qedi_scsi_completion(struct qedi_ctx *qedi,
 	if (qedi_io_tracing)
 		qedi_trace_io(qedi, task, cmd->task_id, QEDI_IO_TRACE_RSP);
 
-	__iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr,
+	__iscsi_complete_pdu(session, conn, (struct iscsi_hdr *)hdr,
 			     conn->data, datalen);
 error:
 	spin_unlock_bh(&session->back_lock);
@@ -722,7 +725,7 @@ static void qedi_process_nopin_local_cmpl(struct qedi_ctx *qedi,
 	cmd->state = RESPONSE_RECEIVED;
 
 	spin_lock_bh(&session->back_lock);
-	__iscsi_put_task(task);
+	__iscsi_put_task(session, task);
 	spin_unlock_bh(&session->back_lock);
 }
 
@@ -1134,6 +1137,7 @@ int qedi_send_iscsi_logout(struct qedi_conn *qedi_conn,
 
 int qedi_cleanup_all_io(struct qedi_ctx *qedi, struct qedi_conn *qedi_conn,
 			struct iscsi_task *task, bool in_recovery)
+	__context_unsafe(/*conditional locking*/)
 {
 	int rval;
 	struct iscsi_task *ctask;
@@ -1316,6 +1320,7 @@ static void qedi_abort_work(struct work_struct *work)
 	struct qedi_conn *qedi_conn = qedi_cmd->conn;
 	struct qedi_ctx *qedi = qedi_conn->qedi;
 	struct iscsi_conn *conn = qedi_conn->cls_conn->dd_data;
+	struct iscsi_session *session = conn->session;
 	struct qedi_work_map *list_work = NULL;
 	struct iscsi_task *mtask;
 	struct qedi_cmd *cmd;
@@ -1326,16 +1331,16 @@ static void qedi_abort_work(struct work_struct *work)
 	mtask = qedi_cmd->task;
 	tmf_hdr = (struct iscsi_tm *)mtask->hdr;
 
-	spin_lock_bh(&conn->session->back_lock);
-	ctask = iscsi_itt_to_ctask(conn, tmf_hdr->rtt);
+	spin_lock_bh(&session->back_lock);
+	ctask = iscsi_itt_to_ctask(session, conn, tmf_hdr->rtt);
 	if (!ctask) {
-		spin_unlock_bh(&conn->session->back_lock);
+		spin_unlock_bh(&session->back_lock);
 		QEDI_ERR(&qedi->dbg_ctx, "Invalid RTT. Letting abort timeout.\n");
 		goto clear_cleanup;
 	}
 
 	if (iscsi_task_is_completed(ctask)) {
-		spin_unlock_bh(&conn->session->back_lock);
+		spin_unlock_bh(&session->back_lock);
 		QEDI_INFO(&qedi->dbg_ctx, QEDI_LOG_INFO,
 			  "Task already completed\n");
 		/*
@@ -1344,7 +1349,7 @@ static void qedi_abort_work(struct work_struct *work)
 		 */
 		goto send_tmf;
 	}
-	spin_unlock_bh(&conn->session->back_lock);
+	spin_unlock_bh(&session->back_lock);
 
 	cmd = (struct qedi_cmd *)ctask->dd_data;
 	QEDI_INFO(&qedi->dbg_ctx, QEDI_LOG_INFO,
diff --git a/drivers/scsi/qedi/qedi_main.c b/drivers/scsi/qedi/qedi_main.c
index 227ff7bd1bdc..f394fcbb97e7 100644
--- a/drivers/scsi/qedi/qedi_main.c
+++ b/drivers/scsi/qedi/qedi_main.c
@@ -2652,8 +2652,6 @@ static int __qedi_probe(struct pci_dev *pdev, int mode)
 	snprintf(host_buf, sizeof(host_buf), "host_%d", qedi->shost->host_no);
 	qedi_ops->common->set_name(qedi->cdev, host_buf);
 
-	qedi_ops->register_ops(qedi->cdev, &qedi_cb_ops, qedi);
-
 	memset(&params, 0, sizeof(params));
 	params.mtu = DEF_PATH_MTU + IPV6_HDR_LEN + TCP_HDR_LEN;
 	qedi->ll2_mtu = DEF_PATH_MTU;
@@ -2670,6 +2668,7 @@ static int __qedi_probe(struct pci_dev *pdev, int mode)
 		spin_lock_init(&qedi->task_idx_lock);
 		mutex_init(&qedi->stats_lock);
 	}
+	qedi_ops->register_ops(qedi->cdev, &qedi_cb_ops, qedi);
 	qedi_ops->ll2->register_cb_ops(qedi->cdev, &qedi_ll2_cb_ops, qedi);
 	qedi_ops->ll2->start(qedi->cdev, &params);
 
diff --git a/drivers/scsi/qla1280.c b/drivers/scsi/qla1280.c
index 348c59a99cc5..f71e668d011c 100644
--- a/drivers/scsi/qla1280.c
+++ b/drivers/scsi/qla1280.c
@@ -735,15 +735,16 @@ static void qla1280_mailbox_timeout(struct timer_list *t)
 }
 
 static int
-_qla1280_wait_for_single_command(struct scsi_qla_host *ha, struct srb *sp,
+_qla1280_wait_for_single_command(struct Scsi_Host *host, struct srb *sp,
 				 struct completion *wait)
+	__must_hold(&host->host_lock)
 {
 	int	status = FAILED;
 	struct scsi_cmnd *cmd = sp->cmd;
 
-	spin_unlock_irq(&ha->host->host_lock);
+	spin_unlock_irq(&host->host_lock);
 	wait_for_completion_timeout(wait, 4*HZ);
-	spin_lock_irq(&ha->host->host_lock);
+	spin_lock_irq(&host->host_lock);
 	sp->wait = NULL;
 	if(CMD_HANDLE(cmd) == COMPLETED_HANDLE) {
 		status = SUCCESS;
@@ -753,16 +754,19 @@ _qla1280_wait_for_single_command(struct scsi_qla_host *ha, struct srb *sp,
 }
 
 static int
-qla1280_wait_for_single_command(struct scsi_qla_host *ha, struct srb *sp)
+qla1280_wait_for_single_command(struct Scsi_Host *host, struct srb *sp)
+	__must_hold(&host->host_lock)
 {
 	DECLARE_COMPLETION_ONSTACK(wait);
 
 	sp->wait = &wait;
-	return _qla1280_wait_for_single_command(ha, sp, &wait);
+	return _qla1280_wait_for_single_command(host, sp, &wait);
 }
 
 static int
-qla1280_wait_for_pending_commands(struct scsi_qla_host *ha, int bus, int target)
+qla1280_wait_for_pending_commands(struct scsi_qla_host *ha, struct Scsi_Host *host,
+				  int bus, int target)
+	__must_hold(&host->host_lock)
 {
 	int		cnt;
 	int		status;
@@ -785,7 +789,7 @@ qla1280_wait_for_pending_commands(struct scsi_qla_host *ha, int bus, int target)
 			if (target >= 0 && SCSI_TCN_32(cmd) != target)
 				continue;
 
-			status = qla1280_wait_for_single_command(ha, sp);
+			status = qla1280_wait_for_single_command(host, sp);
 			if (status == FAILED)
 				break;
 		}
@@ -808,7 +812,9 @@ qla1280_wait_for_pending_commands(struct scsi_qla_host *ha, int bus, int target)
  *
  **************************************************************************/
 static int
-qla1280_error_action(struct scsi_cmnd *cmd, enum action action)
+qla1280_error_action(struct Scsi_Host *host, struct scsi_cmnd *cmd,
+		     enum action action)
+	__must_hold(&host->host_lock)
 {
 	struct scsi_qla_host *ha;
 	int bus, target, lun;
@@ -914,7 +920,7 @@ qla1280_error_action(struct scsi_cmnd *cmd, enum action action)
 	 */
 
 	if (found >= 0)
-		result = _qla1280_wait_for_single_command(ha, sp, &wait);
+		result = _qla1280_wait_for_single_command(host, sp, &wait);
 
 	if (action == ABORT_COMMAND && result != SUCCESS) {
 		printk(KERN_WARNING
@@ -934,7 +940,7 @@ qla1280_error_action(struct scsi_cmnd *cmd, enum action action)
 	 * to wait for them.
 	 */
 	if (result == SUCCESS && wait_for_bus >= 0) {
-		result = qla1280_wait_for_pending_commands(ha,
+		result = qla1280_wait_for_pending_commands(ha, host,
 					wait_for_bus, wait_for_target);
 	}
 
@@ -951,11 +957,12 @@ qla1280_error_action(struct scsi_cmnd *cmd, enum action action)
 static int
 qla1280_eh_abort(struct scsi_cmnd * cmd)
 {
+	struct Scsi_Host *host = cmd->device->host;
 	int rc;
 
-	spin_lock_irq(&cmd->device->host->host_lock);
-	rc = qla1280_error_action(cmd, ABORT_COMMAND);
-	spin_unlock_irq(&cmd->device->host->host_lock);
+	spin_lock_irq(&host->host_lock);
+	rc = qla1280_error_action(host, cmd, ABORT_COMMAND);
+	spin_unlock_irq(&host->host_lock);
 
 	return rc;
 }
@@ -967,11 +974,12 @@ qla1280_eh_abort(struct scsi_cmnd * cmd)
 static int
 qla1280_eh_device_reset(struct scsi_cmnd *cmd)
 {
+	struct Scsi_Host *host = cmd->device->host;
 	int rc;
 
-	spin_lock_irq(&cmd->device->host->host_lock);
-	rc = qla1280_error_action(cmd, DEVICE_RESET);
-	spin_unlock_irq(&cmd->device->host->host_lock);
+	spin_lock_irq(&host->host_lock);
+	rc = qla1280_error_action(host, cmd, DEVICE_RESET);
+	spin_unlock_irq(&host->host_lock);
 
 	return rc;
 }
@@ -983,11 +991,12 @@ qla1280_eh_device_reset(struct scsi_cmnd *cmd)
 static int
 qla1280_eh_bus_reset(struct scsi_cmnd *cmd)
 {
+	struct Scsi_Host *host = cmd->device->host;
 	int rc;
 
-	spin_lock_irq(&cmd->device->host->host_lock);
-	rc = qla1280_error_action(cmd, BUS_RESET);
-	spin_unlock_irq(&cmd->device->host->host_lock);
+	spin_lock_irq(&host->host_lock);
+	rc = qla1280_error_action(host, cmd, BUS_RESET);
+	spin_unlock_irq(&host->host_lock);
 
 	return rc;
 }
@@ -1490,6 +1499,7 @@ qla1280_initialize_adapter(struct scsi_qla_host *ha)
  */
 static const struct firmware *
 qla1280_request_firmware(struct scsi_qla_host *ha)
+	__must_hold(&ha->host->host_lock)
 {
 	const struct firmware *fw;
 	int err;
@@ -1655,6 +1665,7 @@ qla1280_chip_diag(struct scsi_qla_host *ha)
 
 static int
 qla1280_load_firmware_pio(struct scsi_qla_host *ha)
+	__must_hold(&ha->host->host_lock)
 {
 	/* enter with host_lock acquired */
 
@@ -1705,6 +1716,7 @@ qla1280_load_firmware_pio(struct scsi_qla_host *ha)
 #define DUMP_IT_BACK 0		/* for debug of RISC loading */
 static int
 qla1280_load_firmware_dma(struct scsi_qla_host *ha)
+	__must_hold(&ha->host->host_lock)
 {
 	/* enter with host_lock acquired */
 	const struct firmware *fw;
@@ -1844,6 +1856,7 @@ qla1280_start_firmware(struct scsi_qla_host *ha)
 
 static int
 qla1280_load_firmware(struct scsi_qla_host *ha)
+	__must_hold(&ha->host->host_lock)
 {
 	/* enter with host_lock taken */
 	int err;
@@ -2413,6 +2426,7 @@ qla1280_nv_write(struct scsi_qla_host *ha, uint16_t data)
  */
 static int
 qla1280_mailbox_command(struct scsi_qla_host *ha, uint8_t mr, uint16_t *mb)
+	__must_hold(&ha->host->host_lock)
 {
 	struct device_reg __iomem *reg = ha->iobase;
 	int status = 0;
@@ -2538,6 +2552,7 @@ qla1280_poll(struct scsi_qla_host *ha)
  */
 static int
 qla1280_bus_reset(struct scsi_qla_host *ha, int bus)
+	__must_hold(&ha->host->host_lock)
 {
 	uint16_t mb[MAILBOX_REGISTER_COUNT];
 	uint16_t reset_delay;
@@ -2598,6 +2613,7 @@ qla1280_bus_reset(struct scsi_qla_host *ha, int bus)
  */
 static int
 qla1280_device_reset(struct scsi_qla_host *ha, int bus, int target)
+	__must_hold(&ha->host->host_lock)
 {
 	uint16_t mb[MAILBOX_REGISTER_COUNT];
 	int status;
@@ -2632,6 +2648,7 @@ qla1280_device_reset(struct scsi_qla_host *ha, int bus, int target)
  */
 static int
 qla1280_abort_command(struct scsi_qla_host *ha, struct srb * sp, int handle)
+	__must_hold(&ha->host->host_lock)
 {
 	uint16_t mb[MAILBOX_REGISTER_COUNT];
 	unsigned int bus, target, lun;
@@ -3749,6 +3766,7 @@ qla1280_error_entry(struct scsi_qla_host *ha, struct response *pkt,
  */
 static int
 qla1280_abort_isp(struct scsi_qla_host *ha)
+	__must_hold(&ha->host->host_lock)
 {
 	struct device_reg __iomem *reg = ha->iobase;
 	struct srb *sp;
@@ -3881,6 +3899,7 @@ qla1280_check_for_dead_scsi_bus(struct scsi_qla_host *ha, unsigned int bus)
 static void
 qla1280_get_target_parameters(struct scsi_qla_host *ha,
 			      struct scsi_device *device)
+	__must_hold(&ha->host->host_lock)
 {
 	uint16_t mb[MAILBOX_REGISTER_COUNT];
 	int bus, target, lun;
diff --git a/drivers/scsi/qla2xxx/Makefile b/drivers/scsi/qla2xxx/Makefile
index cbc1303e761e..095657510cc3 100644
--- a/drivers/scsi/qla2xxx/Makefile
+++ b/drivers/scsi/qla2xxx/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 qla2xxx-y := qla_os.o qla_init.o qla_mbx.o qla_iocb.o qla_isr.o qla_gs.o \
 		qla_dbg.o qla_sup.o qla_attr.o qla_mid.o qla_dfs.o qla_bsg.o \
 		qla_nx.o qla_mr.o qla_nx2.o qla_target.o qla_tmpl.o qla_nvme.o \
diff --git a/drivers/scsi/qla2xxx/qla_nx.c b/drivers/scsi/qla2xxx/qla_nx.c
index 2366cca51bce..1a9a0f148bb3 100644
--- a/drivers/scsi/qla2xxx/qla_nx.c
+++ b/drivers/scsi/qla2xxx/qla_nx.c
@@ -431,6 +431,7 @@ static int qla82xx_crb_win_lock(struct qla_hw_data *ha)
 
 int
 qla82xx_wr_32(struct qla_hw_data *ha, ulong off_in, u32 data)
+	__context_unsafe(/*conditional locking*/)
 {
 	void __iomem *off;
 	unsigned long flags = 0;
@@ -461,6 +462,7 @@ qla82xx_wr_32(struct qla_hw_data *ha, ulong off_in, u32 data)
 
 int
 qla82xx_rd_32(struct qla_hw_data *ha, ulong off_in)
+	__context_unsafe(/*conditional locking*/)
 {
 	void __iomem *off;
 	unsigned long flags = 0;
diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c
index c0efdbff5da7..3c412c7fb6fe 100644
--- a/drivers/scsi/qla2xxx/qla_os.c
+++ b/drivers/scsi/qla2xxx/qla_os.c
@@ -352,7 +352,7 @@ MODULE_PARM_DESC(ql2xnvme_queues,
 
 int ql2xfc2target = 1;
 module_param(ql2xfc2target, int, 0444);
-MODULE_PARM_DESC(qla2xfc2target,
+MODULE_PARM_DESC(ql2xfc2target,
 		  "Enables FC2 Target support. "
 		  "0 - FC2 Target support is disabled. "
 		  "1 - FC2 Target support is enabled (default).");
diff --git a/drivers/scsi/qla2xxx/qla_target.c b/drivers/scsi/qla2xxx/qla_target.c
index 431a59d499b3..5a7caff61b16 100644
--- a/drivers/scsi/qla2xxx/qla_target.c
+++ b/drivers/scsi/qla2xxx/qla_target.c
@@ -383,11 +383,13 @@ static bool qlt_24xx_atio_pkt_all_vps(struct scsi_qla_host *vha,
 			    vha->vp_idx, entry->vp_index);
 			break;
 		}
-		if (!ha_locked)
+		if (!ha_locked) {
 			spin_lock_irqsave(&host->hw->hardware_lock, flags);
-		qlt_24xx_handle_abts(host, (struct abts_recv_from_24xx *)atio);
-		if (!ha_locked)
+			qlt_24xx_handle_abts(host, (struct abts_recv_from_24xx *)atio);
 			spin_unlock_irqrestore(&host->hw->hardware_lock, flags);
+		} else {
+			qlt_24xx_handle_abts(host, (struct abts_recv_from_24xx *)atio);
+		}
 		break;
 	}
 
@@ -3775,6 +3777,7 @@ static int __qlt_send_term_exchange(struct qla_qpair *qpair,
  */
 void qlt_send_term_exchange(struct qla_qpair *qpair,
 	struct qla_tgt_cmd *cmd, struct atio_from_isp *atio, int ha_locked)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct scsi_qla_host *vha;
 	unsigned long flags = 0;
@@ -6728,11 +6731,13 @@ qlt_chk_qfull_thresh_hold(struct scsi_qla_host *vha, struct qla_qpair *qpair,
 	if (ha->tgt.num_pend_cmds < Q_FULL_THRESH_HOLD(ha))
 		return 0;
 
-	if (!ha_locked)
+	if (!ha_locked) {
 		spin_lock_irqsave(&ha->hardware_lock, flags);
-	qlt_send_busy(qpair, atio, qla_sam_status);
-	if (!ha_locked)
+		qlt_send_busy(qpair, atio, qla_sam_status);
 		spin_unlock_irqrestore(&ha->hardware_lock, flags);
+	} else {
+		qlt_send_busy(qpair, atio, qla_sam_status);
+	}
 
 	return 1;
 }
@@ -6741,6 +6746,7 @@ qlt_chk_qfull_thresh_hold(struct scsi_qla_host *vha, struct qla_qpair *qpair,
 /* called via callback from qla2xxx */
 static void qlt_24xx_atio_pkt(struct scsi_qla_host *vha,
 	struct atio_from_isp *atio, uint8_t ha_locked)
+	__context_unsafe(/*conditional locking*/)
 {
 	struct qla_hw_data *ha = vha->hw;
 	struct qla_tgt *tgt = vha->vha_tgt.qla_tgt;
@@ -6767,12 +6773,13 @@ static void qlt_24xx_atio_pkt(struct scsi_qla_host *vha,
 			    "qla_target(%d): ATIO_TYPE7 "
 			    "received with UNKNOWN exchange address, "
 			    "sending QUEUE_FULL\n", vha->vp_idx);
-			if (!ha_locked)
+			if (!ha_locked) {
 				spin_lock_irqsave(&ha->hardware_lock, flags);
-			qlt_send_busy(ha->base_qpair, atio, qla_sam_status);
-			if (!ha_locked)
-				spin_unlock_irqrestore(&ha->hardware_lock,
-				    flags);
+				qlt_send_busy(ha->base_qpair, atio, qla_sam_status);
+				spin_unlock_irqrestore(&ha->hardware_lock, flags);
+			} else {
+				qlt_send_busy(ha->base_qpair, atio, qla_sam_status);
+			}
 			break;
 		}
 
diff --git a/drivers/scsi/qla2xxx/qla_tmpl.c b/drivers/scsi/qla2xxx/qla_tmpl.c
index fd3984127497..f96b9eb15126 100644
--- a/drivers/scsi/qla2xxx/qla_tmpl.c
+++ b/drivers/scsi/qla2xxx/qla_tmpl.c
@@ -1034,6 +1034,7 @@ qla27xx_fwdt_template_valid(void *p)
 
 void
 qla27xx_mpi_fwdump(scsi_qla_host_t *vha, int hardware_locked)
+	__context_unsafe(/*conditional locking*/)
 {
 	ulong flags = 0;
 
diff --git a/drivers/scsi/qla4xxx/Makefile b/drivers/scsi/qla4xxx/Makefile
index 1f8a9096c744..2178d139f3ca 100644
--- a/drivers/scsi/qla4xxx/Makefile
+++ b/drivers/scsi/qla4xxx/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
+
+CONTEXT_ANALYSIS := y
+
 qla4xxx-y := ql4_os.o ql4_init.o ql4_mbx.o ql4_iocb.o ql4_isr.o \
 		ql4_nx.o ql4_nvram.o ql4_dbg.o ql4_attr.o ql4_bsg.o ql4_83xx.o
 
diff --git a/drivers/scsi/qla4xxx/ql4_isr.c b/drivers/scsi/qla4xxx/ql4_isr.c
index cf52258ecdde..81989c905c82 100644
--- a/drivers/scsi/qla4xxx/ql4_isr.c
+++ b/drivers/scsi/qla4xxx/ql4_isr.c
@@ -367,6 +367,7 @@ static void qla4xxx_passthru_status_entry(struct scsi_qla_host *ha,
 	struct ddb_entry *ddb_entry;
 	struct ql4_task_data *task_data;
 	struct iscsi_cls_conn *cls_conn;
+	struct iscsi_session *session;
 	struct iscsi_conn *conn;
 	itt_t itt;
 	uint32_t fw_ddb_index;
@@ -384,9 +385,10 @@ static void qla4xxx_passthru_status_entry(struct scsi_qla_host *ha,
 
 	cls_conn = ddb_entry->conn;
 	conn = cls_conn->dd_data;
-	spin_lock(&conn->session->back_lock);
-	task = iscsi_itt_to_task(conn, itt);
-	spin_unlock(&conn->session->back_lock);
+	session = conn->session;
+	spin_lock(&session->back_lock);
+	task = iscsi_itt_to_task(session, conn, itt);
+	spin_unlock(&session->back_lock);
 
 	if (task == NULL) {
 		ql4_printk(KERN_ERR, ha, "%s: Task is NULL\n", __func__);
diff --git a/drivers/scsi/qla4xxx/ql4_nx.c b/drivers/scsi/qla4xxx/ql4_nx.c
index f7340cfc990a..6aeb8097a73d 100644
--- a/drivers/scsi/qla4xxx/ql4_nx.c
+++ b/drivers/scsi/qla4xxx/ql4_nx.c
@@ -406,6 +406,7 @@ void qla4_82xx_crb_win_unlock(struct scsi_qla_host *ha)
 
 void
 qla4_82xx_wr_32(struct scsi_qla_host *ha, ulong off, u32 data)
+	__context_unsafe(/*conditional locking*/)
 {
 	unsigned long flags = 0;
 	int rv;
@@ -429,6 +430,7 @@ qla4_82xx_wr_32(struct scsi_qla_host *ha, ulong off, u32 data)
 }
 
 uint32_t qla4_82xx_rd_32(struct scsi_qla_host *ha, ulong off)
+	__context_unsafe(/*conditional locking*/)
 {
 	unsigned long flags = 0;
 	int rv;
diff --git a/drivers/scsi/scsi.c b/drivers/scsi/scsi.c
index 3af9e77847f7..05232ab6366f 100644
--- a/drivers/scsi/scsi.c
+++ b/drivers/scsi/scsi.c
@@ -728,6 +728,7 @@ int scsi_cdl_enable(struct scsi_device *sdev, bool enable)
 		struct scsi_mode_data data;
 		struct scsi_sense_hdr sshdr;
 		char *buf_data;
+		size_t avail, offset;
 		int len;
 
 		ret = scsi_mode_sense(sdev, 0x08, 0x0a, 0xf2, buf, sizeof(buf),
@@ -736,11 +737,24 @@ int scsi_cdl_enable(struct scsi_device *sdev, bool enable)
 			return -EINVAL;
 
 		/* Enable or disable CDL using the ATA feature page */
-		len = min_t(size_t, sizeof(buf),
-			    data.length - data.header_length -
-			    data.block_descriptor_length);
-		buf_data = buf + data.header_length +
-			data.block_descriptor_length;
+		avail = min_t(size_t, data.length, sizeof(buf));
+		if (data.header_length > avail)
+			return -EINVAL;
+
+		offset = data.header_length;
+		avail -= data.header_length;
+
+		if (data.block_descriptor_length > avail)
+			return -EINVAL;
+
+		offset += data.block_descriptor_length;
+		avail -= data.block_descriptor_length;
+
+		if (avail < 5)
+			return -EINVAL;
+
+		buf_data = buf + offset;
+		len = avail;
 
 		/*
 		 * If we want to enable CDL and CDL is already enabled on the
diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c
index e679df1993aa..a922c8318a2f 100644
--- a/drivers/scsi/scsi_debug.c
+++ b/drivers/scsi/scsi_debug.c
@@ -4052,24 +4052,27 @@ static inline struct sdeb_store_info *devip2sip(struct sdebug_dev_info *devip,
 
 static inline void
 sdeb_read_lock(rwlock_t *lock)
+	__acquires_shared(lock)
 {
 	if (sdebug_no_rwlock)
-		__acquire(lock);
+		__acquire_shared(lock);
 	else
 		read_lock(lock);
 }
 
 static inline void
 sdeb_read_unlock(rwlock_t *lock)
+	__releases_shared(lock)
 {
 	if (sdebug_no_rwlock)
-		__release(lock);
+		__release_shared(lock);
 	else
 		read_unlock(lock);
 }
 
 static inline void
 sdeb_write_lock(rwlock_t *lock)
+	__acquires(lock)
 {
 	if (sdebug_no_rwlock)
 		__acquire(lock);
@@ -4079,6 +4082,7 @@ sdeb_write_lock(rwlock_t *lock)
 
 static inline void
 sdeb_write_unlock(rwlock_t *lock)
+	__releases(lock)
 {
 	if (sdebug_no_rwlock)
 		__release(lock);
@@ -4088,6 +4092,7 @@ sdeb_write_unlock(rwlock_t *lock)
 
 static inline void
 sdeb_data_read_lock(struct sdeb_store_info *sip)
+	__acquires_shared(&sip->macc_data_lck)
 {
 	BUG_ON(!sip);
 
@@ -4096,6 +4101,7 @@ sdeb_data_read_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_read_unlock(struct sdeb_store_info *sip)
+	__releases_shared(&sip->macc_data_lck)
 {
 	BUG_ON(!sip);
 
@@ -4104,6 +4110,7 @@ sdeb_data_read_unlock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_write_lock(struct sdeb_store_info *sip)
+	__acquires(&sip->macc_data_lck)
 {
 	BUG_ON(!sip);
 
@@ -4112,6 +4119,7 @@ sdeb_data_write_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_write_unlock(struct sdeb_store_info *sip)
+	__releases(&sip->macc_data_lck)
 {
 	BUG_ON(!sip);
 
@@ -4120,6 +4128,7 @@ sdeb_data_write_unlock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_sector_read_lock(struct sdeb_store_info *sip)
+	__acquires_shared(&sip->macc_sector_lck)
 {
 	BUG_ON(!sip);
 
@@ -4128,6 +4137,7 @@ sdeb_data_sector_read_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_sector_read_unlock(struct sdeb_store_info *sip)
+	__releases_shared(&sip->macc_sector_lck)
 {
 	BUG_ON(!sip);
 
@@ -4136,6 +4146,7 @@ sdeb_data_sector_read_unlock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_sector_write_lock(struct sdeb_store_info *sip)
+	__acquires(&sip->macc_sector_lck)
 {
 	BUG_ON(!sip);
 
@@ -4144,6 +4155,7 @@ sdeb_data_sector_write_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_sector_write_unlock(struct sdeb_store_info *sip)
+	__releases(&sip->macc_sector_lck)
 {
 	BUG_ON(!sip);
 
@@ -4165,50 +4177,67 @@ sdeb_data_sector_write_unlock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_data_lock(struct sdeb_store_info *sip, bool atomic)
+	__acquires(&sip->macc_data_lck)
 {
-	if (atomic)
+	if (atomic) {
 		sdeb_data_write_lock(sip);
-	else
+	} else {
 		sdeb_data_read_lock(sip);
+		__release_shared(&sip->macc_data_lck);
+		__acquire(&sip->macc_data_lck);
+	}
 }
 
 static inline void
 sdeb_data_unlock(struct sdeb_store_info *sip, bool atomic)
+	__releases(&sip->macc_data_lck)
 {
-	if (atomic)
+	if (atomic) {
 		sdeb_data_write_unlock(sip);
-	else
+	} else {
+		__release(&sip->macc_data_lck);
+		__acquire_shared(&sip->macc_data_lck);
 		sdeb_data_read_unlock(sip);
+	}
 }
 
 /* Allow many reads but only 1x write per sector */
 static inline void
 sdeb_data_sector_lock(struct sdeb_store_info *sip, bool do_write)
+	__acquires(&sip->macc_sector_lck)
 {
-	if (do_write)
+	if (do_write) {
 		sdeb_data_sector_write_lock(sip);
-	else
+	} else {
 		sdeb_data_sector_read_lock(sip);
+		__release_shared(&sip->macc_sector_lck);
+		__acquire(&sip->macc_sector_lck);
+	}
 }
 
 static inline void
 sdeb_data_sector_unlock(struct sdeb_store_info *sip, bool do_write)
+	__releases(&sip->macc_sector_lck)
 {
-	if (do_write)
+	if (do_write) {
 		sdeb_data_sector_write_unlock(sip);
-	else
+	} else {
+		__release(&sip->macc_sector_lck);
+		__acquire_shared(&sip->macc_sector_lck);
 		sdeb_data_sector_read_unlock(sip);
+	}
 }
 
 static inline void
 sdeb_meta_read_lock(struct sdeb_store_info *sip)
-{
-	if (sdebug_no_rwlock) {
-		if (sip)
-			__acquire(&sip->macc_meta_lck);
-		else
-			__acquire(&sdeb_fake_rw_lck);
-	} else {
+	__acquires_shared(&sip->macc_meta_lck)
+	__context_unsafe(/*
+			  * Can't be annotated with
+			  * __{acquire,release}(,_shared}() without triggering
+			  * undefined behavior.
+			  */)
+{
+	if (!sdebug_no_rwlock) {
 		if (sip)
 			read_lock(&sip->macc_meta_lck);
 		else
@@ -4218,13 +4247,14 @@ sdeb_meta_read_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_meta_read_unlock(struct sdeb_store_info *sip)
-{
-	if (sdebug_no_rwlock) {
-		if (sip)
-			__release(&sip->macc_meta_lck);
-		else
-			__release(&sdeb_fake_rw_lck);
-	} else {
+	__releases_shared(&sip->macc_meta_lck)
+	__context_unsafe(/*
+			  * Can't be annotated with
+			  * __{acquire,release}(,_shared}() without triggering
+			  * undefined behavior.
+			  */)
+{
+	if (!sdebug_no_rwlock) {
 		if (sip)
 			read_unlock(&sip->macc_meta_lck);
 		else
@@ -4234,13 +4264,14 @@ sdeb_meta_read_unlock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_meta_write_lock(struct sdeb_store_info *sip)
-{
-	if (sdebug_no_rwlock) {
-		if (sip)
-			__acquire(&sip->macc_meta_lck);
-		else
-			__acquire(&sdeb_fake_rw_lck);
-	} else {
+	__acquires(&sip->macc_meta_lck)
+	__context_unsafe(/*
+			  * Can't be annotated with
+			  * __{acquire,release}(,_shared}() without triggering
+			  * undefined behavior.
+			  */)
+{
+	if (!sdebug_no_rwlock) {
 		if (sip)
 			write_lock(&sip->macc_meta_lck);
 		else
@@ -4250,13 +4281,14 @@ sdeb_meta_write_lock(struct sdeb_store_info *sip)
 
 static inline void
 sdeb_meta_write_unlock(struct sdeb_store_info *sip)
-{
-	if (sdebug_no_rwlock) {
-		if (sip)
-			__release(&sip->macc_meta_lck);
-		else
-			__release(&sdeb_fake_rw_lck);
-	} else {
+	__releases(&sip->macc_meta_lck)
+	__context_unsafe(/*
+			  * Can't be annotated with
+			  * __{acquire,release}(,_shared}() without triggering
+			  * undefined behavior.
+			  */)
+{
+	if (!sdebug_no_rwlock) {
 		if (sip)
 			write_unlock(&sip->macc_meta_lck);
 		else
@@ -4608,6 +4640,70 @@ static int resp_read_tape(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	return 0;
 }
 
+/*
+ * Returns 0 upon success or -1 with *scsi_status set to a SCSI status code upon
+ * failure.
+ */
+static int __resp_read_dt0_dix(struct scsi_cmnd *scp, u64 lba, u32 num,
+			       u32 ei_lba, int *scsi_status)
+{
+	const u8 *const cmd = scp->cmnd;
+
+	switch (prot_verify_read(scp, lba, num, ei_lba)) {
+	case 1: /* Guard tag error */
+		if (cmd[1] >> 5 != 3) { /* RDPROTECT != 3 */
+			mk_sense_buffer(scp, ABORTED_COMMAND,
+					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
+			*scsi_status = check_condition_result;
+			return -1;
+		}
+		if (scp->prot_flags & SCSI_PROT_GUARD_CHECK) {
+			mk_sense_buffer(scp, ILLEGAL_REQUEST,
+					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
+			*scsi_status = illegal_condition_result;
+			return -1;
+		}
+		break;
+	case 3: /* Reference tag error */
+		if (cmd[1] >> 5 != 3) { /* RDPROTECT != 3 */
+			mk_sense_buffer(scp, ABORTED_COMMAND,
+				LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
+			*scsi_status = check_condition_result;
+			return -1;
+		}
+		if (scp->prot_flags & SCSI_PROT_REF_CHECK) {
+			mk_sense_buffer(scp, ILLEGAL_REQUEST,
+				LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
+			*scsi_status = illegal_condition_result;
+			return -1;
+		}
+		break;
+	}
+	return 0;
+}
+
+/*
+ * Returns the number of bytes transferred, or -1 with *scsi_status set to a
+ * SCSI status code on failure.
+ */
+static int __resp_read_dt0(struct scsi_cmnd *scp, struct sdeb_store_info *sip,
+			   u64 lba, u32 num, u32 ei_lba, int *scsi_status)
+{
+	int ret;
+
+	/* DIX + T10 DIF */
+	if (unlikely(sdebug_dix && scsi_prot_sg_count(scp))) {
+		ret = __resp_read_dt0_dix(scp, lba, num, ei_lba, scsi_status);
+		if (ret < 0)
+			return ret;
+	}
+
+	ret = do_device_access(sip, scp, 0, lba, num, 0, false, false);
+	if (ret < 0)
+		*scsi_status = DID_ERROR << 16;
+	return ret;
+}
+
 static int resp_read_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 {
 	bool check_prot;
@@ -4617,7 +4713,7 @@ static int resp_read_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	u64 lba;
 	struct sdeb_store_info *sip = devip2sip(devip, true);
 	u8 *cmd = scp->cmnd;
-	bool meta_data_locked = false;
+	int scsi_status;
 
 	switch (cmd[0]) {
 	case READ_16:
@@ -4699,48 +4795,16 @@ static int resp_read_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	}
 
 	if (sdebug_dev_is_zoned(devip) ||
-	    (sdebug_dix && scsi_prot_sg_count(scp)))  {
+	    (sdebug_dix && scsi_prot_sg_count(scp))) {
 		sdeb_meta_read_lock(sip);
-		meta_data_locked = true;
-	}
-
-	/* DIX + T10 DIF */
-	if (unlikely(sdebug_dix && scsi_prot_sg_count(scp))) {
-		switch (prot_verify_read(scp, lba, num, ei_lba)) {
-		case 1: /* Guard tag error */
-			if (cmd[1] >> 5 != 3) { /* RDPROTECT != 3 */
-				sdeb_meta_read_unlock(sip);
-				mk_sense_buffer(scp, ABORTED_COMMAND,
-					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
-				return check_condition_result;
-			} else if (scp->prot_flags & SCSI_PROT_GUARD_CHECK) {
-				sdeb_meta_read_unlock(sip);
-				mk_sense_buffer(scp, ILLEGAL_REQUEST,
-					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
-				return illegal_condition_result;
-			}
-			break;
-		case 3: /* Reference tag error */
-			if (cmd[1] >> 5 != 3) { /* RDPROTECT != 3 */
-				sdeb_meta_read_unlock(sip);
-				mk_sense_buffer(scp, ABORTED_COMMAND,
-				      LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
-				return check_condition_result;
-			} else if (scp->prot_flags & SCSI_PROT_REF_CHECK) {
-				sdeb_meta_read_unlock(sip);
-				mk_sense_buffer(scp, ILLEGAL_REQUEST,
-				      LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
-				return illegal_condition_result;
-			}
-			break;
-		}
+		ret = __resp_read_dt0(scp, sip, lba, num, ei_lba, &scsi_status);
+		sdeb_meta_read_unlock(sip);
+	} else {
+		ret = __resp_read_dt0(scp, sip, lba, num, ei_lba, &scsi_status);
 	}
 
-	ret = do_device_access(sip, scp, 0, lba, num, 0, false, false);
-	if (meta_data_locked)
-		sdeb_meta_read_unlock(sip);
-	if (unlikely(ret == -1))
-		return DID_ERROR << 16;
+	if (unlikely(ret < 0))
+		return scsi_status;
 
 	scsi_set_resid(scp, scsi_bufflen(scp) - ret);
 
@@ -4984,37 +5048,25 @@ static int resp_write_tape(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	return 0;
 }
 
-static int corrupt_lbas(struct sdebug_dev_info *devip, u64 lba, u32 num,
-		u32 nr_bit_errors, s32 reftag_adjust)
+static int __corrupt_lbas(struct sdeb_store_info *sip, u64 lba, u32 num,
+			  u32 nr_bit_errors, s32 reftag_adjust, bool lbp)
 {
-	struct sdeb_store_info *sip = devip2sip(devip, false);
-	bool meta_data_locked = false;
-	bool lbp = scsi_debug_lbp();
 	u32 block, num_mapped, b, i;
-	int error = 0;
-
-	if (sdebug_dev_is_zoned(devip) || sdebug_dix || lbp) {
-		sdeb_meta_write_lock(sip);
-		meta_data_locked = true;
-	}
 
 	if (!sip) {
 		pr_err("can't corrupt with fake_rw\n");
-		error = -EINVAL;
-		goto out_unlock;
+		return -EINVAL;
 	}
 
 	if (num > sdebug_capacity || lba > sdebug_capacity - num) {
 		pr_err("logical blocks out of bounds: %llu:%u", lba, num);
-		error = -EINVAL;
-		goto out_unlock;
+		return -EINVAL;
 	}
 
 	if (lbp && (!map_state(sip, lba, &num_mapped) || num > num_mapped)) {
 		pr_err("can't modify unmapped logical blocks: %llu:%u",
 			lba, num);
-		error = -EINVAL;
-		goto out_unlock;
+		return -EINVAL;
 	}
 
 	/*
@@ -5052,12 +5104,107 @@ static int corrupt_lbas(struct sdebug_dev_info *devip, u64 lba, u32 num,
 	}
 	sdeb_data_unlock(sip, false);
 
-out_unlock:
-	if (meta_data_locked)
+	return 0;
+}
+
+static int corrupt_lbas(struct sdebug_dev_info *devip, u64 lba, u32 num,
+			u32 nr_bit_errors, s32 reftag_adjust)
+{
+	struct sdeb_store_info *sip = devip2sip(devip, false);
+	const bool lbp = scsi_debug_lbp();
+	int error = 0;
+
+	if (sdebug_dev_is_zoned(devip) || sdebug_dix || lbp) {
+		sdeb_meta_write_lock(sip);
+		error = __corrupt_lbas(sip, lba, num, nr_bit_errors,
+				       reftag_adjust, lbp);
 		sdeb_meta_write_unlock(sip);
+	} else {
+		error = __corrupt_lbas(sip, lba, num, nr_bit_errors,
+				       reftag_adjust, lbp);
+	}
 	return error;
 }
 
+/*
+ * Returns 0 upon success or -1 with *scsi_status set to a SCSI status code upon
+ * failure.
+ */
+static int __resp_write_dt0_dix(struct scsi_cmnd *scp,
+				u64 lba, u32 num,
+				u32 ei_lba, int *scsi_status)
+{
+	switch (prot_verify_write(scp, lba, num, ei_lba)) {
+	case 1: /* Guard tag error */
+		if (scp->prot_flags & SCSI_PROT_GUARD_CHECK) {
+			mk_sense_buffer(scp, ILLEGAL_REQUEST,
+					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
+			*scsi_status = illegal_condition_result;
+			return -1;
+		}
+		if (scp->cmnd[1] >> 5 != 3) { /* WRPROTECT != 3 */
+			mk_sense_buffer(scp, ABORTED_COMMAND,
+					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
+			*scsi_status = check_condition_result;
+			return -1;
+		}
+		break;
+	case 3: /* Reference tag error */
+		if (scp->prot_flags & SCSI_PROT_REF_CHECK) {
+			mk_sense_buffer(scp, ILLEGAL_REQUEST,
+				LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
+			*scsi_status = illegal_condition_result;
+			return -1;
+		}
+		if (scp->cmnd[1] >> 5 != 3) { /* WRPROTECT != 3 */
+			mk_sense_buffer(scp, ABORTED_COMMAND,
+				LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
+			*scsi_status = check_condition_result;
+			return -1;
+		}
+		break;
+	}
+
+	return 0;
+}
+
+/*
+ * Returns the number of bytes transferred, or -1 with *scsi_status set to a
+ * SCSI status code on failure.
+ */
+static int __resp_write_dt0(struct scsi_cmnd *scp,
+			    struct sdebug_dev_info *devip,
+			    struct sdeb_store_info *sip, u64 lba, u32 num,
+			    u32 ei_lba, u8 group, bool lbp, int *scsi_status)
+{
+	int ret;
+
+	*scsi_status = check_device_access_params(scp, lba, num, true);
+	if (*scsi_status)
+		return -1;
+
+	/* DIX + T10 DIF */
+	if (unlikely(sdebug_dix && scsi_prot_sg_count(scp))) {
+		ret = __resp_write_dt0_dix(scp, lba, num, ei_lba,
+					   scsi_status);
+		if (ret < 0)
+			return ret;
+	}
+
+	ret = do_device_access(sip, scp, 0, lba, num, group, true, false);
+	if (ret < 0)
+		*scsi_status = DID_ERROR << 16;
+
+	if (unlikely(lbp))
+		map_region(sip, lba, num);
+
+	/* If ZBC zone then bump its write pointer */
+	if (sdebug_dev_is_zoned(devip) && ret > 0)
+		zbc_inc_wp(devip, lba, ret >> ilog2(sdebug_sector_size));
+
+	return ret;
+}
+
 static int resp_write_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 {
 	bool check_prot;
@@ -5068,7 +5215,7 @@ static int resp_write_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	u64 lba;
 	struct sdeb_store_info *sip = devip2sip(devip, true);
 	u8 *cmd = scp->cmnd;
-	bool meta_data_locked = false;
+	int scsi_status = DID_ERROR << 16;
 	bool lbp = scsi_debug_lbp();
 
 	if (unlikely(sdebug_opts & SDEBUG_OPT_UNALIGNED_WRITE &&
@@ -5138,60 +5285,16 @@ static int resp_write_dt0(struct scsi_cmnd *scp, struct sdebug_dev_info *devip)
 	if (sdebug_dev_is_zoned(devip) ||
 	    (sdebug_dix && scsi_prot_sg_count(scp)) || lbp) {
 		sdeb_meta_write_lock(sip);
-		meta_data_locked = true;
-	}
-
-	ret = check_device_access_params(scp, lba, num, true);
-	if (ret) {
-		if (meta_data_locked)
-			sdeb_meta_write_unlock(sip);
-		return ret;
-	}
-
-	/* DIX + T10 DIF */
-	if (unlikely(sdebug_dix && scsi_prot_sg_count(scp))) {
-		switch (prot_verify_write(scp, lba, num, ei_lba)) {
-		case 1: /* Guard tag error */
-			if (scp->prot_flags & SCSI_PROT_GUARD_CHECK) {
-				sdeb_meta_write_unlock(sip);
-				mk_sense_buffer(scp, ILLEGAL_REQUEST,
-					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
-				return illegal_condition_result;
-			} else if (scp->cmnd[1] >> 5 != 3) { /* WRPROTECT != 3 */
-				sdeb_meta_write_unlock(sip);
-				mk_sense_buffer(scp, ABORTED_COMMAND,
-					LOGICAL_BLOCK_GUARD_CHECK_FAILED);
-				return check_condition_result;
-			}
-			break;
-		case 3: /* Reference tag error */
-			if (scp->prot_flags & SCSI_PROT_REF_CHECK) {
-				sdeb_meta_write_unlock(sip);
-				mk_sense_buffer(scp, ILLEGAL_REQUEST,
-					LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
-				return illegal_condition_result;
-			} else if (scp->cmnd[1] >> 5 != 3) { /* WRPROTECT != 3 */
-				sdeb_meta_write_unlock(sip);
-				mk_sense_buffer(scp, ABORTED_COMMAND,
-					LOGICAL_BLOCK_REFERENCE_TAG_CHECK_FAILED);
-				return check_condition_result;
-			}
-			break;
-		}
-	}
-
-	ret = do_device_access(sip, scp, 0, lba, num, group, true, false);
-	if (unlikely(lbp))
-		map_region(sip, lba, num);
-
-	/* If ZBC zone then bump its write pointer over the data written */
-	if (sdebug_dev_is_zoned(devip) && ret > 0)
-		zbc_inc_wp(devip, lba, ret >> ilog2(sdebug_sector_size));
-	if (meta_data_locked)
+		ret = __resp_write_dt0(scp, devip, sip, lba, num, ei_lba, group,
+				       lbp, &scsi_status);
 		sdeb_meta_write_unlock(sip);
+	} else {
+		ret = __resp_write_dt0(scp, devip, sip, lba, num, ei_lba, group,
+				       lbp, &scsi_status);
+	}
 
 	if (unlikely(-1 == ret))
-		return DID_ERROR << 16;
+		return scsi_status;
 	else if (unlikely(sdebug_verbose &&
 			  (ret < (num * sdebug_sector_size))))
 		sdev_printk(KERN_INFO, scp->device,
@@ -5412,8 +5515,8 @@ static int resp_write_scat(struct scsi_cmnd *scp,
 	return ret;
 }
 
-static int resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num,
-			   u32 ei_lba, bool unmap, bool ndob)
+static int __resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num,
+			     u32 ei_lba, bool unmap, bool ndob, bool lbp)
 {
 	struct scsi_device *sdp = scp->device;
 	struct sdebug_dev_info *devip = (struct sdebug_dev_info *)sdp->hostdata;
@@ -5425,21 +5528,14 @@ static int resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num,
 						scp->device->hostdata, true);
 	u8 *fs1p;
 	u8 *fsp;
-	bool meta_data_locked = false;
-	bool lbp = scsi_debug_lbp();
-
-	if (sdebug_dev_is_zoned(devip) || lbp) {
-		sdeb_meta_write_lock(sip);
-		meta_data_locked = true;
-	}
 
 	ret = check_device_access_params(scp, lba, num, true);
 	if (ret)
-		goto out;
+		return ret;
 
 	if (unmap && lbp) {
 		unmap_region(sip, lba, num);
-		goto out;
+		return ret;
 	}
 	lbaa = lba;
 	block = do_div(lbaa, sdebug_store_sectors);
@@ -5455,7 +5551,7 @@ static int resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num,
 
 	if (-1 == ret) {
 		ret = DID_ERROR << 16;
-		goto out;
+		goto unlock;
 	} else if (sdebug_verbose && !ndob && (ret < lb_size))
 		sdev_printk(KERN_INFO, scp->device,
 			    "%s: %s: lb size=%u, IO sent=%d bytes\n",
@@ -5472,11 +5568,31 @@ static int resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num,
 	/* If ZBC zone then bump its write pointer */
 	if (sdebug_dev_is_zoned(devip))
 		zbc_inc_wp(devip, lba, num);
-	sdeb_data_write_unlock(sip);
 	ret = 0;
-out:
-	if (meta_data_locked)
+unlock:
+	sdeb_data_write_unlock(sip);
+	return ret;
+}
+
+static int resp_write_same(struct scsi_cmnd *scp, u64 lba, u32 num, u32 ei_lba,
+			   bool unmap, bool ndob)
+{
+	struct scsi_device *sdp = scp->device;
+	struct sdebug_dev_info *devip = sdp->hostdata;
+	struct sdeb_store_info *sip = devip2sip(devip, true);
+	const bool lbp = scsi_debug_lbp();
+	int ret;
+
+	if (sdebug_dev_is_zoned(devip) || lbp) {
+		sdeb_meta_write_lock(sip);
+		ret = __resp_write_same(scp, lba, num, ei_lba, unmap, ndob,
+					lbp);
 		sdeb_meta_write_unlock(sip);
+	} else {
+		ret = __resp_write_same(scp, lba, num, ei_lba, unmap, ndob,
+					lbp);
+	}
+
 	return ret;
 }
 
@@ -6268,16 +6384,16 @@ static int resp_atomic_write(struct scsi_cmnd *scp,
 	if (scsi_bufflen(scp) < len * sdebug_sector_size)
 		return DID_ERROR << 16;
 
-	if (lbp)
-		sdeb_meta_write_lock(sip);
-
-	ret = do_device_access(sip, scp, 0, lba, len, 0, true, true);
 	if (lbp) {
+		sdeb_meta_write_lock(sip);
+		ret = do_device_access(sip, scp, 0, lba, len, 0, true, true);
 		map_region(sip, lba, len);
 		sdeb_meta_write_unlock(sip);
+	} else {
+		ret = do_device_access(sip, scp, 0, lba, len, 0, true, true);
 	}
 
-	if (unlikely(ret == -1))
+	if (unlikely(ret < 0))
 		return DID_ERROR << 16;
 	if (unlikely(ret != len * sdebug_sector_size))
 		return DID_ERROR << 16;
diff --git a/drivers/scsi/scsi_devinfo.c b/drivers/scsi/scsi_devinfo.c
index 2bccadf4f22f..cfc259fd0141 100644
--- a/drivers/scsi/scsi_devinfo.c
+++ b/drivers/scsi/scsi_devinfo.c
@@ -161,7 +161,7 @@ static struct {
 	{"DGC", "DISK", NULL, BLIST_SPARSELUN},	/* EMC CLARiiON, no storage on LUN 0 */
 	{"EMC",  "Invista", "*", BLIST_SPARSELUN | BLIST_LARGELUN},
 	{"EMC", "SYMMETRIX", NULL, BLIST_SPARSELUN | BLIST_LARGELUN |
-	 BLIST_REPORTLUN2 | BLIST_RETRY_ITF},
+	 BLIST_REPORTLUN2 | BLIST_RETRY_ITF | BLIST_SKIP_IO_HINTS},
 	{"EMULEX", "MD21/S2     ESDI", NULL, BLIST_SINGLELUN},
 	{"easyRAID", "16P", NULL, BLIST_NOREPORTLUN},
 	{"easyRAID", "X6P", NULL, BLIST_NOREPORTLUN},
diff --git a/drivers/scsi/scsi_ioctl.c b/drivers/scsi/scsi_ioctl.c
index 122403ec3ab8..bf049d9cb719 100644
--- a/drivers/scsi/scsi_ioctl.c
+++ b/drivers/scsi/scsi_ioctl.c
@@ -9,6 +9,7 @@
 #include <linux/blkdev.h>
 #include <linux/interrupt.h>
 #include <linux/errno.h>
+#include <linux/jiffies.h>
 #include <linux/kernel.h>
 #include <linux/sched.h>
 #include <linux/mm.h>
@@ -196,10 +197,14 @@ static int sg_set_timeout(struct scsi_device *sdev, int __user *p)
 {
 	int timeout, err = get_user(timeout, p);
 
-	if (!err)
-		sdev->sg_timeout = clock_t_to_jiffies(timeout);
+	if (err)
+		return err;
+	if (timeout < 0)
+		return -EIO;
 
-	return err;
+	sdev->sg_timeout = min(clock_t_to_jiffies(timeout),
+			       min(UINT_MAX, MAX_JIFFY_OFFSET));
+	return 0;
 }
 
 static int sg_get_reserved_size(struct scsi_device *sdev, int __user *p)
diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c
index f695a6605815..ab39514cc0c6 100644
--- a/drivers/scsi/scsi_lib.c
+++ b/drivers/scsi/scsi_lib.c
@@ -1789,6 +1789,20 @@ static void scsi_done_internal(struct scsi_cmnd *cmd, bool complete_directly)
 		blk_mq_complete_request(req);
 }
 
+/**
+ * scsi_done - Notify the SCSI mid-layer that a command has completed
+ * @cmd: Completed SCSI command
+ *
+ * Called by a SCSI low-level driver to notify the SCSI mid-layer that the
+ * command has completed. There are two cases:
+ *
+ * - The SCSI error handler does not own @cmd. In this case scsi_complete()
+ *   decides how to complete the command based on the value of @cmd->result.
+ * - The SCSI error handler owns @cmd because scsi_timeout() has set
+ *   SCMD_STATE_COMPLETE. In this case this function has no effect, @cmd->result
+ *   is ignored and the SCSI error handler decides whether to retry or fail
+ *   @cmd. See also scmd_eh_abort_handler() and scsi_eh_flush_done_q().
+ */
 void scsi_done(struct scsi_cmnd *cmd)
 {
 	scsi_done_internal(cmd, false);
diff --git a/drivers/scsi/scsi_transport_fc.c b/drivers/scsi/scsi_transport_fc.c
index be0efffab2fc..bec6ca38375b 100644
--- a/drivers/scsi/scsi_transport_fc.c
+++ b/drivers/scsi/scsi_transport_fc.c
@@ -4345,7 +4345,8 @@ fc_bsg_hostadd(struct Scsi_Host *shost, struct fc_host_attrs *fc_host)
 	scsi_init_limits(shost, &lim);
 	lim.max_segments = min_not_zero(lim.max_segments, i->f->max_bsg_segments);
 	q = bsg_setup_queue(dev, bsg_name, &lim, fc_bsg_dispatch,
-			fc_bsg_job_timeout, i->f->dd_bsg_size);
+			fc_bsg_job_timeout, i->f->dd_bsg_size,
+			SCSI_SENSE_BUFFERSIZE);
 	if (IS_ERR(q)) {
 		dev_err(dev,
 			"fc_host%d: bsg interface failed to initialize - setup queue\n",
@@ -4378,7 +4379,8 @@ fc_bsg_rportadd(struct Scsi_Host *shost, struct fc_rport *rport)
 	scsi_init_limits(shost, &lim);
 	lim.max_segments = min_not_zero(lim.max_segments, i->f->max_bsg_segments);
 	q = bsg_setup_queue(dev, dev_name(dev), &lim, fc_bsg_dispatch_prep,
-				fc_bsg_job_timeout, i->f->dd_bsg_size);
+				fc_bsg_job_timeout, i->f->dd_bsg_size,
+				SCSI_SENSE_BUFFERSIZE);
 	if (IS_ERR(q)) {
 		dev_err(dev, "failed to setup bsg queue\n");
 		return PTR_ERR(q);
diff --git a/drivers/scsi/scsi_transport_iscsi.c b/drivers/scsi/scsi_transport_iscsi.c
index 8aa76f813bcd..b094af7c997e 100644
--- a/drivers/scsi/scsi_transport_iscsi.c
+++ b/drivers/scsi/scsi_transport_iscsi.c
@@ -1545,7 +1545,7 @@ iscsi_bsg_host_add(struct Scsi_Host *shost, struct iscsi_cls_host *ihost)
 	snprintf(bsg_name, sizeof(bsg_name), "iscsi_host%d", shost->host_no);
 	scsi_init_limits(shost, &lim);
 	q = bsg_setup_queue(dev, bsg_name, &lim, iscsi_bsg_host_dispatch, NULL,
-			0);
+			0, SCSI_SENSE_BUFFERSIZE);
 	if (IS_ERR(q)) {
 		shost_printk(KERN_ERR, shost, "bsg interface failed to "
 			     "initialize - no request queue\n");
@@ -2243,6 +2243,7 @@ static void iscsi_ep_disconnect(struct iscsi_cls_conn *conn, bool is_active)
 static void iscsi_if_disconnect_bound_ep(struct iscsi_cls_conn *conn,
 					 struct iscsi_endpoint *ep,
 					 bool is_active)
+	__must_hold(&conn->ep_mutex)
 {
 	/* Check if this was a conn error and the kernel took ownership */
 	spin_lock_irq(&conn->lock);
diff --git a/drivers/scsi/scsi_transport_sas.c b/drivers/scsi/scsi_transport_sas.c
index d689b9ed08a6..a825966f60e5 100644
--- a/drivers/scsi/scsi_transport_sas.c
+++ b/drivers/scsi/scsi_transport_sas.c
@@ -199,7 +199,8 @@ static int sas_bsg_initialize(struct Scsi_Host *shost, struct sas_rphy *rphy)
 
 	if (rphy) {
 		q = bsg_setup_queue(&rphy->dev, dev_name(&rphy->dev), NULL,
-				sas_smp_dispatch, NULL, 0);
+				sas_smp_dispatch, NULL, 0,
+				SCSI_SENSE_BUFFERSIZE);
 		if (IS_ERR(q))
 			return PTR_ERR(q);
 		rphy->q = q;
@@ -208,7 +209,8 @@ static int sas_bsg_initialize(struct Scsi_Host *shost, struct sas_rphy *rphy)
 
 		snprintf(name, sizeof(name), "sas_host%d", shost->host_no);
 		q = bsg_setup_queue(&shost->shost_gendev, name, NULL,
-				sas_smp_dispatch, NULL, 0);
+				sas_smp_dispatch, NULL, 0,
+				SCSI_SENSE_BUFFERSIZE);
 		if (IS_ERR(q))
 			return PTR_ERR(q);
 		to_sas_host_attrs(shost)->q = q;
diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c
index b0d2542fd317..dc45df819c42 100644
--- a/drivers/scsi/sd.c
+++ b/drivers/scsi/sd.c
@@ -4268,7 +4268,15 @@ static void sd_remove(struct scsi_device *sdp)
 	struct device *dev = &sdp->sdev_gendev;
 	struct scsi_disk *sdkp = dev_get_drvdata(dev);
 
-	scsi_autopm_get_device(sdkp->device);
+	/*
+	 * If runtime resume fails, e.g. because the device was unplugged
+	 * while runtime suspended, the request queue stays in the pm-only
+	 * state and any I/O submitted by del_gendisk(), e.g. from
+	 * sync_filesystem(), would wait forever in __bio_queue_enter().
+	 * Prevent this by marking the disk dead.
+	 */
+	if (scsi_autopm_get_device(sdkp->device) < 0)
+		blk_mark_disk_dead(sdkp->disk);
 
 	device_del(&sdkp->disk_dev);
 	del_gendisk(sdkp->disk);
diff --git a/drivers/scsi/sd_zbc.c b/drivers/scsi/sd_zbc.c
index 8b4850cea10f..8cbf171e6fab 100644
--- a/drivers/scsi/sd_zbc.c
+++ b/drivers/scsi/sd_zbc.c
@@ -589,7 +589,7 @@ int sd_zbc_revalidate_zones(struct scsi_disk *sdkp)
 int sd_zbc_read_zones(struct scsi_disk *sdkp, struct queue_limits *lim,
 		u8 buf[SD_BUF_SIZE])
 {
-	unsigned int nr_zones;
+	u64 nr_zones;
 	u32 zone_blocks = 0;
 	int ret;
 
@@ -621,6 +621,12 @@ int sd_zbc_read_zones(struct scsi_disk *sdkp, struct queue_limits *lim,
 		goto err;
 
 	nr_zones = round_up(sdkp->capacity, zone_blocks) >> ilog2(zone_blocks);
+	if (nr_zones > INT_MAX) {
+		sd_printk(KERN_ERR, sdkp, "Too many zones (%llu)\n",
+			  nr_zones);
+		ret = -EINVAL;
+		goto err;
+	}
 	sdkp->early_zone_info.nr_zones = nr_zones;
 	sdkp->early_zone_info.zone_blocks = zone_blocks;
 
diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c
index 5408f002e6c0..714ae6f0cf18 100644
--- a/drivers/scsi/sg.c
+++ b/drivers/scsi/sg.c
@@ -245,6 +245,7 @@ static int sg_allow_access(struct file *filp, unsigned char *cmd)
 
 static int
 open_wait(Sg_device *sdp, int flags)
+	__must_hold(&sdp->open_rel_lock)
 {
 	int retval = 0;
 
diff --git a/drivers/scsi/smartpqi/Makefile b/drivers/scsi/smartpqi/Makefile
index 28985e508b5c..71db5cd96284 100644
--- a/drivers/scsi/smartpqi/Makefile
+++ b/drivers/scsi/smartpqi/Makefile
@@ -1,3 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_SMARTPQI) += smartpqi.o
 smartpqi-objs := smartpqi_init.o smartpqi_sis.o smartpqi_sas_transport.o
diff --git a/drivers/scsi/smartpqi/smartpqi_init.c b/drivers/scsi/smartpqi/smartpqi_init.c
index d8d0fe915805..9401d9347404 100644
--- a/drivers/scsi/smartpqi/smartpqi_init.c
+++ b/drivers/scsi/smartpqi/smartpqi_init.c
@@ -97,8 +97,12 @@ static int pqi_aio_submit_r56_write_io(struct pqi_ctrl_info *ctrl_info,
 	struct scsi_cmnd *scmd, struct pqi_queue_group *queue_group,
 	struct pqi_encryption_info *encryption_info, struct pqi_scsi_dev *device,
 	struct pqi_scsi_dev_raid_map_data *rmd);
-static void pqi_ofa_ctrl_quiesce(struct pqi_ctrl_info *ctrl_info);
-static void pqi_ofa_ctrl_unquiesce(struct pqi_ctrl_info *ctrl_info);
+static void pqi_ofa_ctrl_quiesce(struct pqi_ctrl_info *ctrl_info)
+	__acquires(&ctrl_info->scan_mutex)
+	__acquires(&ctrl_info->lun_reset_mutex);
+static void pqi_ofa_ctrl_unquiesce(struct pqi_ctrl_info *ctrl_info)
+	__releases(&ctrl_info->lun_reset_mutex)
+	__releases(&ctrl_info->scan_mutex);
 static int pqi_ofa_ctrl_restart(struct pqi_ctrl_info *ctrl_info, unsigned int delay_secs);
 static void pqi_host_setup_buffer(struct pqi_ctrl_info *ctrl_info, struct pqi_host_memory_descriptor *host_memory_descriptor, u32 total_size, u32 min_size);
 static void pqi_host_free_buffer(struct pqi_ctrl_info *ctrl_info, struct pqi_host_memory_descriptor *host_memory_descriptor);
@@ -312,12 +316,14 @@ static inline void pqi_save_fw_triage_setting(struct pqi_ctrl_info *ctrl_info, b
 }
 
 static inline void pqi_ctrl_block_scan(struct pqi_ctrl_info *ctrl_info)
+	__acquires(&ctrl_info->scan_mutex)
 {
 	ctrl_info->scan_blocked = true;
 	mutex_lock(&ctrl_info->scan_mutex);
 }
 
 static inline void pqi_ctrl_unblock_scan(struct pqi_ctrl_info *ctrl_info)
+	__releases(&ctrl_info->scan_mutex)
 {
 	ctrl_info->scan_blocked = false;
 	mutex_unlock(&ctrl_info->scan_mutex);
@@ -329,11 +335,13 @@ static inline bool pqi_ctrl_scan_blocked(struct pqi_ctrl_info *ctrl_info)
 }
 
 static inline void pqi_ctrl_block_device_reset(struct pqi_ctrl_info *ctrl_info)
+	__acquires(&ctrl_info->lun_reset_mutex)
 {
 	mutex_lock(&ctrl_info->lun_reset_mutex);
 }
 
 static inline void pqi_ctrl_unblock_device_reset(struct pqi_ctrl_info *ctrl_info)
+	__releases(&ctrl_info->lun_reset_mutex)
 {
 	mutex_unlock(&ctrl_info->lun_reset_mutex);
 }
@@ -436,11 +444,13 @@ static inline bool pqi_device_offline(struct pqi_scsi_dev *device)
 }
 
 static inline void pqi_ctrl_ofa_start(struct pqi_ctrl_info *ctrl_info)
+	__acquires(&ctrl_info->ofa_mutex)
 {
 	mutex_lock(&ctrl_info->ofa_mutex);
 }
 
 static inline void pqi_ctrl_ofa_done(struct pqi_ctrl_info *ctrl_info)
+	__releases(&ctrl_info->ofa_mutex)
 {
 	mutex_unlock(&ctrl_info->ofa_mutex);
 }
@@ -2305,6 +2315,8 @@ static void pqi_update_device_list(struct pqi_ctrl_info *ctrl_info,
 	 * requests before removal.
 	 */
 	if (pqi_ofa_in_progress(ctrl_info)) {
+		/* What guarantees that &ctrl_info->lun_reset_mutex is held here? */
+		__acquire(&ctrl_info->lun_reset_mutex);
 		list_for_each_entry_safe(device, next, &delete_list, delete_list_entry)
 			if (pqi_is_device_added(device))
 				pqi_device_remove_start(device);
@@ -3672,6 +3684,8 @@ static void pqi_process_soft_reset(struct pqi_ctrl_info *ctrl_info)
 		pqi_save_ctrl_mode(ctrl_info, SIS_MODE);
 		rc = pqi_ofa_ctrl_restart(ctrl_info, delay_secs);
 		pqi_host_free_buffer(ctrl_info, &ctrl_info->ofa_memory);
+		/* What guarantees that &ctrl_info->ofa_mutex is held here? */
+		__acquire(&ctrl_info->ofa_mutex);
 		pqi_ctrl_ofa_done(ctrl_info);
 		dev_info(&ctrl_info->pci_dev->dev,
 				"Online Firmware Activation: %s\n",
@@ -3683,6 +3697,10 @@ static void pqi_process_soft_reset(struct pqi_ctrl_info *ctrl_info)
 		if (ctrl_info->soft_reset_handshake_supported)
 			pqi_clear_soft_reset_status(ctrl_info);
 		pqi_host_free_buffer(ctrl_info, &ctrl_info->ofa_memory);
+		/* What guarantees that these mutexes are held here? */
+		__acquire(&ctrl_info->lun_reset_mutex);
+		__acquire(&ctrl_info->ofa_mutex);
+		__acquire(&ctrl_info->scan_mutex);
 		pqi_ctrl_ofa_done(ctrl_info);
 		pqi_ofa_ctrl_unquiesce(ctrl_info);
 		break;
@@ -3693,6 +3711,10 @@ static void pqi_process_soft_reset(struct pqi_ctrl_info *ctrl_info)
 			"unexpected Online Firmware Activation reset status: 0x%x\n",
 			reset_status);
 		pqi_host_free_buffer(ctrl_info, &ctrl_info->ofa_memory);
+		/* What guarantees that these mutexes are held here? */
+		__acquire(&ctrl_info->lun_reset_mutex);
+		__acquire(&ctrl_info->ofa_mutex);
+		__acquire(&ctrl_info->scan_mutex);
 		pqi_ctrl_ofa_done(ctrl_info);
 		pqi_ofa_ctrl_unquiesce(ctrl_info);
 		pqi_take_ctrl_offline(ctrl_info, PQI_OFA_RESPONSE_TIMEOUT);
@@ -3700,25 +3722,32 @@ static void pqi_process_soft_reset(struct pqi_ctrl_info *ctrl_info)
 	}
 }
 
-static void pqi_ofa_memory_alloc_worker(struct work_struct *work)
+static inline struct pqi_ctrl_info *alloc_work_to_ctrl_info(struct work_struct *work)
 {
-	struct pqi_ctrl_info *ctrl_info;
+	return container_of(work, struct pqi_ctrl_info, ofa_memory_alloc_work);
+}
 
-	ctrl_info = container_of(work, struct pqi_ctrl_info, ofa_memory_alloc_work);
+static void pqi_ofa_memory_alloc_worker(struct work_struct *work)
+	__acquires(&alloc_work_to_ctrl_info(work)->ofa_mutex)
+{
+	struct pqi_ctrl_info *ctrl_info = alloc_work_to_ctrl_info(work);
 
 	pqi_ctrl_ofa_start(ctrl_info);
 	pqi_host_setup_buffer(ctrl_info, &ctrl_info->ofa_memory, ctrl_info->ofa_bytes_requested, ctrl_info->ofa_bytes_requested);
 	pqi_host_memory_update(ctrl_info, &ctrl_info->ofa_memory, PQI_VENDOR_GENERAL_OFA_MEMORY_UPDATE);
 }
 
-static void pqi_ofa_quiesce_worker(struct work_struct *work)
+static inline struct pqi_ctrl_info *quiesce_work_to_ctrl_info(struct work_struct *work)
 {
-	struct pqi_ctrl_info *ctrl_info;
-	struct pqi_event *event;
-
-	ctrl_info = container_of(work, struct pqi_ctrl_info, ofa_quiesce_work);
+	return container_of(work, struct pqi_ctrl_info, ofa_quiesce_work);
+}
 
-	event = &ctrl_info->events[pqi_event_type_to_event_index(PQI_EVENT_TYPE_OFA)];
+static void pqi_ofa_quiesce_worker(struct work_struct *work)
+	__acquires(&quiesce_work_to_ctrl_info(work)->scan_mutex)
+	__acquires(&quiesce_work_to_ctrl_info(work)->lun_reset_mutex)
+{
+	struct pqi_ctrl_info *ctrl_info = quiesce_work_to_ctrl_info(work);
+	struct pqi_event *event = &ctrl_info->events[pqi_event_type_to_event_index(PQI_EVENT_TYPE_OFA)];
 
 	pqi_ofa_ctrl_quiesce(ctrl_info);
 	pqi_acknowledge_event(ctrl_info, event);
@@ -3749,6 +3778,8 @@ static bool pqi_ofa_process_event(struct pqi_ctrl_info *ctrl_info,
 			"received Online Firmware Activation cancel request: reason: %u\n",
 			ctrl_info->ofa_cancel_reason);
 		pqi_host_free_buffer(ctrl_info, &ctrl_info->ofa_memory);
+		/* What guarantees that &ctrl_info->ofa_mutex is held here? */
+		__acquire(&ctrl_info->ofa_mutex);
 		pqi_ctrl_ofa_done(ctrl_info);
 		break;
 	default:
@@ -8893,6 +8924,8 @@ static int pqi_ctrl_init_resume(struct pqi_ctrl_info *ctrl_info)
 	}
 
 	if (pqi_ofa_in_progress(ctrl_info)) {
+		/* What guarantees that &ctrl_info->scan_mutex is held here? */
+		__acquire(&ctrl_info->scan_mutex);
 		pqi_ctrl_unblock_scan(ctrl_info);
 		if (ctrl_info->ctrl_logging_supported) {
 			if (!ctrl_info->ctrl_log_memory.host_memory)
@@ -9653,7 +9686,11 @@ static inline enum bmic_flush_cache_shutdown_event pqi_get_flush_cache_shutdown_
 	return SUSPEND;
 }
 
+#define TO_CTRL_INFO(dev) ((struct pqi_ctrl_info *)pci_get_drvdata(to_pci_dev(dev)))
+
 static int pqi_suspend_or_freeze(struct device *dev, bool suspend)
+	__acquires(&TO_CTRL_INFO(dev)->scan_mutex)
+	__acquires(&TO_CTRL_INFO(dev)->lun_reset_mutex)
 {
 	struct pci_dev *pci_dev;
 	struct pqi_ctrl_info *ctrl_info;
@@ -9687,11 +9724,15 @@ static int pqi_suspend_or_freeze(struct device *dev, bool suspend)
 }
 
 static __maybe_unused int pqi_suspend(struct device *dev)
+	__acquires(&TO_CTRL_INFO(dev)->scan_mutex)
+	__acquires(&TO_CTRL_INFO(dev)->lun_reset_mutex)
 {
 	return pqi_suspend_or_freeze(dev, true);
 }
 
 static int pqi_resume_or_restore(struct device *dev)
+	__cond_releases(0, &TO_CTRL_INFO(dev)->lun_reset_mutex)
+	__cond_releases(0, &TO_CTRL_INFO(dev)->scan_mutex)
 {
 	int rc;
 	struct pci_dev *pci_dev;
@@ -9715,11 +9756,15 @@ static int pqi_resume_or_restore(struct device *dev)
 }
 
 static int pqi_freeze(struct device *dev)
+	__acquires(&TO_CTRL_INFO(dev)->scan_mutex)
+	__acquires(&TO_CTRL_INFO(dev)->lun_reset_mutex)
 {
 	return pqi_suspend_or_freeze(dev, false);
 }
 
 static int pqi_thaw(struct device *dev)
+	__cond_releases(0, &TO_CTRL_INFO(dev)->lun_reset_mutex)
+	__cond_releases(0, &TO_CTRL_INFO(dev)->scan_mutex)
 {
 	int rc;
 	struct pci_dev *pci_dev;
diff --git a/drivers/scsi/snic/Makefile b/drivers/scsi/snic/Makefile
index 41546e3cb701..b12563cb174d 100644
--- a/drivers/scsi/snic/Makefile
+++ b/drivers/scsi/snic/Makefile
@@ -1,4 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0
+
+CONTEXT_ANALYSIS := y
+
 obj-$(CONFIG_SCSI_SNIC) += snic.o
 
 snic-y := \
diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c
index 3dc6723e80a8..e9d41e3cc2dd 100644
--- a/drivers/scsi/st.c
+++ b/drivers/scsi/st.c
@@ -3249,14 +3249,20 @@ static int set_location(struct scsi_tape *STp, unsigned int block, int partition
 	    partition >= ST_NBR_PARTITIONS)
 		return (-EINVAL);
 	if (partition != STp->partition) {
-		if (get_location(STp, &blk, &p, 1))
+		/*
+		 * Save the location for the partition the drive reports,
+		 * not for STp->partition: after a reset STp->partition may
+		 * not match the partition the drive is in.
+		 */
+		if (get_location(STp, &blk, &p, 1) ||
+		    p < 0 || p >= ST_NBR_PARTITIONS)
 			STps->last_block_valid = 0;
 		else {
-			STps->last_block_valid = 1;
-			STps->last_block_visited = blk;
+			STp->ps[p].last_block_valid = 1;
+			STp->ps[p].last_block_visited = blk;
 			DEBC_printk(STp, "Visited block %d for "
 				    "partition %d saved.\n",
-				    blk, STp->partition);
+				    blk, p);
 		}
 	}
 
@@ -3567,6 +3573,7 @@ static int partition_tape(struct scsi_tape *STp, int size)
 static long st_common_ioctl(struct scsi_tape *STp, struct st_modedef *STm,
 			    struct file *file, unsigned int cmd_in,
 			    unsigned long arg)
+	__releases(&STp->lock)
 {
 	int i, retval = 0;
 
@@ -4603,11 +4610,11 @@ static void st_remove(struct scsi_device *SDp)
 	remove_cdevs(tpnt);
 
 	mutex_lock(&st_ref_mutex);
-	kref_put(&tpnt->kref, scsi_tape_release);
-	mutex_unlock(&st_ref_mutex);
 	spin_lock(&st_index_lock);
 	idr_remove(&st_index_idr, index);
 	spin_unlock(&st_index_lock);
+	kref_put(&tpnt->kref, scsi_tape_release);
+	mutex_unlock(&st_ref_mutex);
 }
 
 /**
diff --git a/drivers/scsi/sym53c8xx_2/Makefile b/drivers/scsi/sym53c8xx_2/Makefile
index 0751e2a0cd82..c28fb2b65622 100644
--- a/drivers/scsi/sym53c8xx_2/Makefile
+++ b/drivers/scsi/sym53c8xx_2/Makefile
@@ -1,5 +1,7 @@
 # SPDX-License-Identifier: GPL-2.0-only
 # Makefile for the NCR/SYMBIOS/LSI 53C8XX PCI SCSI controllers driver.
 
+CONTEXT_ANALYSIS := y
+
 sym53c8xx-objs := sym_fw.o sym_glue.o sym_hipd.o sym_malloc.o sym_nvram.o
 obj-$(CONFIG_SCSI_SYM53C8XX_2) := sym53c8xx.o
diff --git a/drivers/scsi/xen-scsifront.c b/drivers/scsi/xen-scsifront.c
index 2bff5e35822f..5c053b972287 100644
--- a/drivers/scsi/xen-scsifront.c
+++ b/drivers/scsi/xen-scsifront.c
@@ -367,6 +367,7 @@ static void scsifront_do_response(struct vscsifrnt_info *info,
 	struct vscsifrnt_shadow *shadow;
 
 	if (ring_rsp->rqid >= VSCSIIF_MAX_REQS ||
+	    !info->shadow[ring_rsp->rqid] ||
 	    !info->shadow[ring_rsp->rqid]->inflight) {
 		scsifront_set_error(info, "illegal rqid returned by backend!");
 		return;
diff --git a/drivers/target/iscsi/Kconfig b/drivers/target/iscsi/Kconfig
index 70d76f3dd693..44bbf1f32859 100644
--- a/drivers/target/iscsi/Kconfig
+++ b/drivers/target/iscsi/Kconfig
@@ -3,8 +3,11 @@ config ISCSI_TARGET
 	tristate "SCSI Target Mode Stack"
 	depends on INET
 	select CRC32
-	select CRYPTO
-	select CRYPTO_HASH
+	select CRYPTO_LIB_MD5
+	select CRYPTO_LIB_SHA1
+	select CRYPTO_LIB_SHA256
+	select CRYPTO_LIB_SHA3
+	select CRYPTO_LIB_UTILS
 	help
 	Say M to enable the SCSI target mode stack. A SCSI target mode stack
 	is software that makes local storage available over a storage network
diff --git a/drivers/target/iscsi/iscsi_target_auth.c b/drivers/target/iscsi/iscsi_target_auth.c
index f3c0cdd31830..945dd6409723 100644
--- a/drivers/target/iscsi/iscsi_target_auth.c
+++ b/drivers/target/iscsi/iscsi_target_auth.c
@@ -8,31 +8,73 @@
  *
  ******************************************************************************/
 
-#include <crypto/hash.h>
+#include <crypto/md5.h>
+#include <crypto/sha1.h>
+#include <crypto/sha2.h>
+#include <crypto/sha3.h>
 #include <crypto/utils.h>
+#include <linux/fips.h>
 #include <linux/kernel.h>
 #include <linux/string.h>
-#include <linux/err.h>
 #include <linux/hex.h>
 #include <linux/random.h>
-#include <linux/scatterlist.h>
+#include <linux/slab.h>
 #include <target/iscsi/iscsi_target_core.h>
 #include "iscsi_target_nego.h"
 #include "iscsi_target_auth.h"
 
-static char *chap_get_digest_name(const int digest_type)
+static const struct {
+	const char *digest_name; /* Used only in log messages */
+	unsigned int digest_size;
+} chap_digest_algs[] = {
+	[CHAP_DIGEST_MD5] = {
+		.digest_name = "md5",
+		.digest_size = MD5_DIGEST_SIZE,
+	},
+	[CHAP_DIGEST_SHA1] = {
+		.digest_name = "sha1",
+		.digest_size = SHA1_DIGEST_SIZE,
+	},
+	[CHAP_DIGEST_SHA256] = {
+		.digest_name = "sha256",
+		.digest_size = SHA256_DIGEST_SIZE,
+	},
+	[CHAP_DIGEST_SHA3_256] = {
+		.digest_name = "sha3-256",
+		.digest_size = SHA3_256_DIGEST_SIZE,
+	},
+};
+
+static int chap_digest(int digest_type, u8 chap_id, const char *password,
+		       const u8 *challenge, size_t challenge_len,
+		       u8 *out_digest)
 {
+	size_t pass_len = strlen(password);
+	size_t data_len = 1 + pass_len + challenge_len;
+	u8 *data __free(kfree_sensitive) = kmalloc(data_len, GFP_KERNEL);
+
+	if (!data)
+		return -ENOMEM;
+	data[0] = chap_id;
+	memcpy(&data[1], password, pass_len);
+	memcpy(&data[1 + pass_len], challenge, challenge_len);
+
 	switch (digest_type) {
 	case CHAP_DIGEST_MD5:
-		return "md5";
+		md5(data, data_len, out_digest);
+		return 0;
 	case CHAP_DIGEST_SHA1:
-		return "sha1";
+		sha1(data, data_len, out_digest);
+		return 0;
 	case CHAP_DIGEST_SHA256:
-		return "sha256";
+		sha256(data, data_len, out_digest);
+		return 0;
 	case CHAP_DIGEST_SHA3_256:
-		return "sha3-256";
+		sha3_256(data, data_len, out_digest);
+		return 0;
 	default:
-		return NULL;
+		WARN_ON_ONCE(1);
+		return -EINVAL;
 	}
 }
 
@@ -72,21 +114,9 @@ static int chap_gen_challenge(
 	return ret;
 }
 
-static int chap_test_algorithm(const char *name)
-{
-	struct crypto_shash *tfm;
-
-	tfm = crypto_alloc_shash(name, 0, 0);
-	if (IS_ERR(tfm))
-		return -1;
-
-	crypto_free_shash(tfm);
-	return 0;
-}
-
 static int chap_check_algorithm(const char *a_str)
 {
-	char *tmp, *orig, *token, *digest_name;
+	char *tmp, *orig, *token;
 	long digest_type;
 	int r = CHAP_DIGEST_UNKNOWN;
 
@@ -113,17 +143,17 @@ static int chap_check_algorithm(const char *a_str)
 		if (kstrtol(token, 10, &digest_type))
 			continue;
 
-		digest_name = chap_get_digest_name(digest_type);
-		if (!digest_name)
+		if (fips_enabled && digest_type == CHAP_DIGEST_MD5)
 			continue;
 
-		pr_debug("Selected %s Algorithm\n", digest_name);
-		if (chap_test_algorithm(digest_name) < 0) {
-			pr_err("failed to allocate %s algo\n", digest_name);
-		} else {
-			r = digest_type;
-			goto out;
-		}
+		if (digest_type < 0 ||
+		    digest_type >= ARRAY_SIZE(chap_digest_algs) ||
+		    chap_digest_algs[digest_type].digest_name == NULL)
+			continue;
+		pr_debug("Selected %s Algorithm\n",
+			 chap_digest_algs[digest_type].digest_name);
+		r = digest_type;
+		goto out;
 	}
 out:
 	kfree(orig);
@@ -159,27 +189,15 @@ static struct iscsi_chap *chap_server_open(
 
 	chap = conn->auth_protocol;
 	digest_type = chap_check_algorithm(a_str);
-	switch (digest_type) {
-	case CHAP_DIGEST_MD5:
-		chap->digest_size = MD5_SIGNATURE_SIZE;
-		break;
-	case CHAP_DIGEST_SHA1:
-		chap->digest_size = SHA1_SIGNATURE_SIZE;
-		break;
-	case CHAP_DIGEST_SHA256:
-		chap->digest_size = SHA256_SIGNATURE_SIZE;
-		break;
-	case CHAP_DIGEST_SHA3_256:
-		chap->digest_size = SHA3_256_SIGNATURE_SIZE;
-		break;
-	case CHAP_DIGEST_UNKNOWN:
-	default:
+	if (digest_type == CHAP_DIGEST_UNKNOWN) {
 		pr_err("Unsupported CHAP_A value\n");
 		chap_close(conn);
 		return NULL;
 	}
 
-	chap->digest_name = chap_get_digest_name(digest_type);
+	chap->digest_name = chap_digest_algs[digest_type].digest_name;
+	chap->digest_type = digest_type;
+	chap->digest_size = chap_digest_algs[digest_type].digest_size;
 
 	/* Tie the challenge length to the digest size */
 	chap->challenge_len = chap->digest_size;
@@ -247,7 +265,6 @@ static int chap_server_compute_hash(
 	unsigned int *nr_out_len)
 {
 	unsigned long id;
-	unsigned char id_as_uchar;
 	unsigned char type;
 	unsigned char identifier[10], *initiatorchg = NULL;
 	unsigned char *initiatorchg_binhex = NULL;
@@ -258,8 +275,6 @@ static int chap_server_compute_hash(
 	unsigned char chap_n[MAX_CHAP_N_SIZE], chap_r[MAX_RESPONSE_LENGTH];
 	size_t compare_len;
 	struct iscsi_chap *chap = conn->auth_protocol;
-	struct crypto_shash *tfm = NULL;
-	struct shash_desc *desc = NULL;
 	int auth_ret = -1, ret, initiatorchg_len;
 
 	digest = kzalloc(chap->digest_size, GFP_KERNEL);
@@ -364,44 +379,10 @@ static int chap_server_compute_hash(
 
 	pr_debug("[server] Got CHAP_R=%s\n", chap_r);
 
-	tfm = crypto_alloc_shash(chap->digest_name, 0, 0);
-	if (IS_ERR(tfm)) {
-		tfm = NULL;
-		pr_err("Unable to allocate struct crypto_shash\n");
-		goto out;
-	}
-
-	desc = kmalloc(sizeof(*desc) + crypto_shash_descsize(tfm), GFP_KERNEL);
-	if (!desc) {
-		pr_err("Unable to allocate struct shash_desc\n");
-		goto out;
-	}
-
-	desc->tfm = tfm;
-
-	ret = crypto_shash_init(desc);
-	if (ret < 0) {
-		pr_err("crypto_shash_init() failed\n");
-		goto out;
-	}
-
-	ret = crypto_shash_update(desc, &chap->id, 1);
-	if (ret < 0) {
-		pr_err("crypto_shash_update() failed for id\n");
-		goto out;
-	}
-
-	ret = crypto_shash_update(desc, (char *)&auth->password,
-				  strlen(auth->password));
-	if (ret < 0) {
-		pr_err("crypto_shash_update() failed for password\n");
-		goto out;
-	}
-
-	ret = crypto_shash_finup(desc, chap->challenge,
-				 chap->challenge_len, server_digest);
+	ret = chap_digest(chap->digest_type, chap->id, auth->password,
+			  chap->challenge, chap->challenge_len, server_digest);
 	if (ret < 0) {
-		pr_err("crypto_shash_finup() failed for challenge\n");
+		pr_err("chap_digest() failed\n");
 		goto out;
 	}
 
@@ -530,40 +511,12 @@ static int chap_server_compute_hash(
 	/*
 	 * Generate CHAP_N and CHAP_R for mutual authentication.
 	 */
-	ret = crypto_shash_init(desc);
+	ret = chap_digest(chap->digest_type, id, auth->password_mutual,
+			  initiatorchg_binhex, initiatorchg_len, digest);
 	if (ret < 0) {
-		pr_err("crypto_shash_init() failed\n");
+		pr_err("chap_digest() failed\n");
 		goto out;
 	}
-
-	/* To handle both endiannesses */
-	id_as_uchar = id;
-	ret = crypto_shash_update(desc, &id_as_uchar, 1);
-	if (ret < 0) {
-		pr_err("crypto_shash_update() failed for id\n");
-		goto out;
-	}
-
-	ret = crypto_shash_update(desc, auth->password_mutual,
-				  strlen(auth->password_mutual));
-	if (ret < 0) {
-		pr_err("crypto_shash_update() failed for"
-				" password_mutual\n");
-		goto out;
-	}
-	/*
-	 * Convert received challenge to binary hex.
-	 */
-	ret = crypto_shash_finup(desc, initiatorchg_binhex, initiatorchg_len,
-				 digest);
-	if (ret < 0) {
-		pr_err("crypto_shash_finup() failed for ma challenge\n");
-		goto out;
-	}
-
-	/*
-	 * Generate CHAP_N and CHAP_R.
-	 */
 	*nr_out_len = sprintf(nr_out_ptr, "CHAP_N=%s", auth->userid_mutual);
 	*nr_out_len += 1;
 	pr_debug("[server] Sending CHAP_N=%s\n", auth->userid_mutual);
@@ -577,9 +530,6 @@ static int chap_server_compute_hash(
 	pr_debug("[server] Sending CHAP_R=0x%s\n", response);
 	auth_ret = 0;
 out:
-	kfree_sensitive(desc);
-	if (tfm)
-		crypto_free_shash(tfm);
 	kfree(initiatorchg);
 	kfree(initiatorchg_binhex);
 	kfree(digest);
diff --git a/drivers/target/iscsi/iscsi_target_auth.h b/drivers/target/iscsi/iscsi_target_auth.h
index ceb9b7754770..7ed288936af2 100644
--- a/drivers/target/iscsi/iscsi_target_auth.h
+++ b/drivers/target/iscsi/iscsi_target_auth.h
@@ -15,11 +15,6 @@
 #define MAX_RESPONSE_LENGTH	128	/* sufficient for SHA3 256 */
 #define	MAX_CHAP_N_SIZE		512
 
-#define MD5_SIGNATURE_SIZE	16	/* 16 bytes in a MD5 message digest */
-#define SHA1_SIGNATURE_SIZE	20	/* 20 bytes in a SHA1 message digest */
-#define SHA256_SIGNATURE_SIZE	32	/* 32 bytes in a SHA256 message digest */
-#define SHA3_256_SIGNATURE_SIZE	32	/* 32 bytes in a SHA3 256 message digest */
-
 #define CHAP_STAGE_CLIENT_A	1
 #define CHAP_STAGE_SERVER_AIC	2
 #define CHAP_STAGE_CLIENT_NR	3
@@ -36,7 +31,8 @@ struct iscsi_chap {
 	unsigned char	id;
 	unsigned char	challenge[MAX_CHAP_CHALLENGE_LEN];
 	unsigned int	challenge_len;
-	unsigned char	*digest_name;
+	const char	*digest_name;
+	int		digest_type;
 	unsigned int	digest_size;
 	unsigned int	authenticate_target;
 	unsigned int	chap_state;
diff --git a/drivers/target/iscsi/iscsi_target_configfs.c b/drivers/target/iscsi/iscsi_target_configfs.c
index 704ec94383c3..e1aa0af52c65 100644
--- a/drivers/target/iscsi/iscsi_target_configfs.c
+++ b/drivers/target/iscsi/iscsi_target_configfs.c
@@ -1306,17 +1306,24 @@ static ssize_t iscsi_disc_enforce_discovery_auth_store(struct config_item *item,
 		return -EINVAL;
 	}
 
+	if (iscsit_get_tpg(discovery_tpg) < 0)
+		return -EINVAL;
+
 	param = iscsi_find_param_from_key(AUTHMETHOD,
 				discovery_tpg->param_list);
-	if (!param)
-		return -EINVAL;
+	if (!param) {
+		err = -EINVAL;
+		goto out;
+	}
 
 	if (op) {
 		/*
 		 * Reset the AuthMethod key to CHAP.
 		 */
-		if (iscsi_update_param_value(param, CHAP) < 0)
-			return -EINVAL;
+		if (iscsi_update_param_value(param, CHAP) < 0) {
+			err = -EINVAL;
+			goto out;
+		}
 
 		discovery_tpg->tpg_attrib.authentication = 1;
 		iscsit_global->discovery_acl.node_auth.enforce_discovery_auth = 1;
@@ -1327,8 +1334,10 @@ static ssize_t iscsi_disc_enforce_discovery_auth_store(struct config_item *item,
 		/*
 		 * Reset the AuthMethod key to CHAP,None
 		 */
-		if (iscsi_update_param_value(param, "CHAP,None") < 0)
-			return -EINVAL;
+		if (iscsi_update_param_value(param, "CHAP,None") < 0) {
+			err = -EINVAL;
+			goto out;
+		}
 
 		discovery_tpg->tpg_attrib.authentication = 0;
 		iscsit_global->discovery_acl.node_auth.enforce_discovery_auth = 0;
@@ -1337,7 +1346,10 @@ static ssize_t iscsi_disc_enforce_discovery_auth_store(struct config_item *item,
 			" Discovery TPG\n");
 	}
 
-	return count;
+	err = count;
+out:
+	iscsit_put_tpg(discovery_tpg);
+	return err;
 }
 
 CONFIGFS_ATTR(iscsi_disc_, enforce_discovery_auth);
diff --git a/drivers/target/target_core_transport.c b/drivers/target/target_core_transport.c
index ba208def8cb5..927861c30afc 100644
--- a/drivers/target/target_core_transport.c
+++ b/drivers/target/target_core_transport.c
@@ -2359,7 +2359,7 @@ void target_do_delayed_work(struct work_struct *work)
 	struct se_device *dev = container_of(work, struct se_device,
 					     delayed_cmd_work);
 
-	spin_lock(&dev->delayed_cmd_lock);
+	spin_lock_irq(&dev->delayed_cmd_lock);
 	while (!dev->ordered_sync_in_progress) {
 		struct se_cmd *cmd;
 
@@ -2380,12 +2380,12 @@ void target_do_delayed_work(struct work_struct *work)
 		dev->ordered_sync_in_progress = true;
 
 		list_del(&cmd->se_delayed_node);
-		spin_unlock(&dev->delayed_cmd_lock);
+		spin_unlock_irq(&dev->delayed_cmd_lock);
 
 		__target_execute_cmd(cmd, true);
-		spin_lock(&dev->delayed_cmd_lock);
+		spin_lock_irq(&dev->delayed_cmd_lock);
 	}
-	spin_unlock(&dev->delayed_cmd_lock);
+	spin_unlock_irq(&dev->delayed_cmd_lock);
 }
 
 static void transport_complete_ordered_sync(struct se_cmd *cmd)
diff --git a/drivers/ufs/core/ufs-mcq.c b/drivers/ufs/core/ufs-mcq.c
index 8106d55f4041..25e392f8ede2 100644
--- a/drivers/ufs/core/ufs-mcq.c
+++ b/drivers/ufs/core/ufs-mcq.c
@@ -183,8 +183,8 @@ static int ufshcd_mcq_config_nr_queues(struct ufs_hba *hba)
 	}
 
 	/*
-	 * Device should support at least one I/O queue to handle device
-	 * commands via hba->dev_cmd_queue.
+	 * At least one non-poll (HCTX_TYPE_DEFAULT) queue is required for
+	 * non-polled SCSI commands and UFS device management commands.
 	 */
 	if (hba_maxq == poll_queues) {
 		dev_err(hba->dev, "At least one non-poll queue required\n");
@@ -312,20 +312,24 @@ static int ufshcd_mcq_get_tag(struct ufs_hba *hba, struct cq_entry *cqe)
 		UFSHCD_NUM_RESERVED;
 }
 
+static void ufshcd_mcq_compl_cqe(struct ufs_hba *hba, struct cq_entry *cqe)
+{
+	int tag = ufshcd_mcq_get_tag(hba, cqe);
+
+	ufshcd_compl_one_cqe(hba, tag, cqe);
+	/* After processing the CQE, mark it as an empty (invalid) entry. */
+	cqe->command_desc_base_addr = 0;
+}
+
 static void ufshcd_mcq_process_cqe(struct ufs_hba *hba,
 				   struct ufs_hw_queue *hwq)
 {
 	struct cq_entry *cqe = ufshcd_mcq_cur_cqe(hwq);
 
-	if (cqe->command_desc_base_addr) {
-		int tag = ufshcd_mcq_get_tag(hba, cqe);
-
-		ufshcd_compl_one_cqe(hba, tag, cqe);
-		/* After processed the cqe, mark it empty (invalid) entry */
-		cqe->command_desc_base_addr = 0;
-	} else {
+	if (cqe->command_desc_base_addr)
+		ufshcd_mcq_compl_cqe(hba, cqe);
+	else
 		dev_err(hba->dev, "Abnormal CQ entry!\n");
-	}
 }
 
 /*
@@ -333,7 +337,7 @@ static void ufshcd_mcq_process_cqe(struct ufs_hba *hba,
  * controller disabled (HCE = 0). Reading host controller registers, e.g. the
  * CQ tail pointer (CQTPy), may not be safe with the host controller disabled.
  * Hence, iterate over all completion queue entries. This won't result in
- * double completions because ufshcd_mcq_process_cqe() clears a CQE after it
+ * double completions because ufshcd_mcq_compl_cqe() clears a CQE after it
  * has been processed.
  */
 void ufshcd_mcq_compl_all_cqes_lock(struct ufs_hba *hba,
@@ -344,13 +348,13 @@ void ufshcd_mcq_compl_all_cqes_lock(struct ufs_hba *hba,
 
 	spin_lock_irqsave(&hwq->cq_lock, flags);
 	while (entries > 0) {
-		ufshcd_mcq_process_cqe(hba, hwq);
+		struct cq_entry *cqe = ufshcd_mcq_cur_cqe(hwq);
+
+		if (cqe->command_desc_base_addr)
+			ufshcd_mcq_compl_cqe(hba, cqe);
 		ufshcd_mcq_inc_cq_head_slot(hwq);
 		entries--;
 	}
-
-	ufshcd_mcq_update_cq_tail_slot(hwq);
-	hwq->cq_head_slot = hwq->cq_tail_slot;
 	spin_unlock_irqrestore(&hwq->cq_lock, flags);
 }
 
diff --git a/drivers/ufs/core/ufs_bsg.c b/drivers/ufs/core/ufs_bsg.c
index 7a66917b3fc0..baf6ae917d36 100644
--- a/drivers/ufs/core/ufs_bsg.c
+++ b/drivers/ufs/core/ufs_bsg.c
@@ -73,6 +73,9 @@ static int ufs_bsg_exec_advanced_rpmb_req(struct ufs_hba *hba, struct bsg_job *j
 	if (hba->ufs_version < ufshci_version(4, 0) || !hba->dev_info.b_advanced_rpmb_en)
 		return -EINVAL;
 
+	if (job->request_len < sizeof(*rpmb_request))
+		return -EINVAL;
+
 	if (rpmb_request->ehs_req.length != 2 || rpmb_request->ehs_req.ehs_type != 1)
 		return -EINVAL;
 
@@ -140,7 +143,12 @@ static int ufs_bsg_request(struct bsg_job *job)
 	int ret;
 	bool rpmb = false;
 
-	bsg_reply->reply_payload_rcv_len = 0;
+	memset(job->reply, 0, job->reply_len);
+
+	if (job->request_len < sizeof(*bsg_request)) {
+		ret = -EINVAL;
+		goto out_complete;
+	}
 
 	ufshcd_rpm_get_sync(hba);
 
@@ -171,6 +179,10 @@ static int ufs_bsg_request(struct bsg_job *job)
 		break;
 	case UPIU_TRANSACTION_UIC_CMD:
 		memcpy(&uc, &bsg_request->upiu_req.uc, UIC_CMD_SIZE);
+		if (uc.argument2 & MASK_UIC_COMMAND_RESULT) {
+			ret = -EINVAL;
+			break;
+		}
 		ret = ufshcd_send_bsg_uic_cmd(hba, &uc);
 		if (ret)
 			dev_err(hba->dev, "send uic cmd: error code %d\n", ret);
@@ -194,15 +206,14 @@ static int ufs_bsg_request(struct bsg_job *job)
 out:
 	ufshcd_rpm_put_sync(hba);
 	kfree(buff);
+out_complete:
 	bsg_reply->result = ret;
-	/* complete the job here only if no error */
-	if (ret == 0) {
+	if (ret == 0)
 		job->reply_len = rpmb ? sizeof(struct ufs_rpmb_reply) :
 					sizeof(struct ufs_bsg_reply);
-		bsg_job_done(job, ret, bsg_reply->reply_payload_rcv_len);
-	}
+	bsg_job_done(job, ret, bsg_reply->reply_payload_rcv_len);
 
-	return ret;
+	return 0;
 }
 
 /**
@@ -258,7 +269,7 @@ int ufs_bsg_probe(struct ufs_hba *hba)
 		goto out;
 
 	q = bsg_setup_queue(bsg_dev, dev_name(bsg_dev), NULL, ufs_bsg_request,
-			NULL, 0);
+			NULL, 0, sizeof(struct ufs_rpmb_reply));
 	if (IS_ERR(q)) {
 		ret = PTR_ERR(q);
 		device_del(bsg_dev);
diff --git a/drivers/ufs/core/ufshcd.c b/drivers/ufs/core/ufshcd.c
index bcc2512bf34b..ee643830a57a 100644
--- a/drivers/ufs/core/ufshcd.c
+++ b/drivers/ufs/core/ufshcd.c
@@ -1360,13 +1360,13 @@ int ufshcd_pause_command_processing(struct ufs_hba *hba, u64 timeout_us)
 	int ret = 0;
 
 	mutex_lock(&hba->host->scan_mutex);
-	blk_mq_quiesce_tagset(&hba->host->tag_set);
 	down_write(&hba->clk_scaling_lock);
+	blk_mq_quiesce_tagset(&hba->host->tag_set);
 
 	if (ufshcd_wait_for_pending_cmds(hba, timeout_us)) {
 		ret = -EBUSY;
-		up_write(&hba->clk_scaling_lock);
 		blk_mq_unquiesce_tagset(&hba->host->tag_set);
+		up_write(&hba->clk_scaling_lock);
 		mutex_unlock(&hba->host->scan_mutex);
 	}
 
@@ -1383,8 +1383,8 @@ void ufshcd_resume_command_processing(struct ufs_hba *hba)
 	__releases(&hba->clk_scaling_lock)
 	__releases(&hba->host->scan_mutex)
 {
-	up_write(&hba->clk_scaling_lock);
 	blk_mq_unquiesce_tagset(&hba->host->tag_set);
+	up_write(&hba->clk_scaling_lock);
 	mutex_unlock(&hba->host->scan_mutex);
 }
 
@@ -1461,16 +1461,16 @@ static int ufshcd_clock_scaling_prepare(struct ufs_hba *hba, u64 timeout_us)
 	 * clock scaling is in progress
 	 */
 	mutex_lock(&hba->host->scan_mutex);
-	blk_mq_quiesce_tagset(&hba->host->tag_set);
 	mutex_lock(&hba->wb_mutex);
 	down_write(&hba->clk_scaling_lock);
+	blk_mq_quiesce_tagset(&hba->host->tag_set);
 
 	if (!hba->clk_scaling.is_allowed ||
 	    ufshcd_wait_for_pending_cmds(hba, timeout_us)) {
 		ret = -EBUSY;
+		blk_mq_unquiesce_tagset(&hba->host->tag_set);
 		up_write(&hba->clk_scaling_lock);
 		mutex_unlock(&hba->wb_mutex);
-		blk_mq_unquiesce_tagset(&hba->host->tag_set);
 		mutex_unlock(&hba->host->scan_mutex);
 		goto out;
 	}
@@ -1487,9 +1487,9 @@ static void ufshcd_clock_scaling_unprepare(struct ufs_hba *hba, int err)
 	__releases(&hba->wb_mutex)
 	__releases(&hba->host->scan_mutex)
 {
+	blk_mq_unquiesce_tagset(&hba->host->tag_set);
 	up_write(&hba->clk_scaling_lock);
 	mutex_unlock(&hba->wb_mutex);
-	blk_mq_unquiesce_tagset(&hba->host->tag_set);
 	mutex_unlock(&hba->host->scan_mutex);
 
 	/* Enable Write Booster if current gear requires it else disable it */
@@ -4400,9 +4400,12 @@ int ufshcd_dme_set_attr(struct ufs_hba *hba, u32 attr_sel,
 	do {
 		/* for peer attributes we retry upon failure */
 		ret = ufshcd_send_uic_cmd(hba, &uic_cmd);
-		if (ret)
+		if (ret) {
 			dev_dbg(hba->dev, "%s: attr-id 0x%x val 0x%x error code %d\n",
 				set, UIC_GET_ATTR_ID(attr_sel), mib_val, ret);
+			uic_cmd.argument2 &= ~MASK_UIC_COMMAND_RESULT;
+			uic_cmd.argument3 = mib_val;
+		}
 	} while (ret && peer && --retries);
 
 	if (ret)
@@ -4467,9 +4470,11 @@ int ufshcd_dme_get_attr(struct ufs_hba *hba, u32 attr_sel,
 	do {
 		/* for peer attributes we retry upon failure */
 		ret = ufshcd_send_uic_cmd(hba, &uic_cmd);
-		if (ret)
+		if (ret) {
 			dev_dbg(hba->dev, "%s: attr-id 0x%x error code %d\n",
 				get, UIC_GET_ATTR_ID(attr_sel), ret);
+			uic_cmd.argument2 &= ~MASK_UIC_COMMAND_RESULT;
+		}
 	} while (ret && peer && --retries);
 
 	if (ret)
@@ -6052,6 +6057,37 @@ static void ufshcd_clear_polled(struct ufs_hba *hba,
 	}
 }
 
+/*
+ * Return a bitmask of the transfer requests cleared from
+ * @hba->outstanding_reqs.
+ */
+static unsigned long __ufshcd_clear_outstanding_reqs(struct ufs_hba *hba,
+						     unsigned long mask,
+						     bool from_irq)
+	__must_hold(&hba->outstanding_lock)
+{
+	unsigned long completed_reqs = mask & hba->outstanding_reqs;
+
+	if (from_irq) {
+		/* Do not complete polled requests from interrupt context. */
+		ufshcd_clear_polled(hba, &completed_reqs);
+	}
+	hba->outstanding_reqs &= ~completed_reqs;
+
+	return completed_reqs;
+}
+
+/*
+ * Return a bitmask of the transfer requests cleared from
+ * @hba->outstanding_reqs.
+ */
+static unsigned long ufshcd_clear_outstanding_reqs(struct ufs_hba *hba,
+						   unsigned long mask)
+{
+	guard(spinlock_irqsave)(&hba->outstanding_lock);
+	return __ufshcd_clear_outstanding_reqs(hba, mask, false);
+}
+
 /*
  * Return: > 0 if one or more commands have been completed or 0 if no
  * requests have been completed.
@@ -6062,6 +6098,7 @@ static int ufshcd_poll(struct Scsi_Host *shost, unsigned int queue_num)
 	unsigned long completed_reqs, flags;
 	u32 tr_doorbell;
 	struct ufs_hw_queue *hwq;
+	bool from_irq;
 
 	if (hba->mcq_enabled) {
 		hwq = &hba->uhq[queue_num];
@@ -6071,15 +6108,9 @@ static int ufshcd_poll(struct Scsi_Host *shost, unsigned int queue_num)
 
 	spin_lock_irqsave(&hba->outstanding_lock, flags);
 	tr_doorbell = ufshcd_readl(hba, REG_UTP_TRANSFER_REQ_DOOR_BELL);
-	completed_reqs = ~tr_doorbell & hba->outstanding_reqs;
-	WARN_ONCE(completed_reqs & ~hba->outstanding_reqs,
-		  "completed: %#lx; outstanding: %#lx\n", completed_reqs,
-		  hba->outstanding_reqs);
-	if (queue_num == UFSHCD_POLL_FROM_INTERRUPT_CONTEXT) {
-		/* Do not complete polled requests from interrupt context. */
-		ufshcd_clear_polled(hba, &completed_reqs);
-	}
-	hba->outstanding_reqs &= ~completed_reqs;
+	from_irq = queue_num == UFSHCD_POLL_FROM_INTERRUPT_CONTEXT;
+	completed_reqs = __ufshcd_clear_outstanding_reqs(hba, ~tr_doorbell,
+							 from_irq);
 	spin_unlock_irqrestore(&hba->outstanding_lock, flags);
 
 	if (completed_reqs)
@@ -6099,8 +6130,6 @@ static bool ufshcd_mcq_force_compl_one(struct request *rq, void *priv)
 	if (blk_mq_is_reserved_rq(rq) || !hwq)
 		return true;
 
-	ufshcd_mcq_compl_all_cqes_lock(hba, hwq);
-
 	/*
 	 * For those cmds of which the cqes are not present in the cq, complete
 	 * them explicitly.
@@ -6116,19 +6145,6 @@ static bool ufshcd_mcq_force_compl_one(struct request *rq, void *priv)
 	return true;
 }
 
-static bool ufshcd_mcq_compl_one(struct request *rq, void *priv)
-{
-	struct scsi_device *sdev = rq->q->queuedata;
-	struct Scsi_Host *shost = sdev->host;
-	struct ufs_hba *hba = shost_priv(shost);
-	struct ufs_hw_queue *hwq = ufshcd_mcq_req_to_hwq(hba, rq);
-
-	if (!blk_mq_is_reserved_rq(rq) && hwq)
-		ufshcd_mcq_poll_cqe_lock(hba, hwq);
-
-	return true;
-}
-
 /**
  * ufshcd_mcq_compl_pending_transfer - MCQ mode function. It is
  * invoked from the error handler context or ufshcd_host_reset_and_restore()
@@ -6143,10 +6159,18 @@ static bool ufshcd_mcq_compl_one(struct request *rq, void *priv)
 static void ufshcd_mcq_compl_pending_transfer(struct ufs_hba *hba,
 					      bool force_compl)
 {
-	blk_mq_tagset_busy_iter(&hba->host->tag_set,
-				force_compl ? ufshcd_mcq_force_compl_one :
-					      ufshcd_mcq_compl_one,
-				NULL);
+	int i;
+
+	for (i = 0; i < hba->nr_hw_queues; i++) {
+		if (force_compl)
+			ufshcd_mcq_compl_all_cqes_lock(hba, &hba->uhq[i]);
+		else
+			ufshcd_mcq_poll_cqe_lock(hba, &hba->uhq[i]);
+	}
+
+	if (force_compl)
+		blk_mq_tagset_busy_iter(&hba->host->tag_set,
+					ufshcd_mcq_force_compl_one, NULL);
 }
 
 /**
@@ -6872,11 +6896,17 @@ static void ufshcd_err_handling_prepare(struct ufs_hba *hba)
 	}
 	/* Wait for ongoing ufshcd_queuecommand() calls to finish. */
 	blk_mq_quiesce_tagset(&hba->host->tag_set);
+	/*
+	 * Internal commands are submitted on the pseudo SCSI device. Let them
+	 * through so that the error handler can recover the link.
+	 */
+	blk_mq_unquiesce_queue(hba->host->pseudo_sdev->request_queue);
 	cancel_work_sync(&hba->eeh_work);
 }
 
 static void ufshcd_err_handling_unprepare(struct ufs_hba *hba)
 {
+	blk_mq_quiesce_queue_nowait(hba->host->pseudo_sdev->request_queue);
 	blk_mq_unquiesce_tagset(&hba->host->tag_set);
 	ufshcd_release(hba);
 	if (ufshcd_is_clkscaling_supported(hba))
@@ -7961,7 +7991,8 @@ static bool ufshcd_clear_lu_cmds(struct request *req, void *priv)
 		return true;
 	}
 
-	ufshcd_compl_one_cqe(hba, tag, NULL);
+	if (ufshcd_clear_outstanding_reqs(hba, BIT(tag)))
+		ufshcd_compl_one_cqe(hba, tag, NULL);
 	return true;
 }
 
@@ -8114,7 +8145,6 @@ static int ufshcd_abort(struct scsi_cmnd *cmd)
 	struct ufshcd_lrb *lrbp = scsi_cmd_priv(cmd);
 	unsigned long flags;
 	int err = FAILED;
-	bool outstanding;
 	u32 reg;
 
 	ufshcd_hold(hba);
@@ -8154,15 +8184,6 @@ static int ufshcd_abort(struct scsi_cmnd *cmd)
 	}
 	hba->req_abort_count++;
 
-	if (!hba->mcq_enabled && !(reg & (1 << tag))) {
-		/* only execute this code in single doorbell mode */
-		dev_err(hba->dev,
-		"%s: cmd was completed, but without a notifying intr, tag = %d",
-		__func__, tag);
-		__ufshcd_transfer_req_compl(hba, 1UL << tag);
-		goto release;
-	}
-
 	/*
 	 * Task abort to the device W-LUN is illegal. When this command
 	 * will fail, due to spec violation, scsi err handling next step
@@ -8209,11 +8230,8 @@ static int ufshcd_abort(struct scsi_cmnd *cmd)
 	 * Clear the corresponding bit from outstanding_reqs since the command
 	 * has been aborted successfully.
 	 */
-	spin_lock_irqsave(&hba->outstanding_lock, flags);
-	outstanding = __test_and_clear_bit(tag, &hba->outstanding_reqs);
-	spin_unlock_irqrestore(&hba->outstanding_lock, flags);
-
-	if (outstanding)
+	if (ufshcd_clear_outstanding_reqs(hba, BIT(tag)) &&
+	    ufshcd_is_scsi_cmd(cmd))
 		ufshcd_release_scsi_cmd(hba, cmd);
 
 	err = SUCCESS;
@@ -9609,6 +9627,7 @@ static void ufshcd_async_scan(void *data, async_cookie_t cookie)
 	ret = ufshcd_add_lus(hba);
 
 out:
+	ufshcd_release(hba);
 	pm_runtime_put_sync(hba->dev);
 
 	if (ret)
@@ -9638,12 +9657,10 @@ static enum scsi_timeout_action ufshcd_eh_timed_out(struct scsi_cmnd *scmd)
 	 */
 	if (!test_bit(SCMD_STATE_COMPLETE, &scmd->state)) {
 		if (!hba->mcq_enabled) {
-			unsigned long flags;
 			struct request *rq = scsi_cmd_to_rq(scmd);
 
-			spin_lock_irqsave(&hba->outstanding_lock, flags);
-			__clear_bit(rq->tag, &hba->outstanding_reqs);
-			spin_unlock_irqrestore(&hba->outstanding_lock, flags);
+			if (!ufshcd_clear_outstanding_reqs(hba, BIT(rq->tag)))
+				return SCSI_EH_DONE;
 		}
 
 		if (ufshcd_is_scsi_cmd(scmd)) {
@@ -11334,6 +11351,9 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 
 	ufshcd_init_clk_gating(hba);
 
+	/* Released by ufshcd_async_scan(), or by out_release on failure. */
+	ufshcd_hold(hba);
+
 	ufshcd_init_clk_scaling(hba);
 
 	/*
@@ -11354,7 +11374,7 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 	err = devm_request_irq(dev, irq, ufshcd_intr, IRQF_SHARED, UFSHCD, hba);
 	if (err) {
 		dev_err(hba->dev, "request irq failed\n");
-		goto out_disable;
+		goto out_release;
 	} else {
 		hba->is_irq_enabled = true;
 	}
@@ -11370,7 +11390,7 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 		dev_err(hba->dev, "Host controller enable failed\n");
 		ufshcd_print_evt_hist(hba);
 		ufshcd_print_host_state(hba);
-		goto out_disable;
+		goto out_release;
 	}
 
 	INIT_DELAYED_WORK(&hba->rpm_dev_flush_recheck_work, ufshcd_rpm_dev_flush_recheck_work);
@@ -11384,7 +11404,7 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 
 	err = ufshcd_add_scsi_host(hba);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	/* Hold auto suspend until async scan completes */
 	pm_runtime_get_sync(dev);
@@ -11404,7 +11424,7 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 
 	err = ufshcd_link_startup(hba);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	if (hba->mcq_enabled)
 		ufshcd_config_mcq(hba);
@@ -11421,23 +11441,23 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 	/* Verify device initialization by sending NOP OUT UPIU */
 	err = ufshcd_verify_dev_init(hba);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	/* Initiate UFS initialization, and waiting until completion */
 	err = ufshcd_complete_dev_init(hba);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	err = ufshcd_device_params_init(hba);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	err = ufshcd_post_device_init(hba);
 
 initialized:
 	ufshcd_process_probe_result(hba, probe_start, err);
 	if (err)
-		goto out_disable;
+		goto out_release;
 
 	ufs_sysfs_add_nodes(hba->dev);
 	hba->dme_qos_sysfs_handle = sysfs_get_dirent(hba->dev->kobj.sd,
@@ -11448,6 +11468,8 @@ int ufshcd_init(struct ufs_hba *hba, void __iomem *mmio_base, unsigned int irq)
 	ufshcd_pm_qos_init(hba);
 	return 0;
 
+out_release:
+	ufshcd_release(hba);
 out_disable:
 	hba->is_irq_enabled = false;
 	ufshcd_hba_exit(hba);
diff --git a/drivers/ufs/host/ufs-mediatek.c b/drivers/ufs/host/ufs-mediatek.c
index 390d7d658835..5b6bff2cf9a2 100644
--- a/drivers/ufs/host/ufs-mediatek.c
+++ b/drivers/ufs/host/ufs-mediatek.c
@@ -509,6 +509,7 @@ static int ufs_mtk_mphy_power_on(struct ufs_hba *hba, bool on)
 	struct ufs_mtk_host *host = ufshcd_get_variant(hba);
 	struct phy *mphy = host->mphy;
 	struct arm_smccc_res res;
+	int err;
 	int ret = 0;
 
 	if (!mphy || !(on ^ host->mphy_powered_on))
@@ -523,7 +524,18 @@ static int ufs_mtk_mphy_power_on(struct ufs_hba *hba, bool on)
 			usleep_range(200, 210);
 			ufs_mtk_va09_pwr_ctrl(res, 1);
 		}
-		phy_power_on(mphy);
+		ret = phy_power_on(mphy);
+		if (ret) {
+			if (ufs_mtk_is_va09_supported(hba)) {
+				ufs_mtk_va09_pwr_ctrl(res, 0);
+				err = regulator_disable(host->reg_va09);
+				if (err)
+					dev_err(hba->dev,
+						"failed to unwind va09: %d\n", err);
+			}
+			dev_err(hba->dev, "failed to enable mphy: %d\n", ret);
+			return ret;
+		}
 	} else {
 		phy_power_off(mphy);
 		if (ufs_mtk_is_va09_supported(hba)) {
@@ -1295,7 +1307,9 @@ static int ufs_mtk_init(struct ufs_hba *hba)
 	 *
 	 * Enable phy clocks specifically here.
 	 */
-	ufs_mtk_mphy_power_on(hba, true);
+	err = ufs_mtk_mphy_power_on(hba, true);
+	if (err)
+		goto out_variant_clear;
 
 	if (ufs_mtk_is_rtff_mtcmos(hba)) {
 		/* First Restore here, to avoid backup unexpected value */
diff --git a/drivers/ufs/host/ufs-qcom.c b/drivers/ufs/host/ufs-qcom.c
index fb5213bad4a6..27c87e62f8e9 100644
--- a/drivers/ufs/host/ufs-qcom.c
+++ b/drivers/ufs/host/ufs-qcom.c
@@ -2438,6 +2438,7 @@ static irqreturn_t ufs_qcom_mcq_esi_handler(int irq, void *data)
 static int ufs_qcom_config_esi(struct ufs_hba *hba)
 {
 	struct ufs_qcom_host *host = ufshcd_get_variant(hba);
+	struct ufs_qcom_irq *qi;
 	int nr_irqs, ret;
 
 	if (host->esi_enabled)
@@ -2456,8 +2457,7 @@ static int ufs_qcom_config_esi(struct ufs_hba *hba)
 		return ret; /* Continue without ESI */
 	}
 
-	struct ufs_qcom_irq *qi = devm_kcalloc(hba->dev, nr_irqs, sizeof(*qi), GFP_KERNEL);
-
+	qi = devm_kcalloc(hba->dev, nr_irqs, sizeof(*qi), GFP_KERNEL);
 	if (!qi) {
 		platform_device_msi_free_irqs_all(hba->dev);
 		return -ENOMEM;
@@ -3037,6 +3037,10 @@ static void ufs_qcom_remove(struct platform_device *pdev)
 		platform_device_msi_free_irqs_all(hba->dev);
 }
 
+static const struct ufs_qcom_drvdata ufs_qcom_milos_drvdata = {
+	.no_phy_retention = true,
+};
+
 static const struct ufs_qcom_drvdata ufs_qcom_sm8550_drvdata = {
 	.quirks = UFSHCD_QUIRK_BROKEN_LSDBS_CAP,
 	.no_phy_retention = true,
@@ -3048,6 +3052,7 @@ static const struct ufs_qcom_drvdata ufs_qcom_sa8255p_drvdata = {
 
 static const struct of_device_id ufs_qcom_of_match[] __maybe_unused = {
 	{ .compatible = "qcom,ufshc" },
+	{ .compatible = "qcom,milos-ufshc", .data = &ufs_qcom_milos_drvdata },
 	{ .compatible = "qcom,sm8550-ufshc", .data = &ufs_qcom_sm8550_drvdata },
 	{ .compatible = "qcom,sm8650-ufshc", .data = &ufs_qcom_sm8550_drvdata },
 	{ .compatible = "qcom,sa8255p-ufshc", .data = &ufs_qcom_sa8255p_drvdata },
diff --git a/drivers/ufs/host/ufshcd-pltfrm.c b/drivers/ufs/host/ufshcd-pltfrm.c
index 5ac7afe75934..169dbc1a75fe 100644
--- a/drivers/ufs/host/ufshcd-pltfrm.c
+++ b/drivers/ufs/host/ufshcd-pltfrm.c
@@ -206,7 +206,11 @@ static void ufshcd_init_lanes_per_dir(struct ufs_hba *hba)
 		dev_dbg(hba->dev,
 			"%s: failed to read lanes-per-direction, ret=%d\n",
 			__func__, ret);
-		hba->lanes_per_direction = UFSHCD_DEFAULT_LANES_PER_DIRECTION;
+		/* Old R-Car S4 DTBs lack "lanes-per-direction = <1>" */
+		if (of_device_is_compatible(dev->of_node, "renesas,r8a779f0-ufs"))
+			hba->lanes_per_direction = 1;
+		else
+			hba->lanes_per_direction = UFSHCD_DEFAULT_LANES_PER_DIRECTION;
 	}
 }
 
diff --git a/include/linux/bsg-lib.h b/include/linux/bsg-lib.h
index 14fa93268630..a697246feeac 100644
--- a/include/linux/bsg-lib.h
+++ b/include/linux/bsg-lib.h
@@ -66,7 +66,8 @@ void bsg_job_done(struct bsg_job *job, int result,
 		  unsigned int reply_payload_rcv_len);
 struct request_queue *bsg_setup_queue(struct device *dev, const char *name,
 		struct queue_limits *lim, bsg_job_fn *job_fn,
-		bsg_timeout_fn *timeout, int dd_job_size);
+		bsg_timeout_fn *timeout, int dd_job_size,
+		unsigned int reply_len);
 void bsg_remove_queue(struct request_queue *q);
 void bsg_job_put(struct bsg_job *job);
 int __must_check bsg_job_get(struct bsg_job *job);
diff --git a/include/linux/pci.h b/include/linux/pci.h
index d31a8d107b1e..68166c9f8158 100644
--- a/include/linux/pci.h
+++ b/include/linux/pci.h
@@ -611,7 +611,10 @@ static inline struct pci_dev *pci_physfn(struct pci_dev *dev)
 
 struct pci_dev *pci_alloc_dev(struct pci_bus *bus);
 
-#define	to_pci_dev(n) container_of(n, struct pci_dev, dev)
+static inline struct pci_dev *to_pci_dev(const struct device *dev)
+{
+	return container_of(dev, struct pci_dev, dev);
+}
 #define for_each_pci_dev(d) while ((d = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, d)) != NULL)
 #define for_each_pci_dev_reverse(d) \
 	while ((d = pci_get_device_reverse(PCI_ANY_ID, PCI_ANY_ID, d)) != NULL)
diff --git a/include/scsi/libiscsi.h b/include/scsi/libiscsi.h
index 3d765c77bcd9..e4ac4ec0ac3e 100644
--- a/include/scsi/libiscsi.h
+++ b/include/scsi/libiscsi.h
@@ -474,17 +474,26 @@ extern int iscsi_conn_send_pdu(struct iscsi_cls_conn *, struct iscsi_hdr *,
 				char *, uint32_t);
 extern int iscsi_complete_pdu(struct iscsi_conn *, struct iscsi_hdr *,
 			      char *, int);
-extern int __iscsi_complete_pdu(struct iscsi_conn *, struct iscsi_hdr *,
-				char *, int);
+extern int __iscsi_complete_pdu(struct iscsi_session *session,
+				struct iscsi_conn *conn, struct iscsi_hdr *,
+				char *, int)
+	__must_hold(&session->back_lock);
 extern int iscsi_verify_itt(struct iscsi_conn *, itt_t);
-extern struct iscsi_task *iscsi_itt_to_ctask(struct iscsi_conn *, itt_t);
-extern struct iscsi_task *iscsi_itt_to_task(struct iscsi_conn *, itt_t);
+struct iscsi_task *iscsi_itt_to_ctask(struct iscsi_session *session,
+				      struct iscsi_conn *conn, itt_t itt)
+	__must_hold(&session->back_lock);
+struct iscsi_task *iscsi_itt_to_task(struct iscsi_session *session,
+				     struct iscsi_conn *conn, itt_t itt)
+	__must_hold(&session->back_lock);
 extern void iscsi_requeue_task(struct iscsi_task *task);
 extern void iscsi_put_task(struct iscsi_task *task);
-extern void __iscsi_put_task(struct iscsi_task *task);
+void __iscsi_put_task(struct iscsi_session *session, struct iscsi_task *task)
+	__must_hold(&session->back_lock);
 extern bool iscsi_get_task(struct iscsi_task *task);
-extern void iscsi_complete_scsi_task(struct iscsi_task *task,
-				     uint32_t exp_cmdsn, uint32_t max_cmdsn);
+void iscsi_complete_scsi_task(struct iscsi_session *session,
+			      struct iscsi_task *task,
+			      uint32_t exp_cmdsn, uint32_t max_cmdsn)
+	__must_hold(&session->back_lock);
 
 /*
  * generic helpers
diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h
index 08ac3200b4a4..0e284caea9a7 100644
--- a/include/scsi/scsi.h
+++ b/include/scsi/scsi.h
@@ -176,7 +176,7 @@ enum scsi_qc_status {
 /*
  * Here are some scsi specific ioctl commands which are sometimes useful.
  *
- * Note that include/linux/cdrom.h also defines IOCTL 0x5300 - 0x5395
+ * Note that include/uapi/linux/cdrom.h also defines IOCTL 0x5301 - 0x5396.
  */
 
 /* Used to obtain PUN and LUN info.  Conflicts with CDROMAUDIOBUFSIZ */
