aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/target/iscsi/iscsi_target.c30
-rw-r--r--drivers/target/iscsi/iscsi_target_erl0.c6
-rw-r--r--drivers/target/iscsi/iscsi_target_erl0.h2
-rw-r--r--drivers/target/iscsi/iscsi_target_login.c4
4 files changed, 34 insertions, 8 deletions
diff --git a/drivers/target/iscsi/iscsi_target.c b/drivers/target/iscsi/iscsi_target.c
index 26a9bcd5ee6a..0d8f81591bed 100644
--- a/drivers/target/iscsi/iscsi_target.c
+++ b/drivers/target/iscsi/iscsi_target.c
@@ -3790,6 +3790,8 @@ int iscsi_target_tx_thread(void *arg)
3790{ 3790{
3791 int ret = 0; 3791 int ret = 0;
3792 struct iscsi_conn *conn = arg; 3792 struct iscsi_conn *conn = arg;
3793 bool conn_freed = false;
3794
3793 /* 3795 /*
3794 * Allow ourselves to be interrupted by SIGINT so that a 3796 * Allow ourselves to be interrupted by SIGINT so that a
3795 * connection recovery / failure event can be triggered externally. 3797 * connection recovery / failure event can be triggered externally.
@@ -3815,12 +3817,14 @@ get_immediate:
3815 goto transport_err; 3817 goto transport_err;
3816 3818
3817 ret = iscsit_handle_response_queue(conn); 3819 ret = iscsit_handle_response_queue(conn);
3818 if (ret == 1) 3820 if (ret == 1) {
3819 goto get_immediate; 3821 goto get_immediate;
3820 else if (ret == -ECONNRESET) 3822 } else if (ret == -ECONNRESET) {
3823 conn_freed = true;
3821 goto out; 3824 goto out;
3822 else if (ret < 0) 3825 } else if (ret < 0) {
3823 goto transport_err; 3826 goto transport_err;
3827 }
3824 } 3828 }
3825 3829
3826transport_err: 3830transport_err:
@@ -3830,8 +3834,13 @@ transport_err:
3830 * responsible for cleaning up the early connection failure. 3834 * responsible for cleaning up the early connection failure.
3831 */ 3835 */
3832 if (conn->conn_state != TARG_CONN_STATE_IN_LOGIN) 3836 if (conn->conn_state != TARG_CONN_STATE_IN_LOGIN)
3833 iscsit_take_action_for_connection_exit(conn); 3837 iscsit_take_action_for_connection_exit(conn, &conn_freed);
3834out: 3838out:
3839 if (!conn_freed) {
3840 while (!kthread_should_stop()) {
3841 msleep(100);
3842 }
3843 }
3835 return 0; 3844 return 0;
3836} 3845}
3837 3846
@@ -4004,6 +4013,7 @@ int iscsi_target_rx_thread(void *arg)
4004{ 4013{
4005 int rc; 4014 int rc;
4006 struct iscsi_conn *conn = arg; 4015 struct iscsi_conn *conn = arg;
4016 bool conn_freed = false;
4007 4017
4008 /* 4018 /*
4009 * Allow ourselves to be interrupted by SIGINT so that a 4019 * Allow ourselves to be interrupted by SIGINT so that a
@@ -4016,7 +4026,7 @@ int iscsi_target_rx_thread(void *arg)
4016 */ 4026 */
4017 rc = wait_for_completion_interruptible(&conn->rx_login_comp); 4027 rc = wait_for_completion_interruptible(&conn->rx_login_comp);
4018 if (rc < 0 || iscsi_target_check_conn_state(conn)) 4028 if (rc < 0 || iscsi_target_check_conn_state(conn))
4019 return 0; 4029 goto out;
4020 4030
4021 if (!conn->conn_transport->iscsit_get_rx_pdu) 4031 if (!conn->conn_transport->iscsit_get_rx_pdu)
4022 return 0; 4032 return 0;
@@ -4025,7 +4035,15 @@ int iscsi_target_rx_thread(void *arg)
4025 4035
4026 if (!signal_pending(current)) 4036 if (!signal_pending(current))
4027 atomic_set(&conn->transport_failed, 1); 4037 atomic_set(&conn->transport_failed, 1);
4028 iscsit_take_action_for_connection_exit(conn); 4038 iscsit_take_action_for_connection_exit(conn, &conn_freed);
4039
4040out:
4041 if (!conn_freed) {
4042 while (!kthread_should_stop()) {
4043 msleep(100);
4044 }
4045 }
4046
4029 return 0; 4047 return 0;
4030} 4048}
4031 4049
diff --git a/drivers/target/iscsi/iscsi_target_erl0.c b/drivers/target/iscsi/iscsi_target_erl0.c
index 9a96e17bf7cd..7fe2aa73cff6 100644
--- a/drivers/target/iscsi/iscsi_target_erl0.c
+++ b/drivers/target/iscsi/iscsi_target_erl0.c
@@ -930,8 +930,10 @@ static void iscsit_handle_connection_cleanup(struct iscsi_conn *conn)
930 } 930 }
931} 931}
932 932
933void iscsit_take_action_for_connection_exit(struct iscsi_conn *conn) 933void iscsit_take_action_for_connection_exit(struct iscsi_conn *conn, bool *conn_freed)
934{ 934{
935 *conn_freed = false;
936
935 spin_lock_bh(&conn->state_lock); 937 spin_lock_bh(&conn->state_lock);
936 if (atomic_read(&conn->connection_exit)) { 938 if (atomic_read(&conn->connection_exit)) {
937 spin_unlock_bh(&conn->state_lock); 939 spin_unlock_bh(&conn->state_lock);
@@ -942,6 +944,7 @@ void iscsit_take_action_for_connection_exit(struct iscsi_conn *conn)
942 if (conn->conn_state == TARG_CONN_STATE_IN_LOGOUT) { 944 if (conn->conn_state == TARG_CONN_STATE_IN_LOGOUT) {
943 spin_unlock_bh(&conn->state_lock); 945 spin_unlock_bh(&conn->state_lock);
944 iscsit_close_connection(conn); 946 iscsit_close_connection(conn);
947 *conn_freed = true;
945 return; 948 return;
946 } 949 }
947 950
@@ -955,4 +958,5 @@ void iscsit_take_action_for_connection_exit(struct iscsi_conn *conn)
955 spin_unlock_bh(&conn->state_lock); 958 spin_unlock_bh(&conn->state_lock);
956 959
957 iscsit_handle_connection_cleanup(conn); 960 iscsit_handle_connection_cleanup(conn);
961 *conn_freed = true;
958} 962}
diff --git a/drivers/target/iscsi/iscsi_target_erl0.h b/drivers/target/iscsi/iscsi_target_erl0.h
index 60e69e2af6ed..3822d9cd1230 100644
--- a/drivers/target/iscsi/iscsi_target_erl0.h
+++ b/drivers/target/iscsi/iscsi_target_erl0.h
@@ -15,6 +15,6 @@ extern int iscsit_stop_time2retain_timer(struct iscsi_session *);
15extern void iscsit_connection_reinstatement_rcfr(struct iscsi_conn *); 15extern void iscsit_connection_reinstatement_rcfr(struct iscsi_conn *);
16extern void iscsit_cause_connection_reinstatement(struct iscsi_conn *, int); 16extern void iscsit_cause_connection_reinstatement(struct iscsi_conn *, int);
17extern void iscsit_fall_back_to_erl0(struct iscsi_session *); 17extern void iscsit_fall_back_to_erl0(struct iscsi_session *);
18extern void iscsit_take_action_for_connection_exit(struct iscsi_conn *); 18extern void iscsit_take_action_for_connection_exit(struct iscsi_conn *, bool *);
19 19
20#endif /*** ISCSI_TARGET_ERL0_H ***/ 20#endif /*** ISCSI_TARGET_ERL0_H ***/
diff --git a/drivers/target/iscsi/iscsi_target_login.c b/drivers/target/iscsi/iscsi_target_login.c
index 66238477137b..92b96b51d506 100644
--- a/drivers/target/iscsi/iscsi_target_login.c
+++ b/drivers/target/iscsi/iscsi_target_login.c
@@ -1464,5 +1464,9 @@ int iscsi_target_login_thread(void *arg)
1464 break; 1464 break;
1465 } 1465 }
1466 1466
1467 while (!kthread_should_stop()) {
1468 msleep(100);
1469 }
1470
1467 return 0; 1471 return 0;
1468} 1472}