aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorJens Axboe <axboe@fb.com>2015-11-03 22:37:26 -0500
committerJens Axboe <axboe@fb.com>2015-11-07 12:40:47 -0500
commita0fa9647a54e81883abd57c5c865d1747f68a577 (patch)
treef017a7459fd6e0cc36b0e004c7d4a059b5a04c15 /drivers
parent05229beeddf7e75e2e616ddaad4b70e7fca9528d (diff)
NVMe: add blk polling support
Add nvme_poll(), which will check a specific completion queue for command completions. Wire that up to the new block layer poll mechanism. Signed-off-by: Jens Axboe <axboe@fb.com> Signed-off-by: Christoph Hellwig <hch@lst.de> Acked-by: Keith Busch <keith.busch@intel.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/nvme/host/pci.c32
1 files changed, 28 insertions, 4 deletions
diff --git a/drivers/nvme/host/pci.c b/drivers/nvme/host/pci.c
index e878590e71b6..4a715f49f5db 100644
--- a/drivers/nvme/host/pci.c
+++ b/drivers/nvme/host/pci.c
@@ -90,7 +90,7 @@ static struct class *nvme_class;
90 90
91static int __nvme_reset(struct nvme_dev *dev); 91static int __nvme_reset(struct nvme_dev *dev);
92static int nvme_reset(struct nvme_dev *dev); 92static int nvme_reset(struct nvme_dev *dev);
93static int nvme_process_cq(struct nvme_queue *nvmeq); 93static void nvme_process_cq(struct nvme_queue *nvmeq);
94static void nvme_dead_ctrl(struct nvme_dev *dev); 94static void nvme_dead_ctrl(struct nvme_dev *dev);
95 95
96struct async_cmd_info { 96struct async_cmd_info {
@@ -935,7 +935,7 @@ static int nvme_queue_rq(struct blk_mq_hw_ctx *hctx,
935 return BLK_MQ_RQ_QUEUE_BUSY; 935 return BLK_MQ_RQ_QUEUE_BUSY;
936} 936}
937 937
938static int nvme_process_cq(struct nvme_queue *nvmeq) 938static void __nvme_process_cq(struct nvme_queue *nvmeq, unsigned int *tag)
939{ 939{
940 u16 head, phase; 940 u16 head, phase;
941 941
@@ -953,6 +953,8 @@ static int nvme_process_cq(struct nvme_queue *nvmeq)
953 head = 0; 953 head = 0;
954 phase = !phase; 954 phase = !phase;
955 } 955 }
956 if (tag && *tag == cqe.command_id)
957 *tag = -1;
956 ctx = nvme_finish_cmd(nvmeq, cqe.command_id, &fn); 958 ctx = nvme_finish_cmd(nvmeq, cqe.command_id, &fn);
957 fn(nvmeq, ctx, &cqe); 959 fn(nvmeq, ctx, &cqe);
958 } 960 }
@@ -964,14 +966,18 @@ static int nvme_process_cq(struct nvme_queue *nvmeq)
964 * a big problem. 966 * a big problem.
965 */ 967 */
966 if (head == nvmeq->cq_head && phase == nvmeq->cq_phase) 968 if (head == nvmeq->cq_head && phase == nvmeq->cq_phase)
967 return 0; 969 return;
968 970
969 writel(head, nvmeq->q_db + nvmeq->dev->db_stride); 971 writel(head, nvmeq->q_db + nvmeq->dev->db_stride);
970 nvmeq->cq_head = head; 972 nvmeq->cq_head = head;
971 nvmeq->cq_phase = phase; 973 nvmeq->cq_phase = phase;
972 974
973 nvmeq->cqe_seen = 1; 975 nvmeq->cqe_seen = 1;
974 return 1; 976}
977
978static void nvme_process_cq(struct nvme_queue *nvmeq)
979{
980 __nvme_process_cq(nvmeq, NULL);
975} 981}
976 982
977static irqreturn_t nvme_irq(int irq, void *data) 983static irqreturn_t nvme_irq(int irq, void *data)
@@ -995,6 +1001,23 @@ static irqreturn_t nvme_irq_check(int irq, void *data)
995 return IRQ_WAKE_THREAD; 1001 return IRQ_WAKE_THREAD;
996} 1002}
997 1003
1004static int nvme_poll(struct blk_mq_hw_ctx *hctx, unsigned int tag)
1005{
1006 struct nvme_queue *nvmeq = hctx->driver_data;
1007
1008 if ((le16_to_cpu(nvmeq->cqes[nvmeq->cq_head].status) & 1) ==
1009 nvmeq->cq_phase) {
1010 spin_lock_irq(&nvmeq->q_lock);
1011 __nvme_process_cq(nvmeq, &tag);
1012 spin_unlock_irq(&nvmeq->q_lock);
1013
1014 if (tag == -1)
1015 return 1;
1016 }
1017
1018 return 0;
1019}
1020
998/* 1021/*
999 * Returns 0 on success. If the result is negative, it's a Linux error code; 1022 * Returns 0 on success. If the result is negative, it's a Linux error code;
1000 * if the result is positive, it's an NVM Express status code 1023 * if the result is positive, it's an NVM Express status code
@@ -1654,6 +1677,7 @@ static struct blk_mq_ops nvme_mq_ops = {
1654 .init_hctx = nvme_init_hctx, 1677 .init_hctx = nvme_init_hctx,
1655 .init_request = nvme_init_request, 1678 .init_request = nvme_init_request,
1656 .timeout = nvme_timeout, 1679 .timeout = nvme_timeout,
1680 .poll = nvme_poll,
1657}; 1681};
1658 1682
1659static void nvme_dev_remove_admin(struct nvme_dev *dev) 1683static void nvme_dev_remove_admin(struct nvme_dev *dev)