diff options
Diffstat (limited to 'drivers/nvme/host/tcp.c')
-rw-r--r-- | drivers/nvme/host/tcp.c | 32 |
1 files changed, 28 insertions, 4 deletions
diff --git a/drivers/nvme/host/tcp.c b/drivers/nvme/host/tcp.c index 208ee518af65..e7e08889865e 100644 --- a/drivers/nvme/host/tcp.c +++ b/drivers/nvme/host/tcp.c | |||
@@ -463,6 +463,15 @@ static int nvme_tcp_handle_c2h_data(struct nvme_tcp_queue *queue, | |||
463 | 463 | ||
464 | queue->data_remaining = le32_to_cpu(pdu->data_length); | 464 | queue->data_remaining = le32_to_cpu(pdu->data_length); |
465 | 465 | ||
466 | if (pdu->hdr.flags & NVME_TCP_F_DATA_SUCCESS && | ||
467 | unlikely(!(pdu->hdr.flags & NVME_TCP_F_DATA_LAST))) { | ||
468 | dev_err(queue->ctrl->ctrl.device, | ||
469 | "queue %d tag %#x SUCCESS set but not last PDU\n", | ||
470 | nvme_tcp_queue_id(queue), rq->tag); | ||
471 | nvme_tcp_error_recovery(&queue->ctrl->ctrl); | ||
472 | return -EPROTO; | ||
473 | } | ||
474 | |||
466 | return 0; | 475 | return 0; |
467 | 476 | ||
468 | } | 477 | } |
@@ -618,6 +627,14 @@ static int nvme_tcp_recv_pdu(struct nvme_tcp_queue *queue, struct sk_buff *skb, | |||
618 | return ret; | 627 | return ret; |
619 | } | 628 | } |
620 | 629 | ||
630 | static inline void nvme_tcp_end_request(struct request *rq, __le16 status) | ||
631 | { | ||
632 | union nvme_result res = {}; | ||
633 | |||
634 | nvme_end_request(rq, cpu_to_le16(status << 1), res); | ||
635 | } | ||
636 | |||
637 | |||
621 | static int nvme_tcp_recv_data(struct nvme_tcp_queue *queue, struct sk_buff *skb, | 638 | static int nvme_tcp_recv_data(struct nvme_tcp_queue *queue, struct sk_buff *skb, |
622 | unsigned int *offset, size_t *len) | 639 | unsigned int *offset, size_t *len) |
623 | { | 640 | { |
@@ -685,6 +702,8 @@ static int nvme_tcp_recv_data(struct nvme_tcp_queue *queue, struct sk_buff *skb, | |||
685 | nvme_tcp_ddgst_final(queue->rcv_hash, &queue->exp_ddgst); | 702 | nvme_tcp_ddgst_final(queue->rcv_hash, &queue->exp_ddgst); |
686 | queue->ddgst_remaining = NVME_TCP_DIGEST_LENGTH; | 703 | queue->ddgst_remaining = NVME_TCP_DIGEST_LENGTH; |
687 | } else { | 704 | } else { |
705 | if (pdu->hdr.flags & NVME_TCP_F_DATA_SUCCESS) | ||
706 | nvme_tcp_end_request(rq, NVME_SC_SUCCESS); | ||
688 | nvme_tcp_init_recv_ctx(queue); | 707 | nvme_tcp_init_recv_ctx(queue); |
689 | } | 708 | } |
690 | } | 709 | } |
@@ -695,6 +714,7 @@ static int nvme_tcp_recv_data(struct nvme_tcp_queue *queue, struct sk_buff *skb, | |||
695 | static int nvme_tcp_recv_ddgst(struct nvme_tcp_queue *queue, | 714 | static int nvme_tcp_recv_ddgst(struct nvme_tcp_queue *queue, |
696 | struct sk_buff *skb, unsigned int *offset, size_t *len) | 715 | struct sk_buff *skb, unsigned int *offset, size_t *len) |
697 | { | 716 | { |
717 | struct nvme_tcp_data_pdu *pdu = (void *)queue->pdu; | ||
698 | char *ddgst = (char *)&queue->recv_ddgst; | 718 | char *ddgst = (char *)&queue->recv_ddgst; |
699 | size_t recv_len = min_t(size_t, *len, queue->ddgst_remaining); | 719 | size_t recv_len = min_t(size_t, *len, queue->ddgst_remaining); |
700 | off_t off = NVME_TCP_DIGEST_LENGTH - queue->ddgst_remaining; | 720 | off_t off = NVME_TCP_DIGEST_LENGTH - queue->ddgst_remaining; |
@@ -718,6 +738,13 @@ static int nvme_tcp_recv_ddgst(struct nvme_tcp_queue *queue, | |||
718 | return -EIO; | 738 | return -EIO; |
719 | } | 739 | } |
720 | 740 | ||
741 | if (pdu->hdr.flags & NVME_TCP_F_DATA_SUCCESS) { | ||
742 | struct request *rq = blk_mq_tag_to_rq(nvme_tcp_tagset(queue), | ||
743 | pdu->command_id); | ||
744 | |||
745 | nvme_tcp_end_request(rq, NVME_SC_SUCCESS); | ||
746 | } | ||
747 | |||
721 | nvme_tcp_init_recv_ctx(queue); | 748 | nvme_tcp_init_recv_ctx(queue); |
722 | return 0; | 749 | return 0; |
723 | } | 750 | } |
@@ -815,10 +842,7 @@ static inline void nvme_tcp_done_send_req(struct nvme_tcp_queue *queue) | |||
815 | 842 | ||
816 | static void nvme_tcp_fail_request(struct nvme_tcp_request *req) | 843 | static void nvme_tcp_fail_request(struct nvme_tcp_request *req) |
817 | { | 844 | { |
818 | union nvme_result res = {}; | 845 | nvme_tcp_end_request(blk_mq_rq_from_pdu(req), NVME_SC_DATA_XFER_ERROR); |
819 | |||
820 | nvme_end_request(blk_mq_rq_from_pdu(req), | ||
821 | cpu_to_le16(NVME_SC_DATA_XFER_ERROR), res); | ||
822 | } | 846 | } |
823 | 847 | ||
824 | static int nvme_tcp_try_send_data(struct nvme_tcp_request *req) | 848 | static int nvme_tcp_try_send_data(struct nvme_tcp_request *req) |