scsi: mpi3mr: Fix scheduling while atomic type bug
authorSreekanth Reddy <sreekanth.reddy@broadcom.com>
Mon, 12 Sep 2022 13:57:41 +0000 (19:27 +0530)
committerMartin K. Petersen <martin.petersen@oracle.com>
Sun, 25 Sep 2022 17:49:52 +0000 (13:49 -0400)
Fix 'scheduling while atomic' type bug, which is observed when
pci_irq_vector() is called from interrupt context.

Link: https://lore.kernel.org/r/20220912135742.11764-9-sreekanth.reddy@broadcom.com
Signed-off-by: Sreekanth Reddy <sreekanth.reddy@broadcom.com>
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
drivers/scsi/mpi3mr/mpi3mr.h
drivers/scsi/mpi3mr/mpi3mr_fw.c

index 5b10504..41dc2bb 100644 (file)
@@ -431,12 +431,14 @@ struct op_reply_qinfo {
  * struct mpi3mr_intr_info -  Interrupt cookie information
  *
  * @mrioc: Adapter instance reference
+ * @os_irq: irq number
  * @msix_index: MSIx index
  * @op_reply_q: Associated operational reply queue
  * @name: Dev name for the irq claiming device
  */
 struct mpi3mr_intr_info {
        struct mpi3mr_ioc *mrioc;
+       int os_irq;
        u16 msix_index;
        struct op_reply_qinfo *op_reply_q;
        char name[MPI3MR_NAME_LENGTH];
index f841a44..d5da49a 100644 (file)
@@ -627,15 +627,11 @@ static irqreturn_t mpi3mr_isr_primary(int irq, void *privdata)
 static irqreturn_t mpi3mr_isr(int irq, void *privdata)
 {
        struct mpi3mr_intr_info *intr_info = privdata;
-       struct mpi3mr_ioc *mrioc;
-       u16 midx;
        int ret;
 
        if (!intr_info)
                return IRQ_NONE;
 
-       mrioc = intr_info->mrioc;
-       midx = intr_info->msix_index;
        /* Call primary ISR routine */
        ret = mpi3mr_isr_primary(irq, privdata);
 
@@ -650,7 +646,7 @@ static irqreturn_t mpi3mr_isr(int irq, void *privdata)
            !atomic_read(&intr_info->op_reply_q->pend_ios))
                return ret;
 
-       disable_irq_nosync(pci_irq_vector(mrioc->pdev, midx));
+       disable_irq_nosync(intr_info->os_irq);
 
        return IRQ_WAKE_THREAD;
 }
@@ -696,7 +692,7 @@ static irqreturn_t mpi3mr_isr_poll(int irq, void *privdata)
            (num_op_reply < mrioc->max_host_ios));
 
        intr_info->op_reply_q->enable_irq_poll = false;
-       enable_irq(pci_irq_vector(mrioc->pdev, midx));
+       enable_irq(intr_info->os_irq);
 
        return IRQ_HANDLED;
 }
@@ -738,6 +734,7 @@ static inline int mpi3mr_request_irq(struct mpi3mr_ioc *mrioc, u16 index)
                return retval;
        }
 
+       intr_info->os_irq = pci_irq_vector(pdev, index);
        return retval;
 }