]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
scsi: ufs: core: Fix NULL pointer dereference in scsi_cmd_priv() calls
authorChanwoo Lee <cw9316.lee@samsung.com>
Fri, 29 May 2026 01:07:39 +0000 (10:07 +0900)
committerMartin K. Petersen <martin.petersen@oracle.com>
Tue, 2 Jun 2026 01:57:52 +0000 (21:57 -0400)
ufshcd_tag_to_cmd() may return NULL if no command is associated with the
given tag. However, several callers dereference the returned cmd pointer
via scsi_cmd_priv() without checking for NULL first, leading to a
potential NULL pointer dereference.

Fix this by adding NULL checks for cmd before calling scsi_cmd_priv()
and moving the lrbp initialization after the NULL check.

Signed-off-by: Chanwoo Lee <cw9316.lee@samsung.com>
Reviewed-by: Peter Wang <peter.wang@mediatek.com>
Reviewed-by: Bart Van Assche <bvanassche@acm.org>
Link: https://patch.msgid.link/20260529010739.295391-1-cw9316.lee@samsung.com
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
drivers/ufs/core/ufs-mcq.c
drivers/ufs/core/ufshcd.c

index c1b1d67a1ddc0493686101668d35e3441c68ff65..13b60a2d06db6aacf96dffdeb881faf2c09e5dff 100644 (file)
@@ -637,7 +637,7 @@ static bool ufshcd_mcq_sqe_search(struct ufs_hba *hba,
                                  struct ufs_hw_queue *hwq, int task_tag)
 {
        struct scsi_cmnd *cmd = ufshcd_tag_to_cmd(hba, task_tag);
-       struct ufshcd_lrb *lrbp = scsi_cmd_priv(cmd);
+       struct ufshcd_lrb *lrbp;
        struct utp_transfer_req_desc *utrd;
        __le64  cmd_desc_base_addr;
        bool ret = false;
@@ -647,6 +647,11 @@ static bool ufshcd_mcq_sqe_search(struct ufs_hba *hba,
        if (hba->quirks & UFSHCD_QUIRK_MCQ_BROKEN_RTC)
                return true;
 
+       if (!cmd)
+               return false;
+
+       lrbp = scsi_cmd_priv(cmd);
+
        mutex_lock(&hwq->sq_mutex);
 
        ufshcd_mcq_sq_stop(hba, hwq);
index 1061e20786fa41f2345081522719841f5828a53a..9b6cb6b569bc93b7ccc50cd039493ca09fb4f089 100644 (file)
@@ -7903,8 +7903,12 @@ static void ufshcd_set_req_abort_skip(struct ufs_hba *hba, unsigned long bitmap)
 
        for_each_set_bit(tag, &bitmap, hba->nutrs) {
                struct scsi_cmnd *cmd = ufshcd_tag_to_cmd(hba, tag);
-               struct ufshcd_lrb *lrbp = scsi_cmd_priv(cmd);
+               struct ufshcd_lrb *lrbp;
 
+               if (!cmd)
+                       continue;
+
+               lrbp = scsi_cmd_priv(cmd);
                lrbp->req_abort_skip = true;
        }
 }
@@ -7925,11 +7929,16 @@ static void ufshcd_set_req_abort_skip(struct ufs_hba *hba, unsigned long bitmap)
 int ufshcd_try_to_abort_task(struct ufs_hba *hba, int tag)
 {
        struct scsi_cmnd *cmd = ufshcd_tag_to_cmd(hba, tag);
-       struct ufshcd_lrb *lrbp = scsi_cmd_priv(cmd);
+       struct ufshcd_lrb *lrbp;
        int err;
        int poll_cnt;
        u8 resp = 0xF;
 
+       if (!cmd)
+               return -EINVAL;
+
+       lrbp = scsi_cmd_priv(cmd);
+
        for (poll_cnt = 100; poll_cnt; poll_cnt--) {
                err = ufshcd_issue_tm_cmd(hba, lrbp->lun, tag, UFS_QUERY_TASK,
                                          &resp);