Abort connect when IP fails to bind

This commit is contained in:
konsolebox 2024-04-16 15:28:39 +08:00
parent 24a44662cc
commit a29514f3dd
4 changed files with 51 additions and 11 deletions

View File

@ -24,6 +24,7 @@
#include <string.h>
#include <stdio.h>
#include <glib.h>
#include <errno.h>
#ifndef WIN32
#include <unistd.h>
@ -164,13 +165,25 @@ net_connect (netstore * ns, int sok4, int sok6, int *sok_return)
return error;
}
void
net_bind (netstore * tobindto, int sok4, int sok6)
int
net_bind (netstore *tobindto, int sok4, int sok6, const char **sok4_error, const char **sok6_error)
{
bind (sok4, tobindto->ip6_hostent->ai_addr,
tobindto->ip6_hostent->ai_addrlen);
bind (sok6, tobindto->ip6_hostent->ai_addr,
tobindto->ip6_hostent->ai_addrlen);
int r = 0;
*sok4_error = *sok6_error = NULL;
if (bind (sok4, tobindto->ip6_hostent->ai_addr, tobindto->ip6_hostent->ai_addrlen) != 0)
{
r |= 1;
*sok4_error = strerror (errno);
}
if (bind (sok6, tobindto->ip6_hostent->ai_addr, tobindto->ip6_hostent->ai_addrlen) != 0)
{
r |= 2;
*sok6_error = strerror (errno);
}
return r;
}
void

View File

@ -35,7 +35,7 @@ netstore *net_store_new (void);
void net_store_destroy (netstore *ns);
int net_connect (netstore *ns, int sok4, int sok6, int *sok_return);
char *net_resolve (netstore *ns, char *hostname, int port, char **real_host);
void net_bind (netstore *tobindto, int sok4, int sok6);
int net_bind (netstore *tobindto, int sok4, int sok6, const char **sok4_error, const char **sok6_error);
char *net_ip (guint32 addr);
void net_sockets (int *sok4, int *sok6);

View File

@ -802,6 +802,7 @@ server_read_child (GIOChannel *source, GIOCondition condition, server *serv)
{
session *sess = serv->server_session;
char tbuf[128];
char tbuf2[128];
char outbuf[512];
char host[100];
char ip[100];
@ -906,6 +907,7 @@ server_read_child (GIOChannel *source, GIOCondition condition, server *serv)
_("Cannot resolve hostname %s\nCheck your IP Settings!\n"),
prefs.hex_net_bind_host);
PrintText (sess, outbuf);
server_disconnect (sess, FALSE, -1);
break;
case 8:
PrintText (sess, _("Proxy traversal failed.\n"));
@ -915,6 +917,13 @@ server_read_child (GIOChannel *source, GIOCondition condition, server *serv)
waitline2 (source, tbuf, sizeof tbuf);
EMIT_SIGNAL (XP_TE_SERVERLOOKUP, sess, tbuf, NULL, NULL, NULL, 0);
break;
case 10: /* net_bind failed */
waitline2 (source, tbuf, sizeof tbuf);
waitline2 (source, tbuf2, sizeof tbuf2);
sprintf (outbuf, _("Failed to bind %s to socket: %s\n"), tbuf, tbuf2);
PrintText (sess, outbuf);
server_disconnect (sess, FALSE, -1);
break;
}
return TRUE;
@ -1389,13 +1398,31 @@ server_child (server * serv)
{
g_snprintf (buf, sizeof (buf), "5\n%s\n", local_ip);
write (serv->childwrite, buf, strlen (buf));
net_bind (ns_local, serv->sok4, serv->sok6);
bound = 1;
const char *sok4_error, *sok6_error;
int r = net_bind (ns_local, serv->sok4, serv->sok6, &sok4_error, &sok6_error);
if (r & 1 && r & 2)
{
/* attempt to bind failed on both ipv4 and ipv6 */
const char *format = (strncmp (sok4_error, sok6_error, 128) == 0) ? "10\n%s\n%s\n" :
"10\n%s\n%s; %s\n";
g_snprintf (buf, sizeof (buf), format, local_ip, sok4_error, sok6_error);
write (serv->childwrite, buf, strlen (buf));
} else
{
bound = 1;
/* close the socket that fails to bind to make sure it isn't used */
if (r == 1)
closesocket (serv->sok4);
else if (r == 2)
closesocket (serv->sok6);
}
} else
{
write (serv->childwrite, "7\n", 2);
}
net_store_destroy (ns_local);
if (! bound)
goto xit;
}
if (!serv->dont_use_proxy) /* blocked in serverlist? */

View File

@ -811,8 +811,8 @@ pevt_topicdate_help
Unknown Host
XP_TE_UKNHOST
pevt_generic_none_help
%C20*%O$tUnknown host. Maybe you misspelled it?
0
%C20*%O$tUnknown host '%C22$1%C'. Maybe you misspelled it?
1
User Limit
XP_TE_USERLIMIT