summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2025-11-22 10:16:21 -0800
committerLinus Torvalds <torvalds@linux-foundation.org>2025-11-22 10:16:21 -0800
commit7e29f077609413f94f70d4da4d7602a59abad991 (patch)
tree626062fe9abc6464ba2771c8e1a2964040e0ee16
parentebd975458deada5eadcc9f4e0f63fc4ce6aa90ea (diff)
parent90449f2d1e1f020835cba5417234636937dd657e (diff)
Merge tag 'scsi-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi
Pull SCSI fixes from James Bottomley: "One target driver fix and one scsi-generic one. The latter is 10 lines because the problem lock has to be dropped and re-taken around the call causing the sleep in atomic" * tag 'scsi-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi: scsi: sg: Do not sleep in atomic context scsi: target: tcm_loop: Fix segfault in tcm_loop_tpg_address_show()
-rw-r--r--drivers/scsi/sg.c10
-rw-r--r--drivers/target/loopback/tcm_loop.c3
2 files changed, 12 insertions, 1 deletions
diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c
index 4c62c597c7be..b3af9b78fa12 100644
--- a/drivers/scsi/sg.c
+++ b/drivers/scsi/sg.c
@@ -2208,9 +2208,17 @@ sg_remove_sfp_usercontext(struct work_struct *work)
write_lock_irqsave(&sfp->rq_list_lock, iflags);
while (!list_empty(&sfp->rq_list)) {
srp = list_first_entry(&sfp->rq_list, Sg_request, entry);
- sg_finish_rem_req(srp);
list_del(&srp->entry);
+ write_unlock_irqrestore(&sfp->rq_list_lock, iflags);
+
+ sg_finish_rem_req(srp);
+ /*
+ * sg_rq_end_io() uses srp->parentfp. Hence, only clear
+ * srp->parentfp after blk_mq_free_request() has been called.
+ */
srp->parentfp = NULL;
+
+ write_lock_irqsave(&sfp->rq_list_lock, iflags);
}
write_unlock_irqrestore(&sfp->rq_list_lock, iflags);
diff --git a/drivers/target/loopback/tcm_loop.c b/drivers/target/loopback/tcm_loop.c
index c7b7da629741..01a8e349dc4d 100644
--- a/drivers/target/loopback/tcm_loop.c
+++ b/drivers/target/loopback/tcm_loop.c
@@ -894,6 +894,9 @@ static ssize_t tcm_loop_tpg_address_show(struct config_item *item,
struct tcm_loop_tpg, tl_se_tpg);
struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba;
+ if (!tl_hba->sh)
+ return -ENODEV;
+
return snprintf(page, PAGE_SIZE, "%d:0:%d\n",
tl_hba->sh->host_no, tl_tpg->tl_tpgt);
}