diff --git a/common.c b/common.c index b64c114..2660535 100644 --- a/common.c +++ b/common.c @@ -620,7 +620,7 @@ int inc_proto_connections(struct sslhcfg_protocols_item* proto) proto->num_connections, proto->max_connections); if (proto->num_connections > proto->max_connections) { - print_message(msg_connections_error, "%s: too many connections, dropping", proto->name); + print_message(msg_connections_error, "%s: too many connections, dropping\n", proto->name); return 1; } } diff --git a/processes.c b/processes.c index aa23c66..997fe92 100644 --- a/processes.c +++ b/processes.c @@ -50,7 +50,7 @@ int tidy_connection(struct connection *cnx, struct loop_info* fd_info) fd_info->num_probing--; dec_proto_connections(cnx->proto); - dec_listen_connections(cnx); + dec_listen_connections(cnx->endpoint); collection_remove_cnx(fd_info->collection, cnx); return 0; @@ -145,6 +145,8 @@ void sigchld_process(struct loop_info* loop) p2p.proto = NULL; struct pid2proto* found = hash_find(loop->pid2proto, &p2p); dec_proto_connections(found->proto); + dec_listen_connections(found->endpoint); + hash_remove(loop->pid2proto, found); free(found); } diff --git a/tcp-listener.c b/tcp-listener.c index 5fb100a..227e79d 100644 --- a/tcp-listener.c +++ b/tcp-listener.c @@ -127,30 +127,32 @@ void tcp_read_process(struct loop_info* fd_info, /* *cnx must have its endpoint field filled; * Increment the connection count for the listen endpoint. * Return 1 if connection count is exceeded, 0 otherwise */ -static int inc_listen_connections(struct connection* cnx) +static int inc_listen_connections(struct listen_endpoint* endpoint) { - cnx->endpoint->num_connections++; - if (cnx->endpoint->endpoint_cfg->max_connections_is_present) { - int num_cnx = cnx->endpoint->num_connections; - int max_cnx = cnx->endpoint->endpoint_cfg->max_connections; + endpoint->num_connections++; + if (endpoint->endpoint_cfg->max_connections_is_present) { + int num_cnx = endpoint->num_connections; + int max_cnx = endpoint->endpoint_cfg->max_connections; print_message(msg_connections, "Endpoint %d +1: %d/%d cnx\n", - cnx->endpoint->socketfd, num_cnx, max_cnx); + endpoint->socketfd, num_cnx, max_cnx); if (num_cnx > max_cnx) { - print_message(msg_connections_error, "Endpoint %d: too many connections, dropping\n", cnx->endpoint->socketfd); + print_message(msg_connections_error, "Endpoint %d: too many connections, dropping\n", endpoint->socketfd); return 1; } } return 0; } -void dec_listen_connections(struct connection* cnx) +void dec_listen_connections(struct listen_endpoint* endpoint) { - cnx->endpoint->num_connections--; - print_message(msg_connections, "Endpoint %d -1: %d/%d cnx\n", - cnx->endpoint->socketfd, - cnx->endpoint->num_connections, - cnx->endpoint->endpoint_cfg->max_connections); + if (endpoint) { + endpoint->num_connections--; + print_message(msg_connections, "Endpoint %d -1: %d/%d cnx\n", + endpoint->socketfd, + endpoint->num_connections, + endpoint->endpoint_cfg->max_connections); + } } @@ -179,7 +181,7 @@ struct connection* accept_new_connection(struct listen_endpoint* endpoint, struc return NULL; } cnx->endpoint = endpoint; - if (inc_listen_connections(cnx)) { + if (inc_listen_connections(endpoint)) { tidy_connection(cnx, fd_info); return NULL; } @@ -317,6 +319,7 @@ void fork_shoveling_process(struct loop_info* fd_info, struct connection* cnx) { } /* Free file descriptor, but do not reduce protocol count */ cnx->proto = NULL; + cnx->endpoint = NULL; tidy_connection(cnx, fd_info); } diff --git a/tcp-listener.h b/tcp-listener.h index d623b5d..e6f8e53 100644 --- a/tcp-listener.h +++ b/tcp-listener.h @@ -5,9 +5,11 @@ #include "collection.h" #include "tcp-probe.h" -/* Struct to keep track of an association of a forked PID to a protocol */ +/* Struct to keep track of an association of a forked PID to its + * listening socket and its protocol */ struct pid2proto { pid_t pid; + struct listen_endpoint* endpoint; struct sslhcfg_protocols_item* proto; }; @@ -16,5 +18,5 @@ struct connection* accept_new_connection(struct listen_endpoint* endpoint, struc void probing_read_process(struct connection* cnx, struct loop_info* fd_info); void cnx_write_process(struct loop_info* fd_info, int fd); -void dec_listen_connections(struct connection* cnx); +void dec_listen_connections(struct listen_endpoint*); #endif diff --git a/test.cfg b/test.cfg index 5978eac..464ae7c 100644 --- a/test.cfg +++ b/test.cfg @@ -43,7 +43,7 @@ listen: protocols: ( - { name: "ssh"; host: "localhost"; port: "9000"; fork: true; transparent: true; resolve_on_forward: true; max_connections: 2; }, + { name: "ssh"; host: "localhost"; port: "9000"; fork: true; transparent: true; resolve_on_forward: true; max_connections: 4; }, { name: "socks5"; host: "localhost"; port: "9001"; }, { name: "http"; host: "localhost"; port: "80"; proxyprotocol: 2; }, { name: "tinc"; host: "localhost"; port: "9003"; },