mirror of
https://github.com/weechat/weechat.git
synced 2026-07-07 18:23:13 +02:00
relay: fix the max number of clients connected on a port, allow value 0 for "no limit" (closes #669)
This commit is contained in:
@@ -161,6 +161,31 @@ relay_client_status_search (const char *name)
|
||||
return -1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns the number of active clients (connecting or connected) on a given
|
||||
* server port.
|
||||
*/
|
||||
|
||||
int
|
||||
relay_client_count_active_by_port (int server_port)
|
||||
{
|
||||
struct t_relay_client *ptr_client;
|
||||
int count;
|
||||
|
||||
count = 0;
|
||||
for (ptr_client = relay_clients; ptr_client;
|
||||
ptr_client = ptr_client->next_client)
|
||||
{
|
||||
if ((ptr_client->server_port == server_port)
|
||||
&& !RELAY_CLIENT_HAS_ENDED(ptr_client))
|
||||
{
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
/*
|
||||
* Sends a signal with the status of client ("relay_client_xxx").
|
||||
*/
|
||||
@@ -1163,6 +1188,7 @@ relay_client_new (int sock, const char *address, struct t_relay_server *server)
|
||||
new_client->id = (relay_clients) ? relay_clients->id + 1 : 1;
|
||||
new_client->desc = NULL;
|
||||
new_client->sock = sock;
|
||||
new_client->server_port = server->port;
|
||||
new_client->ssl = server->ssl;
|
||||
#ifdef HAVE_GNUTLS
|
||||
new_client->hook_timer_handshake = NULL;
|
||||
@@ -1330,6 +1356,7 @@ relay_client_new_with_infolist (struct t_infolist *infolist)
|
||||
new_client->id = weechat_infolist_integer (infolist, "id");
|
||||
new_client->desc = NULL;
|
||||
new_client->sock = weechat_infolist_integer (infolist, "sock");
|
||||
new_client->server_port = weechat_infolist_integer (infolist, "server_port");
|
||||
new_client->ssl = weechat_infolist_integer (infolist, "ssl");
|
||||
#ifdef HAVE_GNUTLS
|
||||
new_client->gnutls_sess = NULL;
|
||||
@@ -1636,6 +1663,8 @@ relay_client_add_to_infolist (struct t_infolist *infolist,
|
||||
return 0;
|
||||
if (!weechat_infolist_new_var_integer (ptr_item, "sock", client->sock))
|
||||
return 0;
|
||||
if (!weechat_infolist_new_var_integer (ptr_item, "server_port", client->server_port))
|
||||
return 0;
|
||||
if (!weechat_infolist_new_var_integer (ptr_item, "ssl", client->ssl))
|
||||
return 0;
|
||||
#ifdef HAVE_GNUTLS
|
||||
@@ -1715,6 +1744,7 @@ relay_client_print_log ()
|
||||
weechat_log_printf (" id. . . . . . . . . . : %d", ptr_client->id);
|
||||
weechat_log_printf (" desc. . . . . . . . . : '%s'", ptr_client->desc);
|
||||
weechat_log_printf (" sock. . . . . . . . . : %d", ptr_client->sock);
|
||||
weechat_log_printf (" server_port . . . . . : %d", ptr_client->server_port);
|
||||
weechat_log_printf (" ssl . . . . . . . . . : %d", ptr_client->ssl);
|
||||
#ifdef HAVE_GNUTLS
|
||||
weechat_log_printf (" gnutls_sess . . . . . : 0x%lx", ptr_client->gnutls_sess);
|
||||
|
||||
@@ -87,6 +87,7 @@ struct t_relay_client
|
||||
int id; /* unique id (diff. for each client) */
|
||||
char *desc; /* description, used for display */
|
||||
int sock; /* socket for connection */
|
||||
int server_port; /* port used for connection */
|
||||
int ssl; /* 1 if SSL is enabled */
|
||||
#ifdef HAVE_GNUTLS
|
||||
gnutls_session_t gnutls_sess; /* gnutls session (only if SSL used) */
|
||||
@@ -128,6 +129,7 @@ extern int relay_client_valid (struct t_relay_client *client);
|
||||
extern struct t_relay_client *relay_client_search_by_number (int number);
|
||||
extern struct t_relay_client *relay_client_search_by_id (int id);
|
||||
extern int relay_client_status_search (const char *name);
|
||||
extern int relay_client_count_active_by_port (int server_port);
|
||||
extern void relay_client_set_desc (struct t_relay_client *client);
|
||||
extern int relay_client_recv_cb (void *arg_client, int fd);
|
||||
extern int relay_client_send (struct t_relay_client *client,
|
||||
|
||||
@@ -748,8 +748,8 @@ relay_config_init ()
|
||||
relay_config_network_max_clients = weechat_config_new_option (
|
||||
relay_config_file, ptr_section,
|
||||
"max_clients", "integer",
|
||||
N_("maximum number of clients connecting to a port"),
|
||||
NULL, 1, 1024, "5", NULL, 0,
|
||||
N_("maximum number of clients connecting to a port (0 = no limit)"),
|
||||
NULL, 0, INT_MAX, "5", NULL, 0,
|
||||
NULL, NULL, NULL, NULL, NULL, NULL);
|
||||
relay_config_network_password = weechat_config_new_option (
|
||||
relay_config_file, ptr_section,
|
||||
|
||||
@@ -226,7 +226,7 @@ relay_server_sock_cb (void *data, int fd)
|
||||
struct sockaddr_in6 client_addr6;
|
||||
socklen_t client_addr_size;
|
||||
void *ptr_addr;
|
||||
int client_fd, flags, set;
|
||||
int client_fd, flags, set, max_clients, num_clients_on_port;
|
||||
char ipv4_address[INET_ADDRSTRLEN + 1], ipv6_address[INET6_ADDRSTRLEN + 1];
|
||||
char *ptr_ip_address;
|
||||
|
||||
@@ -260,6 +260,28 @@ relay_server_sock_cb (void *data, int fd)
|
||||
return WEECHAT_RC_OK;
|
||||
}
|
||||
|
||||
/* check if we have reached the max number of clients on this port */
|
||||
max_clients = weechat_config_integer (relay_config_network_max_clients);
|
||||
if (max_clients > 0)
|
||||
{
|
||||
num_clients_on_port = relay_client_count_active_by_port (server->port);
|
||||
if (num_clients_on_port >= max_clients)
|
||||
{
|
||||
weechat_printf (
|
||||
NULL,
|
||||
NG_("%s%s: client not allowed (max %d client is "
|
||||
"allowed at same time)",
|
||||
"%s%s: client not allowed (max %d clients are "
|
||||
"allowed at same time)",
|
||||
max_clients),
|
||||
weechat_prefix ("error"), RELAY_PLUGIN_NAME,
|
||||
max_clients);
|
||||
close (client_fd);
|
||||
return WEECHAT_RC_OK;
|
||||
}
|
||||
}
|
||||
|
||||
/* get the IP address */
|
||||
ptr_ip_address = NULL;
|
||||
if (server->ipv6)
|
||||
{
|
||||
@@ -474,9 +496,11 @@ relay_server_create_socket (struct t_relay_server *server)
|
||||
return 0;
|
||||
}
|
||||
|
||||
max_clients = weechat_config_integer (relay_config_network_max_clients);
|
||||
|
||||
if (listen (server->sock, max_clients) != 0)
|
||||
#ifdef SOMAXCONN
|
||||
if (listen (server->sock, SOMAXCONN) != 0)
|
||||
#else
|
||||
if (listen (server->sock, 1) != 0)
|
||||
#endif
|
||||
{
|
||||
weechat_printf (NULL,
|
||||
_("%s%s: cannot \"listen\" on port %d (%s): error %d %s"),
|
||||
@@ -488,14 +512,30 @@ relay_server_create_socket (struct t_relay_server *server)
|
||||
return 0;
|
||||
}
|
||||
|
||||
weechat_printf (NULL,
|
||||
_("%s: listening on port %d (relay: %s, %s, max %d clients)"),
|
||||
RELAY_PLUGIN_NAME,
|
||||
server->port,
|
||||
server->protocol_string,
|
||||
((server->ipv4 && server->ipv6) ? "IPv4+6" : ((server->ipv6) ? "IPv6" : "IPv4")),
|
||||
max_clients);
|
||||
|
||||
max_clients = weechat_config_integer (relay_config_network_max_clients);
|
||||
if (max_clients > 0)
|
||||
{
|
||||
weechat_printf (
|
||||
NULL,
|
||||
NG_("%s: listening on port %d (relay: %s, %s, max %d client)",
|
||||
"%s: listening on port %d (relay: %s, %s, max %d clients)",
|
||||
max_clients),
|
||||
RELAY_PLUGIN_NAME,
|
||||
server->port,
|
||||
server->protocol_string,
|
||||
((server->ipv4 && server->ipv6) ? "IPv4+6" : ((server->ipv6) ? "IPv6" : "IPv4")),
|
||||
max_clients);
|
||||
}
|
||||
else
|
||||
{
|
||||
weechat_printf (
|
||||
NULL,
|
||||
_("%s: listening on port %d (relay: %s, %s)"),
|
||||
RELAY_PLUGIN_NAME,
|
||||
server->port,
|
||||
server->protocol_string,
|
||||
((server->ipv4 && server->ipv6) ? "IPv4+6" : ((server->ipv6) ? "IPv6" : "IPv4")));
|
||||
}
|
||||
server->hook_fd = weechat_hook_fd (server->sock,
|
||||
1, 0, 0,
|
||||
&relay_server_sock_cb,
|
||||
|
||||
Reference in New Issue
Block a user