diff options
Diffstat (limited to 'kernel/drivers/target/iscsi')
-rw-r--r-- | kernel/drivers/target/iscsi/iscsi_target.c | 22 | ||||
-rw-r--r-- | kernel/drivers/target/iscsi/iscsi_target_login.c | 5 | ||||
-rw-r--r-- | kernel/drivers/target/iscsi/iscsi_target_tpg.c | 1 |
3 files changed, 19 insertions, 9 deletions
diff --git a/kernel/drivers/target/iscsi/iscsi_target.c b/kernel/drivers/target/iscsi/iscsi_target.c index 72204fbf2..bd810c109 100644 --- a/kernel/drivers/target/iscsi/iscsi_target.c +++ b/kernel/drivers/target/iscsi/iscsi_target.c @@ -492,7 +492,8 @@ static void iscsit_aborted_task(struct iscsi_conn *conn, struct iscsi_cmd *cmd) bool scsi_cmd = (cmd->iscsi_opcode == ISCSI_OP_SCSI_CMD); spin_lock_bh(&conn->cmd_lock); - if (!list_empty(&cmd->i_conn_node)) + if (!list_empty(&cmd->i_conn_node) && + !(cmd->se_cmd.transport_state & CMD_T_FABRIC_STOP)) list_del_init(&cmd->i_conn_node); spin_unlock_bh(&conn->cmd_lock); @@ -4194,6 +4195,7 @@ transport_err: static void iscsit_release_commands_from_conn(struct iscsi_conn *conn) { + LIST_HEAD(tmp_list); struct iscsi_cmd *cmd = NULL, *cmd_tmp = NULL; struct iscsi_session *sess = conn->sess; /* @@ -4202,18 +4204,26 @@ static void iscsit_release_commands_from_conn(struct iscsi_conn *conn) * has been reset -> returned sleeping pre-handler state. */ spin_lock_bh(&conn->cmd_lock); - list_for_each_entry_safe(cmd, cmd_tmp, &conn->conn_cmd_list, i_conn_node) { + list_splice_init(&conn->conn_cmd_list, &tmp_list); + list_for_each_entry(cmd, &tmp_list, i_conn_node) { + struct se_cmd *se_cmd = &cmd->se_cmd; + + if (se_cmd->se_tfo != NULL) { + spin_lock(&se_cmd->t_state_lock); + se_cmd->transport_state |= CMD_T_FABRIC_STOP; + spin_unlock(&se_cmd->t_state_lock); + } + } + spin_unlock_bh(&conn->cmd_lock); + + list_for_each_entry_safe(cmd, cmd_tmp, &tmp_list, i_conn_node) { list_del_init(&cmd->i_conn_node); - spin_unlock_bh(&conn->cmd_lock); iscsit_increment_maxcmdsn(cmd, sess); - iscsit_free_cmd(cmd, true); - spin_lock_bh(&conn->cmd_lock); } - spin_unlock_bh(&conn->cmd_lock); } static void iscsit_stop_timers_for_cmds( diff --git a/kernel/drivers/target/iscsi/iscsi_target_login.c b/kernel/drivers/target/iscsi/iscsi_target_login.c index 96e78c823..316f66172 100644 --- a/kernel/drivers/target/iscsi/iscsi_target_login.c +++ b/kernel/drivers/target/iscsi/iscsi_target_login.c @@ -1357,8 +1357,9 @@ static int __iscsi_target_login_thread(struct iscsi_np *np) } login->zero_tsih = zero_tsih; - conn->sess->se_sess->sup_prot_ops = - conn->conn_transport->iscsit_get_sup_prot_ops(conn); + if (conn->sess) + conn->sess->se_sess->sup_prot_ops = + conn->conn_transport->iscsit_get_sup_prot_ops(conn); tpg = conn->tpg; if (!tpg) { diff --git a/kernel/drivers/target/iscsi/iscsi_target_tpg.c b/kernel/drivers/target/iscsi/iscsi_target_tpg.c index 23c95cd14..68261b7dc 100644 --- a/kernel/drivers/target/iscsi/iscsi_target_tpg.c +++ b/kernel/drivers/target/iscsi/iscsi_target_tpg.c @@ -260,7 +260,6 @@ err_out: iscsi_release_param_list(tpg->param_list); tpg->param_list = NULL; } - kfree(tpg); return -ENOMEM; } |