nvme-pci: Print invalid SGL only once
authorKeith Busch <keith.busch@intel.com>
Fri, 15 Sep 2017 17:05:38 +0000 (13:05 -0400)
committerJens Axboe <axboe@kernel.dk>
Mon, 25 Sep 2017 14:56:05 +0000 (08:56 -0600)
The WARN_ONCE macro returns true if the condition is true, not if the
warn was raised, so we're printing the scatter list every time it's
invalid. This is excessive and makes debugging harder, so this patch
prints it just once.

Signed-off-by: Keith Busch <keith.busch@intel.com>
Reviewed-by: Martin K. Petersen <martin.petersen@oracle.com>
Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Jens Axboe <axboe@kernel.dk>
drivers/nvme/host/pci.c

index 004018c5dccc3c312a307bc5b68d32f2f48653ec..cb73bc8cad3bd2c332bdf3c7c4903e1b0c0f035c 100644 (file)
@@ -24,6 +24,7 @@
 #include <linux/mm.h>
 #include <linux/module.h>
 #include <linux/mutex.h>
+#include <linux/once.h>
 #include <linux/pci.h>
 #include <linux/poison.h>
 #include <linux/t10-pi.h>
@@ -540,6 +541,20 @@ static void nvme_dif_complete(u32 p, u32 v, struct t10_pi_tuple *pi)
 }
 #endif
 
+static void nvme_print_sgl(struct scatterlist *sgl, int nents)
+{
+       int i;
+       struct scatterlist *sg;
+
+       for_each_sg(sgl, sg, nents, i) {
+               dma_addr_t phys = sg_phys(sg);
+               pr_warn("sg[%d] phys_addr:%pad offset:%d length:%d "
+                       "dma_address:%pad dma_length:%d\n",
+                       i, &phys, sg->offset, sg->length, &sg_dma_address(sg),
+                       sg_dma_len(sg));
+       }
+}
+
 static blk_status_t nvme_setup_prps(struct nvme_dev *dev, struct request *req)
 {
        struct nvme_iod *iod = blk_mq_rq_to_pdu(req);
@@ -622,19 +637,10 @@ static blk_status_t nvme_setup_prps(struct nvme_dev *dev, struct request *req)
        return BLK_STS_OK;
 
  bad_sgl:
-       if (WARN_ONCE(1, "Invalid SGL for payload:%d nents:%d\n",
-                               blk_rq_payload_bytes(req), iod->nents)) {
-               for_each_sg(iod->sg, sg, iod->nents, i) {
-                       dma_addr_t phys = sg_phys(sg);
-                       pr_warn("sg[%d] phys_addr:%pad offset:%d length:%d "
-                              "dma_address:%pad dma_length:%d\n", i, &phys,
-                                       sg->offset, sg->length,
-                                       &sg_dma_address(sg),
-                                       sg_dma_len(sg));
-               }
-       }
+       WARN(DO_ONCE(nvme_print_sgl, iod->sg, iod->nents),
+                       "Invalid SGL for payload:%d nents:%d\n",
+                       blk_rq_payload_bytes(req), iod->nents);
        return BLK_STS_IOERR;
-
 }
 
 static blk_status_t nvme_map_data(struct nvme_dev *dev, struct request *req,