aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSagi Grimberg <sagi@grimberg.me>2017-06-18 10:28:08 -0400
committerJens Axboe <axboe@kernel.dk>2017-06-28 10:14:13 -0400
commit83a12fb77b941a6735026e46c8ef5f4ec1204e97 (patch)
tree9410ae40e14d107e6cb4cc711499542c40cd2630
parenteb281c8283e87a2d1d6ed406f9c6408c39737b4d (diff)
nvme-pci: factor out cqe handling into a dedicated routine
Makes the code slightly more readable. Signed-off-by: Sagi Grimberg <sagi@grimberg.me> Reviewed-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Keith Busch <keith.busch@intel.com> Signed-off-by: Jens Axboe <axboe@kernel.dk>
-rw-r--r--drivers/nvme/host/pci.c53
1 files changed, 30 insertions, 23 deletions
diff --git a/drivers/nvme/host/pci.c b/drivers/nvme/host/pci.c
index 042cfe5ef8e9..26eb1743f8bc 100644
--- a/drivers/nvme/host/pci.c
+++ b/drivers/nvme/host/pci.c
@@ -741,6 +741,35 @@ static inline void nvme_ring_cq_doorbell(struct nvme_queue *nvmeq)
741 } 741 }
742} 742}
743 743
744static inline void nvme_handle_cqe(struct nvme_queue *nvmeq,
745 struct nvme_completion *cqe)
746{
747 struct request *req;
748
749 if (unlikely(cqe->command_id >= nvmeq->q_depth)) {
750 dev_warn(nvmeq->dev->ctrl.device,
751 "invalid id %d completed on queue %d\n",
752 cqe->command_id, le16_to_cpu(cqe->sq_id));
753 return;
754 }
755
756 /*
757 * AEN requests are special as they don't time out and can
758 * survive any kind of queue freeze and often don't respond to
759 * aborts. We don't even bother to allocate a struct request
760 * for them but rather special case them here.
761 */
762 if (unlikely(nvmeq->qid == 0 &&
763 cqe->command_id >= NVME_AQ_BLKMQ_DEPTH)) {
764 nvme_complete_async_event(&nvmeq->dev->ctrl,
765 cqe->status, &cqe->result);
766 return;
767 }
768
769 req = blk_mq_tag_to_rq(*nvmeq->tags, cqe->command_id);
770 nvme_end_request(req, cqe->status, cqe->result);
771}
772
744static void __nvme_process_cq(struct nvme_queue *nvmeq, unsigned int *tag) 773static void __nvme_process_cq(struct nvme_queue *nvmeq, unsigned int *tag)
745{ 774{
746 u16 head, phase; 775 u16 head, phase;
@@ -750,7 +779,6 @@ static void __nvme_process_cq(struct nvme_queue *nvmeq, unsigned int *tag)
750 779
751 while (nvme_cqe_valid(nvmeq, head, phase)) { 780 while (nvme_cqe_valid(nvmeq, head, phase)) {
752 struct nvme_completion cqe = nvmeq->cqes[head]; 781 struct nvme_completion cqe = nvmeq->cqes[head];
753 struct request *req;
754 782
755 if (++head == nvmeq->q_depth) { 783 if (++head == nvmeq->q_depth) {
756 head = 0; 784 head = 0;
@@ -760,28 +788,7 @@ static void __nvme_process_cq(struct nvme_queue *nvmeq, unsigned int *tag)
760 if (tag && *tag == cqe.command_id) 788 if (tag && *tag == cqe.command_id)
761 *tag = -1; 789 *tag = -1;
762 790
763 if (unlikely(cqe.command_id >= nvmeq->q_depth)) { 791 nvme_handle_cqe(nvmeq, &cqe);
764 dev_warn(nvmeq->dev->ctrl.device,
765 "invalid id %d completed on queue %d\n",
766 cqe.command_id, le16_to_cpu(cqe.sq_id));
767 continue;
768 }
769
770 /*
771 * AEN requests are special as they don't time out and can
772 * survive any kind of queue freeze and often don't respond to
773 * aborts. We don't even bother to allocate a struct request
774 * for them but rather special case them here.
775 */
776 if (unlikely(nvmeq->qid == 0 &&
777 cqe.command_id >= NVME_AQ_BLKMQ_DEPTH)) {
778 nvme_complete_async_event(&nvmeq->dev->ctrl,
779 cqe.status, &cqe.result);
780 continue;
781 }
782
783 req = blk_mq_tag_to_rq(*nvmeq->tags, cqe.command_id);
784 nvme_end_request(req, cqe.status, cqe.result);
785 } 792 }
786 793
787 if (head == nvmeq->cq_head && phase == nvmeq->cq_phase) 794 if (head == nvmeq->cq_head && phase == nvmeq->cq_phase)