diff --git a/iscsi-scst/usr/iscsi_scstd.c b/iscsi-scst/usr/iscsi_scstd.c index 8bb0df9f0..0b57a56bc 100644 --- a/iscsi-scst/usr/iscsi_scstd.c +++ b/iscsi-scst/usr/iscsi_scstd.c @@ -578,6 +578,12 @@ static void event_loop(void) conn->sess->sid.id64, conn->cid); } else { + /* + * Check if session could not be established, + * but sessions count was already incremented + */ + if (!sess && conn->sessions_count_incremented) + conn->target->sessions_count--; conn_free(conn); log_debug(1, "conn %p freed (sess %p, empty %d)", conn, sess, diff --git a/iscsi-scst/usr/iscsid.c b/iscsi-scst/usr/iscsid.c index c9d993017..0aebb933b 100644 --- a/iscsi-scst/usr/iscsid.c +++ b/iscsi-scst/usr/iscsid.c @@ -525,6 +525,8 @@ static void login_start(struct connection *conn) return; } + conn->target = target; + /* We may "leak" here if we have an iSCSI event on the wrong time */ if (!iscsi_enabled) { log_info("Connect from %s to disabled iSCSI-SCST refused", @@ -580,13 +582,15 @@ static void login_start(struct connection *conn) rc = login_check_reinstatement(conn); if (rc < 0) return; - else if (rc == ISCSI_SESS_REINSTATEMENT) - target->sessions_count++; - else if (rc != ISCSI_CONN_REINSTATEMENT) { - if ((target->target_params[key_max_sessions] == 0) || - (target->sessions_count < target->target_params[key_max_sessions])) + else if (rc == ISCSI_SESS_REINSTATEMENT) { target->sessions_count++; - else { + conn->sessions_count_incremented = 1; + } else if (rc != ISCSI_CONN_REINSTATEMENT) { + if ((target->target_params[key_max_sessions] == 0) || + (target->sessions_count < target->target_params[key_max_sessions])) { + target->sessions_count++; + conn->sessions_count_incremented = 1; + } else { log_warning("Initiator %s not allowed to connect to " "target %s - max sessions limit " "reached (%d)", name, target_name, diff --git a/iscsi-scst/usr/iscsid.h b/iscsi-scst/usr/iscsid.h index eca1024ae..e93980e50 100644 --- a/iscsi-scst/usr/iscsid.h +++ b/iscsi-scst/usr/iscsid.h @@ -82,7 +82,9 @@ struct connection { int fd; unsigned int passed_to_kern:1; + unsigned int sessions_count_incremented:1; + struct target *target; struct session *sess; u32 tid;