diff options
Diffstat (limited to 'drivers/infiniband')
-rw-r--r-- | drivers/infiniband/ulp/iser/iscsi_iser.c | 13 | ||||
-rw-r--r-- | drivers/infiniband/ulp/iser/iscsi_iser.h | 3 | ||||
-rw-r--r-- | drivers/infiniband/ulp/iser/iser_verbs.c | 29 |
3 files changed, 22 insertions, 23 deletions
diff --git a/drivers/infiniband/ulp/iser/iscsi_iser.c b/drivers/infiniband/ulp/iser/iscsi_iser.c index 3dc853c9e4bf..61ee91d88380 100644 --- a/drivers/infiniband/ulp/iser/iscsi_iser.c +++ b/drivers/infiniband/ulp/iser/iscsi_iser.c | |||
@@ -627,10 +627,8 @@ iscsi_iser_ep_poll(struct iscsi_endpoint *ep, int timeout_ms) | |||
627 | int rc; | 627 | int rc; |
628 | 628 | ||
629 | ib_conn = ep->dd_data; | 629 | ib_conn = ep->dd_data; |
630 | rc = wait_event_interruptible_timeout(ib_conn->wait, | 630 | rc = wait_for_completion_interruptible_timeout(&ib_conn->up_completion, |
631 | ib_conn->state == ISER_CONN_UP, | 631 | msecs_to_jiffies(timeout_ms)); |
632 | msecs_to_jiffies(timeout_ms)); | ||
633 | |||
634 | /* if conn establishment failed, return error code to iscsi */ | 632 | /* if conn establishment failed, return error code to iscsi */ |
635 | if (rc == 0) { | 633 | if (rc == 0) { |
636 | mutex_lock(&ib_conn->state_mutex); | 634 | mutex_lock(&ib_conn->state_mutex); |
@@ -661,9 +659,10 @@ iscsi_iser_ep_disconnect(struct iscsi_endpoint *ep) | |||
661 | iser_conn_terminate(ib_conn); | 659 | iser_conn_terminate(ib_conn); |
662 | 660 | ||
663 | /* | 661 | /* |
664 | * if iser_conn and iscsi_conn are bound, we must wait iscsi_conn_stop | 662 | * if iser_conn and iscsi_conn are bound, we must wait for |
665 | * call and ISER_CONN_DOWN state before freeing the iser resources. | 663 | * iscsi_conn_stop and flush errors completion before freeing |
666 | * otherwise we are safe to free resources immediately. | 664 | * the iser resources. Otherwise we are safe to free resources |
665 | * immediately. | ||
667 | */ | 666 | */ |
668 | if (ib_conn->iscsi_conn) { | 667 | if (ib_conn->iscsi_conn) { |
669 | INIT_WORK(&ib_conn->release_work, iser_release_work); | 668 | INIT_WORK(&ib_conn->release_work, iser_release_work); |
diff --git a/drivers/infiniband/ulp/iser/iscsi_iser.h b/drivers/infiniband/ulp/iser/iscsi_iser.h index c7efc5a91604..c877dad381cb 100644 --- a/drivers/infiniband/ulp/iser/iscsi_iser.h +++ b/drivers/infiniband/ulp/iser/iscsi_iser.h | |||
@@ -326,7 +326,6 @@ struct iser_conn { | |||
326 | struct iser_device *device; /* device context */ | 326 | struct iser_device *device; /* device context */ |
327 | struct rdma_cm_id *cma_id; /* CMA ID */ | 327 | struct rdma_cm_id *cma_id; /* CMA ID */ |
328 | struct ib_qp *qp; /* QP */ | 328 | struct ib_qp *qp; /* QP */ |
329 | wait_queue_head_t wait; /* waitq for conn/disconn */ | ||
330 | unsigned qp_max_recv_dtos; /* num of rx buffers */ | 329 | unsigned qp_max_recv_dtos; /* num of rx buffers */ |
331 | unsigned qp_max_recv_dtos_mask; /* above minus 1 */ | 330 | unsigned qp_max_recv_dtos_mask; /* above minus 1 */ |
332 | unsigned min_posted_rx; /* qp_max_recv_dtos >> 2 */ | 331 | unsigned min_posted_rx; /* qp_max_recv_dtos >> 2 */ |
@@ -336,6 +335,8 @@ struct iser_conn { | |||
336 | struct work_struct release_work; | 335 | struct work_struct release_work; |
337 | struct completion stop_completion; | 336 | struct completion stop_completion; |
338 | struct mutex state_mutex; | 337 | struct mutex state_mutex; |
338 | struct completion flush_completion; | ||
339 | struct completion up_completion; | ||
339 | struct list_head conn_list; /* entry in ig conn list */ | 340 | struct list_head conn_list; /* entry in ig conn list */ |
340 | 341 | ||
341 | char *login_buf; | 342 | char *login_buf; |
diff --git a/drivers/infiniband/ulp/iser/iser_verbs.c b/drivers/infiniband/ulp/iser/iser_verbs.c index 6e7e54d883ab..06a49b3df3fd 100644 --- a/drivers/infiniband/ulp/iser/iser_verbs.c +++ b/drivers/infiniband/ulp/iser/iser_verbs.c | |||
@@ -582,15 +582,19 @@ static int iser_conn_state_comp_exch(struct iser_conn *ib_conn, | |||
582 | void iser_release_work(struct work_struct *work) | 582 | void iser_release_work(struct work_struct *work) |
583 | { | 583 | { |
584 | struct iser_conn *ib_conn; | 584 | struct iser_conn *ib_conn; |
585 | int rc; | ||
585 | 586 | ||
586 | ib_conn = container_of(work, struct iser_conn, release_work); | 587 | ib_conn = container_of(work, struct iser_conn, release_work); |
587 | 588 | ||
588 | /* wait for .conn_stop callback */ | 589 | /* wait for .conn_stop callback */ |
589 | wait_for_completion(&ib_conn->stop_completion); | 590 | rc = wait_for_completion_timeout(&ib_conn->stop_completion, 30 * HZ); |
591 | WARN_ON(rc == 0); | ||
590 | 592 | ||
591 | /* wait for the qp`s post send and post receive buffers to empty */ | 593 | /* wait for the qp`s post send and post receive buffers to empty */ |
592 | wait_event_interruptible(ib_conn->wait, | 594 | rc = wait_for_completion_timeout(&ib_conn->flush_completion, 30 * HZ); |
593 | ib_conn->state == ISER_CONN_DOWN); | 595 | WARN_ON(rc == 0); |
596 | |||
597 | ib_conn->state = ISER_CONN_DOWN; | ||
594 | 598 | ||
595 | mutex_lock(&ib_conn->state_mutex); | 599 | mutex_lock(&ib_conn->state_mutex); |
596 | ib_conn->state = ISER_CONN_DOWN; | 600 | ib_conn->state = ISER_CONN_DOWN; |
@@ -656,9 +660,7 @@ static void iser_connect_error(struct rdma_cm_id *cma_id) | |||
656 | struct iser_conn *ib_conn; | 660 | struct iser_conn *ib_conn; |
657 | 661 | ||
658 | ib_conn = (struct iser_conn *)cma_id->context; | 662 | ib_conn = (struct iser_conn *)cma_id->context; |
659 | |||
660 | ib_conn->state = ISER_CONN_DOWN; | 663 | ib_conn->state = ISER_CONN_DOWN; |
661 | wake_up_interruptible(&ib_conn->wait); | ||
662 | } | 664 | } |
663 | 665 | ||
664 | /** | 666 | /** |
@@ -761,9 +763,8 @@ static void iser_connected_handler(struct rdma_cm_id *cma_id) | |||
761 | (void)ib_query_qp(cma_id->qp, &attr, ~0, &init_attr); | 763 | (void)ib_query_qp(cma_id->qp, &attr, ~0, &init_attr); |
762 | iser_info("remote qpn:%x my qpn:%x\n", attr.dest_qp_num, cma_id->qp->qp_num); | 764 | iser_info("remote qpn:%x my qpn:%x\n", attr.dest_qp_num, cma_id->qp->qp_num); |
763 | 765 | ||
764 | ib_conn = (struct iser_conn *)cma_id->context; | 766 | ib_conn->state = ISER_CONN_UP; |
765 | if (iser_conn_state_comp_exch(ib_conn, ISER_CONN_PENDING, ISER_CONN_UP)) | 767 | complete(&ib_conn->up_completion); |
766 | wake_up_interruptible(&ib_conn->wait); | ||
767 | } | 768 | } |
768 | 769 | ||
769 | static void iser_disconnected_handler(struct rdma_cm_id *cma_id) | 770 | static void iser_disconnected_handler(struct rdma_cm_id *cma_id) |
@@ -785,8 +786,7 @@ static void iser_disconnected_handler(struct rdma_cm_id *cma_id) | |||
785 | /* Complete the termination process if no posts are pending */ | 786 | /* Complete the termination process if no posts are pending */ |
786 | if (ib_conn->post_recv_buf_count == 0 && | 787 | if (ib_conn->post_recv_buf_count == 0 && |
787 | (atomic_read(&ib_conn->post_send_buf_count) == 0)) { | 788 | (atomic_read(&ib_conn->post_send_buf_count) == 0)) { |
788 | ib_conn->state = ISER_CONN_DOWN; | 789 | complete(&ib_conn->flush_completion); |
789 | wake_up_interruptible(&ib_conn->wait); | ||
790 | } | 790 | } |
791 | } | 791 | } |
792 | 792 | ||
@@ -833,10 +833,11 @@ static int iser_cma_handler(struct rdma_cm_id *cma_id, struct rdma_cm_event *eve | |||
833 | void iser_conn_init(struct iser_conn *ib_conn) | 833 | void iser_conn_init(struct iser_conn *ib_conn) |
834 | { | 834 | { |
835 | ib_conn->state = ISER_CONN_INIT; | 835 | ib_conn->state = ISER_CONN_INIT; |
836 | init_waitqueue_head(&ib_conn->wait); | ||
837 | ib_conn->post_recv_buf_count = 0; | 836 | ib_conn->post_recv_buf_count = 0; |
838 | atomic_set(&ib_conn->post_send_buf_count, 0); | 837 | atomic_set(&ib_conn->post_send_buf_count, 0); |
839 | init_completion(&ib_conn->stop_completion); | 838 | init_completion(&ib_conn->stop_completion); |
839 | init_completion(&ib_conn->flush_completion); | ||
840 | init_completion(&ib_conn->up_completion); | ||
840 | INIT_LIST_HEAD(&ib_conn->conn_list); | 841 | INIT_LIST_HEAD(&ib_conn->conn_list); |
841 | spin_lock_init(&ib_conn->lock); | 842 | spin_lock_init(&ib_conn->lock); |
842 | mutex_init(&ib_conn->state_mutex); | 843 | mutex_init(&ib_conn->state_mutex); |
@@ -880,8 +881,7 @@ int iser_connect(struct iser_conn *ib_conn, | |||
880 | } | 881 | } |
881 | 882 | ||
882 | if (!non_blocking) { | 883 | if (!non_blocking) { |
883 | wait_event_interruptible(ib_conn->wait, | 884 | wait_for_completion_interruptible(&ib_conn->up_completion); |
884 | (ib_conn->state != ISER_CONN_PENDING)); | ||
885 | 885 | ||
886 | if (ib_conn->state != ISER_CONN_UP) { | 886 | if (ib_conn->state != ISER_CONN_UP) { |
887 | err = -EIO; | 887 | err = -EIO; |
@@ -1097,8 +1097,7 @@ static void iser_handle_comp_error(struct iser_tx_desc *desc, | |||
1097 | 1097 | ||
1098 | /* no more non completed posts to the QP, complete the | 1098 | /* no more non completed posts to the QP, complete the |
1099 | * termination process w.o worrying on disconnect event */ | 1099 | * termination process w.o worrying on disconnect event */ |
1100 | ib_conn->state = ISER_CONN_DOWN; | 1100 | complete(&ib_conn->flush_completion); |
1101 | wake_up_interruptible(&ib_conn->wait); | ||
1102 | } | 1101 | } |
1103 | } | 1102 | } |
1104 | 1103 | ||