aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/infiniband/ulp/iser/iser_verbs.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/infiniband/ulp/iser/iser_verbs.c')
-rw-r--r--drivers/infiniband/ulp/iser/iser_verbs.c75
1 files changed, 13 insertions, 62 deletions
diff --git a/drivers/infiniband/ulp/iser/iser_verbs.c b/drivers/infiniband/ulp/iser/iser_verbs.c
index 218aa10939a0..18cf65f092e8 100644
--- a/drivers/infiniband/ulp/iser/iser_verbs.c
+++ b/drivers/infiniband/ulp/iser/iser_verbs.c
@@ -194,7 +194,7 @@ static int iser_create_ib_conn_res(struct iser_conn *ib_conn)
194 init_attr.recv_cq = device->rx_cq; 194 init_attr.recv_cq = device->rx_cq;
195 init_attr.cap.max_send_wr = ISER_QP_MAX_REQ_DTOS; 195 init_attr.cap.max_send_wr = ISER_QP_MAX_REQ_DTOS;
196 init_attr.cap.max_recv_wr = ISER_QP_MAX_RECV_DTOS; 196 init_attr.cap.max_recv_wr = ISER_QP_MAX_RECV_DTOS;
197 init_attr.cap.max_send_sge = MAX_REGD_BUF_VECTOR_LEN; 197 init_attr.cap.max_send_sge = 2;
198 init_attr.cap.max_recv_sge = 1; 198 init_attr.cap.max_recv_sge = 1;
199 init_attr.sq_sig_type = IB_SIGNAL_REQ_WR; 199 init_attr.sq_sig_type = IB_SIGNAL_REQ_WR;
200 init_attr.qp_type = IB_QPT_RC; 200 init_attr.qp_type = IB_QPT_RC;
@@ -702,85 +702,36 @@ int iser_post_recvm(struct iser_conn *ib_conn, int count)
702 702
703 703
704/** 704/**
705 * iser_dto_to_iov - builds IOV from a dto descriptor
706 */
707static void iser_dto_to_iov(struct iser_dto *dto, struct ib_sge *iov, int iov_len)
708{
709 int i;
710 struct ib_sge *sge;
711 struct iser_regd_buf *regd_buf;
712
713 if (dto->regd_vector_len > iov_len) {
714 iser_err("iov size %d too small for posting dto of len %d\n",
715 iov_len, dto->regd_vector_len);
716 BUG();
717 }
718
719 for (i = 0; i < dto->regd_vector_len; i++) {
720 sge = &iov[i];
721 regd_buf = dto->regd[i];
722
723 sge->addr = regd_buf->reg.va;
724 sge->length = regd_buf->reg.len;
725 sge->lkey = regd_buf->reg.lkey;
726
727 if (dto->used_sz[i] > 0) /* Adjust size */
728 sge->length = dto->used_sz[i];
729
730 /* offset and length should not exceed the regd buf length */
731 if (sge->length + dto->offset[i] > regd_buf->reg.len) {
732 iser_err("Used len:%ld + offset:%d, exceed reg.buf.len:"
733 "%ld in dto:0x%p [%d], va:0x%08lX\n",
734 (unsigned long)sge->length, dto->offset[i],
735 (unsigned long)regd_buf->reg.len, dto, i,
736 (unsigned long)sge->addr);
737 BUG();
738 }
739
740 sge->addr += dto->offset[i]; /* Adjust offset */
741 }
742}
743
744
745/**
746 * iser_start_send - Initiate a Send DTO operation 705 * iser_start_send - Initiate a Send DTO operation
747 * 706 *
748 * returns 0 on success, -1 on failure 707 * returns 0 on success, -1 on failure
749 */ 708 */
750int iser_post_send(struct iser_desc *tx_desc) 709int iser_post_send(struct iser_conn *ib_conn, struct iser_tx_desc *tx_desc)
751{ 710{
752 int ib_ret, ret_val = 0; 711 int ib_ret;
753 struct ib_send_wr send_wr, *send_wr_failed; 712 struct ib_send_wr send_wr, *send_wr_failed;
754 struct ib_sge iov[MAX_REGD_BUF_VECTOR_LEN];
755 struct iser_conn *ib_conn;
756 struct iser_dto *dto = &tx_desc->dto;
757 713
758 ib_conn = dto->ib_conn; 714 ib_dma_sync_single_for_device(ib_conn->device->ib_device,
759 715 tx_desc->dma_addr, ISER_HEADERS_LEN, DMA_TO_DEVICE);
760 iser_dto_to_iov(dto, iov, MAX_REGD_BUF_VECTOR_LEN);
761 716
762 send_wr.next = NULL; 717 send_wr.next = NULL;
763 send_wr.wr_id = (unsigned long)tx_desc; 718 send_wr.wr_id = (unsigned long)tx_desc;
764 send_wr.sg_list = iov; 719 send_wr.sg_list = tx_desc->tx_sg;
765 send_wr.num_sge = dto->regd_vector_len; 720 send_wr.num_sge = tx_desc->num_sge;
766 send_wr.opcode = IB_WR_SEND; 721 send_wr.opcode = IB_WR_SEND;
767 send_wr.send_flags = dto->notify_enable ? IB_SEND_SIGNALED : 0; 722 send_wr.send_flags = IB_SEND_SIGNALED;
768 723
769 atomic_inc(&ib_conn->post_send_buf_count); 724 atomic_inc(&ib_conn->post_send_buf_count);
770 725
771 ib_ret = ib_post_send(ib_conn->qp, &send_wr, &send_wr_failed); 726 ib_ret = ib_post_send(ib_conn->qp, &send_wr, &send_wr_failed);
772 if (ib_ret) { 727 if (ib_ret) {
773 iser_err("Failed to start SEND DTO, dto: 0x%p, IOV len: %d\n",
774 dto, dto->regd_vector_len);
775 iser_err("ib_post_send failed, ret:%d\n", ib_ret); 728 iser_err("ib_post_send failed, ret:%d\n", ib_ret);
776 atomic_dec(&ib_conn->post_send_buf_count); 729 atomic_dec(&ib_conn->post_send_buf_count);
777 ret_val = -1;
778 } 730 }
779 731 return ib_ret;
780 return ret_val;
781} 732}
782 733
783static void iser_handle_comp_error(struct iser_desc *desc, 734static void iser_handle_comp_error(struct iser_tx_desc *desc,
784 struct iser_conn *ib_conn) 735 struct iser_conn *ib_conn)
785{ 736{
786 if (desc && desc->type == ISCSI_TX_DATAOUT) 737 if (desc && desc->type == ISCSI_TX_DATAOUT)
@@ -809,16 +760,16 @@ static int iser_drain_tx_cq(struct iser_device *device)
809{ 760{
810 struct ib_cq *cq = device->tx_cq; 761 struct ib_cq *cq = device->tx_cq;
811 struct ib_wc wc; 762 struct ib_wc wc;
812 struct iser_desc *tx_desc; 763 struct iser_tx_desc *tx_desc;
813 struct iser_conn *ib_conn; 764 struct iser_conn *ib_conn;
814 int completed_tx = 0; 765 int completed_tx = 0;
815 766
816 while (ib_poll_cq(cq, 1, &wc) == 1) { 767 while (ib_poll_cq(cq, 1, &wc) == 1) {
817 tx_desc = (struct iser_desc *) (unsigned long) wc.wr_id; 768 tx_desc = (struct iser_tx_desc *) (unsigned long) wc.wr_id;
818 ib_conn = wc.qp->qp_context; 769 ib_conn = wc.qp->qp_context;
819 if (wc.status == IB_WC_SUCCESS) { 770 if (wc.status == IB_WC_SUCCESS) {
820 if (wc.opcode == IB_WC_SEND) 771 if (wc.opcode == IB_WC_SEND)
821 iser_snd_completion(tx_desc); 772 iser_snd_completion(tx_desc, ib_conn);
822 else 773 else
823 iser_err("expected opcode %d got %d\n", 774 iser_err("expected opcode %d got %d\n",
824 IB_WC_SEND, wc.opcode); 775 IB_WC_SEND, wc.opcode);