mirror of
https://github.com/irssi/irssi.git
synced 2024-09-01 04:14:16 -04:00
Initial work to make irssi respect the resolved ip order
Ip's aren't selected using random() anymore, also select the ip version by using getaddrinfo and some proper hints.
This commit is contained in:
parent
0912a11050
commit
ffaa890e99
@ -128,10 +128,10 @@ static SERVER_CONNECT_REC *get_server_connect(const char *data, int *plus_addr,
|
||||
|
||||
host = g_hash_table_lookup(optlist, "host");
|
||||
if (host != NULL && *host != '\0') {
|
||||
IPADDR ip4, ip6;
|
||||
IPADDR ip;
|
||||
|
||||
if (net_gethostbyname(host, &ip4, &ip6) == 0)
|
||||
server_connect_own_ip_save(conn, &ip4, &ip6);
|
||||
if (net_gethostbyname(host, &ip) == 0)
|
||||
server_connect_own_ip_save(conn, &ip);
|
||||
}
|
||||
|
||||
cmd_params_free(free_arg);
|
||||
|
@ -9,4 +9,4 @@ char *realname;
|
||||
|
||||
char *own_host; /* address to use when connecting this server */
|
||||
char *autosendcmd; /* command to send after connecting to this ircnet */
|
||||
IPADDR *own_ip4, *own_ip6; /* resolved own_address if not NULL */
|
||||
IPADDR *own_ip; /* resolved own_address if not NULL */
|
||||
|
@ -103,15 +103,12 @@ int net_gethostbyname_nonblock(const char *addr, GIOChannel *pipe,
|
||||
srand(time(NULL));
|
||||
|
||||
memset(&rec, 0, sizeof(rec));
|
||||
rec.error = net_gethostbyname(addr, &rec.ip4, &rec.ip6);
|
||||
rec.error = net_gethostbyname(addr, &rec.ip);
|
||||
if (rec.error == 0) {
|
||||
errorstr = NULL;
|
||||
if (reverse_lookup) {
|
||||
/* reverse lookup the IP, ignore any error */
|
||||
if (rec.ip4.family != 0)
|
||||
net_gethostbyaddr(&rec.ip4, &rec.host4);
|
||||
if (rec.ip6.family != 0)
|
||||
net_gethostbyaddr(&rec.ip6, &rec.host6);
|
||||
net_gethostbyaddr(&rec.ip, &rec.host);
|
||||
}
|
||||
} else {
|
||||
errorstr = net_gethosterror(rec.error);
|
||||
@ -122,18 +119,11 @@ int net_gethostbyname_nonblock(const char *addr, GIOChannel *pipe,
|
||||
if (rec.errlen != 0)
|
||||
g_io_channel_write_block(pipe, (void *) errorstr, rec.errlen);
|
||||
else {
|
||||
if (rec.host4) {
|
||||
len = strlen(rec.host4) + 1;
|
||||
if (rec.host) {
|
||||
len = strlen(rec.host) + 1;
|
||||
g_io_channel_write_block(pipe, (void *) &len,
|
||||
sizeof(int));
|
||||
g_io_channel_write_block(pipe, (void *) rec.host4,
|
||||
len);
|
||||
}
|
||||
if (rec.host6) {
|
||||
len = strlen(rec.host6) + 1;
|
||||
g_io_channel_write_block(pipe, (void *) &len,
|
||||
sizeof(int));
|
||||
g_io_channel_write_block(pipe, (void *) rec.host6,
|
||||
g_io_channel_write_block(pipe, (void *) rec.host,
|
||||
len);
|
||||
}
|
||||
}
|
||||
@ -154,8 +144,7 @@ int net_gethostbyname_return(GIOChannel *pipe, RESOLVED_IP_REC *rec)
|
||||
|
||||
rec->error = -1;
|
||||
rec->errorstr = NULL;
|
||||
rec->host4 = NULL;
|
||||
rec->host6 = NULL;
|
||||
rec->host = NULL;
|
||||
|
||||
#ifndef WIN32
|
||||
fcntl(g_io_channel_unix_get_fd(pipe), F_SETFL, O_NONBLOCK);
|
||||
@ -174,15 +163,10 @@ int net_gethostbyname_return(GIOChannel *pipe, RESOLVED_IP_REC *rec)
|
||||
rec->errorstr = g_malloc0(rec->errlen+1);
|
||||
g_io_channel_read_block(pipe, rec->errorstr, rec->errlen);
|
||||
} else {
|
||||
if (rec->host4) {
|
||||
if (rec->host) {
|
||||
g_io_channel_read_block(pipe, &len, sizeof(int));
|
||||
rec->host4 = g_malloc0(len);
|
||||
g_io_channel_read_block(pipe, rec->host4, len);
|
||||
}
|
||||
if (rec->host6) {
|
||||
g_io_channel_read_block(pipe, &len, sizeof(int));
|
||||
rec->host6 = g_malloc0(len);
|
||||
g_io_channel_read_block(pipe, rec->host6, len);
|
||||
rec->host = g_malloc0(len);
|
||||
g_io_channel_read_block(pipe, rec->host, len);
|
||||
}
|
||||
}
|
||||
|
||||
@ -227,7 +211,6 @@ static void simple_readpipe(SIMPLE_THREAD_REC *rec, GIOChannel *pipe)
|
||||
{
|
||||
RESOLVED_IP_REC iprec;
|
||||
GIOChannel *handle;
|
||||
IPADDR *ip;
|
||||
|
||||
g_return_if_fail(rec != NULL);
|
||||
|
||||
@ -241,9 +224,8 @@ static void simple_readpipe(SIMPLE_THREAD_REC *rec, GIOChannel *pipe)
|
||||
g_io_channel_shutdown(rec->pipes[1], TRUE, NULL);
|
||||
g_io_channel_unref(rec->pipes[1]);
|
||||
|
||||
ip = iprec.ip4.family != 0 ? &iprec.ip4 : &iprec.ip6;
|
||||
handle = iprec.error == -1 ? NULL :
|
||||
net_connect_ip(ip, rec->port, rec->my_ip);
|
||||
net_connect_ip(&iprec.ip, rec->port, rec->my_ip);
|
||||
|
||||
g_free_not_null(rec->my_ip);
|
||||
|
||||
|
@ -4,12 +4,12 @@
|
||||
#include "network.h"
|
||||
|
||||
typedef struct {
|
||||
IPADDR ip4, ip6; /* resolved ip addresses */
|
||||
IPADDR ip; /* resolved ip address */
|
||||
int error; /* error, 0 = no error, -1 = error: */
|
||||
int errlen; /* error text length */
|
||||
char *errorstr; /* error string - dynamically allocated, you'll
|
||||
need to free() it yourself unless it's NULL */
|
||||
char *host4, *host6; /* dito */
|
||||
char *host; /* dito */
|
||||
} RESOLVED_IP_REC;
|
||||
|
||||
typedef struct {
|
||||
|
@ -137,35 +137,14 @@ static int sin_get_port(union sockaddr_union *so)
|
||||
/* Connect to socket */
|
||||
GIOChannel *net_connect(const char *addr, int port, IPADDR *my_ip)
|
||||
{
|
||||
IPADDR ip4, ip6, *ip;
|
||||
IPADDR ip;
|
||||
|
||||
g_return_val_if_fail(addr != NULL, NULL);
|
||||
|
||||
if (net_gethostbyname(addr, &ip4, &ip6) == -1)
|
||||
if (net_gethostbyname(addr, &ip) == -1)
|
||||
return NULL;
|
||||
|
||||
if (my_ip == NULL) {
|
||||
/* prefer IPv4 addresses */
|
||||
ip = ip4.family != 0 ? &ip4 : &ip6;
|
||||
} else if (IPADDR_IS_V6(my_ip)) {
|
||||
/* my_ip is IPv6 address, use it if possible */
|
||||
if (ip6.family != 0)
|
||||
ip = &ip6;
|
||||
else {
|
||||
my_ip = NULL;
|
||||
ip = &ip4;
|
||||
}
|
||||
} else {
|
||||
/* my_ip is IPv4 address, use it if possible */
|
||||
if (ip4.family != 0)
|
||||
ip = &ip4;
|
||||
else {
|
||||
my_ip = NULL;
|
||||
ip = &ip6;
|
||||
}
|
||||
}
|
||||
|
||||
return net_connect_ip(ip, port, my_ip);
|
||||
return net_connect_ip(&ip, port, my_ip);
|
||||
}
|
||||
|
||||
/* Connect to socket with ip address */
|
||||
@ -413,82 +392,35 @@ int net_getsockname(GIOChannel *handle, IPADDR *addr, int *port)
|
||||
/* Get IP addresses for host, both IPv4 and IPv6 if possible.
|
||||
If ip->family is 0, the address wasn't found.
|
||||
Returns 0 = ok, others = error code for net_gethosterror() */
|
||||
int net_gethostbyname(const char *addr, IPADDR *ip4, IPADDR *ip6)
|
||||
int net_gethostbyname(const char *addr, IPADDR *ip)
|
||||
{
|
||||
#ifdef HAVE_IPV6
|
||||
union sockaddr_union *so;
|
||||
struct addrinfo hints, *ai, *ailist;
|
||||
int ret, count_v4, count_v6, use_v4, use_v6;
|
||||
#else
|
||||
struct hostent *hp;
|
||||
int count;
|
||||
#endif
|
||||
struct addrinfo hints, *ailist;
|
||||
int ret;
|
||||
|
||||
g_return_val_if_fail(addr != NULL, -1);
|
||||
|
||||
memset(ip4, 0, sizeof(IPADDR));
|
||||
memset(ip6, 0, sizeof(IPADDR));
|
||||
memset(ip, 0, sizeof(IPADDR));
|
||||
|
||||
#ifdef HAVE_IPV6
|
||||
memset(&hints, 0, sizeof(struct addrinfo));
|
||||
hints.ai_socktype = SOCK_STREAM;
|
||||
#ifdef HAVE_IPV6
|
||||
hints.ai_family = AF_UNSPEC;
|
||||
#else
|
||||
hints.ai_family = AF_INET;
|
||||
#endif
|
||||
hints.ai_flags = (AI_V4MAPPED | AI_ADDRCONFIG);
|
||||
|
||||
/* save error to host_error for later use */
|
||||
ret = getaddrinfo(addr, NULL, &hints, &ailist);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
|
||||
/* count IPs */
|
||||
count_v4 = count_v6 = 0;
|
||||
for (ai = ailist; ai != NULL; ai = ai->ai_next) {
|
||||
if (ai->ai_family == AF_INET)
|
||||
count_v4++;
|
||||
else if (ai->ai_family == AF_INET6)
|
||||
count_v6++;
|
||||
}
|
||||
|
||||
if (count_v4 == 0 && count_v6 == 0)
|
||||
return HOST_NOT_FOUND; /* shouldn't happen? */
|
||||
|
||||
/* if there are multiple addresses, return random one */
|
||||
use_v4 = count_v4 <= 1 ? 0 : rand() % count_v4;
|
||||
use_v6 = count_v6 <= 1 ? 0 : rand() % count_v6;
|
||||
|
||||
count_v4 = count_v6 = 0;
|
||||
for (ai = ailist; ai != NULL; ai = ai->ai_next) {
|
||||
so = (union sockaddr_union *) ai->ai_addr;
|
||||
|
||||
if (ai->ai_family == AF_INET) {
|
||||
if (use_v4 == count_v4)
|
||||
sin_get_ip(so, ip4);
|
||||
count_v4++;
|
||||
} else if (ai->ai_family == AF_INET6) {
|
||||
if (use_v6 == count_v6)
|
||||
sin_get_ip(so, ip6);
|
||||
count_v6++;
|
||||
}
|
||||
}
|
||||
so = (const union sockaddr_union *)ailist->ai_addr;
|
||||
sin_get_ip(so, ip);
|
||||
freeaddrinfo(ailist);
|
||||
return 0;
|
||||
#else
|
||||
hp = gethostbyname(addr);
|
||||
if (hp == NULL)
|
||||
return h_errno;
|
||||
|
||||
/* count IPs */
|
||||
count = 0;
|
||||
while (hp->h_addr_list[count] != NULL)
|
||||
count++;
|
||||
|
||||
if (count == 0)
|
||||
return HOST_NOT_FOUND; /* shouldn't happen? */
|
||||
|
||||
/* if there are multiple addresses, return random one */
|
||||
ip4->family = AF_INET;
|
||||
memcpy(&ip4->ip, hp->h_addr_list[rand() % count], 4);
|
||||
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
/* Get name for host, *name should be g_free()'d unless it's NULL.
|
||||
|
@ -71,7 +71,7 @@ int net_transmit(GIOChannel *handle, const char *data, int len);
|
||||
/* Get IP addresses for host, both IPv4 and IPv6 if possible.
|
||||
If ip->family is 0, the address wasn't found.
|
||||
Returns 0 = ok, others = error code for net_gethosterror() */
|
||||
int net_gethostbyname(const char *addr, IPADDR *ip4, IPADDR *ip6);
|
||||
int net_gethostbyname(const char *addr, IPADDR *ip);
|
||||
/* Get name for host, *name should be g_free()'d unless it's NULL.
|
||||
Return values are the same as with net_gethostbyname() */
|
||||
int net_gethostbyaddr(IPADDR *ip, char **name);
|
||||
|
@ -16,7 +16,7 @@ char *address;
|
||||
int port;
|
||||
char *chatnet;
|
||||
|
||||
IPADDR *own_ip4, *own_ip6;
|
||||
IPADDR *own_ip;
|
||||
|
||||
char *password;
|
||||
char *nick;
|
||||
|
@ -19,7 +19,7 @@ char *ssl_capath;
|
||||
char *ssl_ciphers;
|
||||
|
||||
char *own_host; /* address to use when connecting this server */
|
||||
IPADDR *own_ip4, *own_ip6; /* resolved own_address if not NULL */
|
||||
IPADDR *own_ip; /* resolved own_address if not NULL */
|
||||
|
||||
time_t last_connect; /* to avoid reconnecting too fast.. */
|
||||
|
||||
|
@ -177,13 +177,9 @@ server_connect_copy_skeleton(SERVER_CONNECT_REC *src, int connect_info)
|
||||
dest->username = g_strdup(src->username);
|
||||
dest->realname = g_strdup(src->realname);
|
||||
|
||||
if (src->own_ip4 != NULL) {
|
||||
dest->own_ip4 = g_new(IPADDR, 1);
|
||||
memcpy(dest->own_ip4, src->own_ip4, sizeof(IPADDR));
|
||||
}
|
||||
if (src->own_ip6 != NULL) {
|
||||
dest->own_ip6 = g_new(IPADDR, 1);
|
||||
memcpy(dest->own_ip6, src->own_ip6, sizeof(IPADDR));
|
||||
if (src->own_ip != NULL) {
|
||||
dest->own_ip = g_new(IPADDR, 1);
|
||||
memcpy(dest->own_ip, src->own_ip, sizeof(IPADDR));
|
||||
}
|
||||
|
||||
dest->channels = g_strdup(src->channels);
|
||||
|
@ -33,32 +33,22 @@ GSList *setupservers;
|
||||
|
||||
static char *old_source_host;
|
||||
int source_host_ok; /* Use source_host_ip .. */
|
||||
IPADDR *source_host_ip4, *source_host_ip6; /* Resolved address */
|
||||
IPADDR source_host_ip; /* Resolved address */
|
||||
|
||||
static void save_ips(IPADDR *ip4, IPADDR *ip6,
|
||||
IPADDR **save_ip4, IPADDR **save_ip6)
|
||||
static void save_ips(IPADDR *ip, IPADDR **save_ip)
|
||||
{
|
||||
if (ip4->family == 0)
|
||||
g_free_and_null(*save_ip4);
|
||||
if (ip->family == 0)
|
||||
g_free_and_null(*save_ip);
|
||||
else {
|
||||
if (*save_ip4 == NULL)
|
||||
*save_ip4 = g_new(IPADDR, 1);
|
||||
memcpy(*save_ip4, ip4, sizeof(IPADDR));
|
||||
}
|
||||
|
||||
if (ip6->family == 0)
|
||||
g_free_and_null(*save_ip6);
|
||||
else {
|
||||
if (*save_ip6 == NULL)
|
||||
*save_ip6 = g_new(IPADDR, 1);
|
||||
memcpy(*save_ip6, ip6, sizeof(IPADDR));
|
||||
if (*save_ip == NULL)
|
||||
*save_ip = g_new(IPADDR, 1);
|
||||
memcpy(*save_ip, ip, sizeof(IPADDR));
|
||||
}
|
||||
}
|
||||
|
||||
static void get_source_host_ip(void)
|
||||
{
|
||||
const char *hostname;
|
||||
IPADDR ip4, ip6;
|
||||
|
||||
if (source_host_ok)
|
||||
return;
|
||||
@ -66,28 +56,21 @@ static void get_source_host_ip(void)
|
||||
/* FIXME: This will block! */
|
||||
hostname = settings_get_str("hostname");
|
||||
source_host_ok = *hostname != '\0' &&
|
||||
net_gethostbyname(hostname, &ip4, &ip6) == 0;
|
||||
|
||||
if (source_host_ok)
|
||||
save_ips(&ip4, &ip6, &source_host_ip4, &source_host_ip6);
|
||||
else {
|
||||
g_free_and_null(source_host_ip4);
|
||||
g_free_and_null(source_host_ip6);
|
||||
}
|
||||
net_gethostbyname(hostname, &source_host_ip) == 0;
|
||||
}
|
||||
|
||||
static void conn_set_ip(SERVER_CONNECT_REC *conn, const char *own_host,
|
||||
IPADDR **own_ip4, IPADDR **own_ip6)
|
||||
IPADDR **own_ip)
|
||||
{
|
||||
IPADDR ip4, ip6;
|
||||
IPADDR ip;
|
||||
|
||||
if (*own_ip4 == NULL && *own_ip6 == NULL) {
|
||||
if (*own_ip == NULL) {
|
||||
/* resolve the IP */
|
||||
if (net_gethostbyname(own_host, &ip4, &ip6) == 0)
|
||||
save_ips(&ip4, &ip6, own_ip4, own_ip6);
|
||||
if (net_gethostbyname(own_host, &ip) == 0)
|
||||
save_ips(&ip, own_ip);
|
||||
}
|
||||
|
||||
server_connect_own_ip_save(conn, *own_ip4, *own_ip6);
|
||||
server_connect_own_ip_save(conn, *own_ip);
|
||||
}
|
||||
|
||||
/* Fill information to connection from server setup record */
|
||||
@ -98,8 +81,7 @@ void server_setup_fill_reconn(SERVER_CONNECT_REC *conn,
|
||||
g_return_if_fail(IS_SERVER_SETUP(sserver));
|
||||
|
||||
if (sserver->own_host != NULL) {
|
||||
conn_set_ip(conn, sserver->own_host,
|
||||
&sserver->own_ip4, &sserver->own_ip6);
|
||||
conn_set_ip(conn, sserver->own_host, &sserver->own_ip);
|
||||
}
|
||||
|
||||
if (sserver->chatnet != NULL && conn->chatnet == NULL)
|
||||
@ -139,13 +121,9 @@ static void server_setup_fill(SERVER_CONNECT_REC *conn,
|
||||
}
|
||||
|
||||
/* source IP */
|
||||
if (source_host_ip4 != NULL) {
|
||||
conn->own_ip4 = g_new(IPADDR, 1);
|
||||
memcpy(conn->own_ip4, source_host_ip4, sizeof(IPADDR));
|
||||
}
|
||||
if (source_host_ip6 != NULL) {
|
||||
conn->own_ip6 = g_new(IPADDR, 1);
|
||||
memcpy(conn->own_ip6, source_host_ip6, sizeof(IPADDR));
|
||||
if (source_host_ok) {
|
||||
conn->own_ip = g_new(IPADDR, 1);
|
||||
memcpy(conn->own_ip, &source_host_ip, sizeof(IPADDR));
|
||||
}
|
||||
|
||||
signal_emit("server setup fill connect", 1, conn);
|
||||
@ -206,8 +184,7 @@ static void server_setup_fill_chatnet(SERVER_CONNECT_REC *conn,
|
||||
conn->realname = g_strdup(chatnet->realname);;
|
||||
}
|
||||
if (chatnet->own_host != NULL) {
|
||||
conn_set_ip(conn, chatnet->own_host,
|
||||
&chatnet->own_ip4, &chatnet->own_ip6);
|
||||
conn_set_ip(conn, chatnet->own_host, &chatnet->own_ip);
|
||||
}
|
||||
|
||||
signal_emit("server setup fill chatnet", 2, conn, chatnet);
|
||||
@ -481,8 +458,7 @@ static void server_setup_destroy(SERVER_SETUP_REC *rec)
|
||||
signal_emit("server setup destroyed", 1, rec);
|
||||
|
||||
g_free_not_null(rec->own_host);
|
||||
g_free_not_null(rec->own_ip4);
|
||||
g_free_not_null(rec->own_ip6);
|
||||
g_free_not_null(rec->own_ip);
|
||||
g_free_not_null(rec->chatnet);
|
||||
g_free_not_null(rec->password);
|
||||
g_free_not_null(rec->ssl_cert);
|
||||
@ -556,7 +532,6 @@ void servers_setup_init(void)
|
||||
settings_add_str("proxy", "proxy_password", "");
|
||||
|
||||
setupservers = NULL;
|
||||
source_host_ip4 = source_host_ip6 = NULL;
|
||||
old_source_host = NULL;
|
||||
read_settings();
|
||||
|
||||
@ -567,8 +542,6 @@ void servers_setup_init(void)
|
||||
|
||||
void servers_setup_deinit(void)
|
||||
{
|
||||
g_free_not_null(source_host_ip4);
|
||||
g_free_not_null(source_host_ip6);
|
||||
g_free_not_null(old_source_host);
|
||||
|
||||
while (setupservers != NULL)
|
||||
|
@ -16,7 +16,7 @@ struct _SERVER_SETUP_REC {
|
||||
|
||||
extern GSList *setupservers;
|
||||
|
||||
extern IPADDR *source_host_ip4, *source_host_ip6; /* Resolved address */
|
||||
extern IPADDR source_host_ip; /* Resolved address */
|
||||
extern int source_host_ok; /* Use source_host_ip .. */
|
||||
|
||||
/* Fill reconnection specific information to connection
|
||||
|
@ -218,7 +218,7 @@ static void server_real_connect(SERVER_REC *server, IPADDR *ip,
|
||||
return;
|
||||
|
||||
if (ip != NULL) {
|
||||
own_ip = IPADDR_IS_V6(ip) ? server->connrec->own_ip6 : server->connrec->own_ip4;
|
||||
own_ip = server->connrec->own_ip;
|
||||
port = server->connrec->proxy != NULL ?
|
||||
server->connrec->proxy_port : server->connrec->port;
|
||||
handle = server->connrec->use_ssl ?
|
||||
@ -280,30 +280,15 @@ static void server_connect_callback_readpipe(SERVER_REC *server)
|
||||
server->connect_pipe[0] = NULL;
|
||||
server->connect_pipe[1] = NULL;
|
||||
|
||||
/* figure out if we should use IPv4 or v6 address */
|
||||
if (iprec.error != 0) {
|
||||
/* error */
|
||||
ip = NULL;
|
||||
} else if (server->connrec->family == AF_INET) {
|
||||
/* force IPv4 connection */
|
||||
ip = iprec.ip4.family == 0 ? NULL : &iprec.ip4;
|
||||
servername = iprec.host4;
|
||||
} else if (server->connrec->family == AF_INET6) {
|
||||
/* force IPv6 connection */
|
||||
ip = iprec.ip6.family == 0 ? NULL : &iprec.ip6;
|
||||
servername = iprec.host6;
|
||||
} else {
|
||||
/* pick the one that was found, or if both do it like
|
||||
/SET resolve_prefer_ipv6 says. */
|
||||
if (iprec.ip4.family == 0 ||
|
||||
(iprec.ip6.family != 0 &&
|
||||
settings_get_bool("resolve_prefer_ipv6"))) {
|
||||
ip = &iprec.ip6;
|
||||
servername = iprec.host6;
|
||||
} else {
|
||||
ip = &iprec.ip4;
|
||||
servername = iprec.host4;
|
||||
}
|
||||
ip = NULL;
|
||||
|
||||
if (iprec.error == 0) {
|
||||
// FIXME : REMOVE THIS BEFORE MERGE
|
||||
if (server->connrec->family)
|
||||
g_assert(server->connrec->family == iprec.ip.family);
|
||||
|
||||
ip = &iprec.ip;
|
||||
servername = iprec.host;
|
||||
}
|
||||
|
||||
if (ip != NULL) {
|
||||
@ -337,8 +322,7 @@ static void server_connect_callback_readpipe(SERVER_REC *server)
|
||||
}
|
||||
|
||||
g_free(iprec.errorstr);
|
||||
g_free(iprec.host4);
|
||||
g_free(iprec.host6);
|
||||
g_free(iprec.host);
|
||||
}
|
||||
|
||||
SERVER_REC *server_connect(SERVER_CONNECT_REC *conn)
|
||||
@ -623,8 +607,7 @@ void server_connect_unref(SERVER_CONNECT_REC *conn)
|
||||
g_free_not_null(conn->address);
|
||||
g_free_not_null(conn->chatnet);
|
||||
|
||||
g_free_not_null(conn->own_ip4);
|
||||
g_free_not_null(conn->own_ip6);
|
||||
g_free_not_null(conn->own_ip);
|
||||
|
||||
g_free_not_null(conn->password);
|
||||
g_free_not_null(conn->nick);
|
||||
@ -654,26 +637,15 @@ void server_change_nick(SERVER_REC *server, const char *nick)
|
||||
}
|
||||
|
||||
/* Update own IPv4 and IPv6 records */
|
||||
void server_connect_own_ip_save(SERVER_CONNECT_REC *conn,
|
||||
IPADDR *ip4, IPADDR *ip6)
|
||||
void server_connect_own_ip_save(SERVER_CONNECT_REC *conn, IPADDR *ip)
|
||||
{
|
||||
if (ip4 == NULL || ip4->family == 0)
|
||||
g_free_and_null(conn->own_ip4);
|
||||
if (ip6 == NULL || ip6->family == 0)
|
||||
g_free_and_null(conn->own_ip6);
|
||||
if (ip == NULL || ip->family == 0)
|
||||
g_free_and_null(conn->own_ip);
|
||||
|
||||
if (ip4 != NULL && ip4->family != 0) {
|
||||
/* IPv4 address was found */
|
||||
if (conn->own_ip4 == NULL)
|
||||
conn->own_ip4 = g_new0(IPADDR, 1);
|
||||
memcpy(conn->own_ip4, ip4, sizeof(IPADDR));
|
||||
}
|
||||
|
||||
if (ip6 != NULL && ip6->family != 0) {
|
||||
/* IPv6 address was found */
|
||||
if (conn->own_ip6 == NULL)
|
||||
conn->own_ip6 = g_new0(IPADDR, 1);
|
||||
memcpy(conn->own_ip6, ip6, sizeof(IPADDR));
|
||||
if (ip != NULL && ip->family != 0) {
|
||||
if (conn->own_ip == NULL)
|
||||
conn->own_ip = g_new0(IPADDR, 1);
|
||||
memcpy(conn->own_ip, ip, sizeof(IPADDR));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -67,8 +67,7 @@ void server_connect_failed(SERVER_REC *server, const char *msg);
|
||||
void server_change_nick(SERVER_REC *server, const char *nick);
|
||||
|
||||
/* Update own IPv4 and IPv6 records */
|
||||
void server_connect_own_ip_save(SERVER_CONNECT_REC *conn,
|
||||
IPADDR *ip4, IPADDR *ip6);
|
||||
void server_connect_own_ip_save(SERVER_CONNECT_REC *conn, IPADDR *ip);
|
||||
|
||||
/* `optlist' should contain only one unknown key - the server tag.
|
||||
returns NULL if there was unknown -option */
|
||||
|
@ -138,7 +138,7 @@ static void cmd_server_add(const char *data)
|
||||
if (*password != '\0') g_free_and_null(rec->password);
|
||||
if (g_hash_table_lookup(optlist, "host")) {
|
||||
g_free_and_null(rec->own_host);
|
||||
rec->own_ip4 = rec->own_ip6 = NULL;
|
||||
rec->own_ip = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
@ -193,7 +193,7 @@ static void cmd_server_add(const char *data)
|
||||
value = g_hash_table_lookup(optlist, "host");
|
||||
if (value != NULL && *value != '\0') {
|
||||
rec->own_host = g_strdup(value);
|
||||
rec->own_ip4 = rec->own_ip6 = NULL;
|
||||
rec->own_ip = NULL;
|
||||
}
|
||||
|
||||
signal_emit("server add fill", 2, rec, optlist);
|
||||
|
@ -108,7 +108,7 @@ static void cmd_network_add(const char *data)
|
||||
if (g_hash_table_lookup(optlist, "realname")) g_free_and_null(rec->realname);
|
||||
if (g_hash_table_lookup(optlist, "host")) {
|
||||
g_free_and_null(rec->own_host);
|
||||
rec->own_ip4 = rec->own_ip6 = NULL;
|
||||
rec->own_ip = NULL;
|
||||
}
|
||||
if (g_hash_table_lookup(optlist, "usermode")) g_free_and_null(rec->usermode);
|
||||
if (g_hash_table_lookup(optlist, "autosendcmd")) g_free_and_null(rec->autosendcmd);
|
||||
@ -140,7 +140,7 @@ static void cmd_network_add(const char *data)
|
||||
value = g_hash_table_lookup(optlist, "host");
|
||||
if (value != NULL && *value != '\0') {
|
||||
rec->own_host = g_strdup(value);
|
||||
rec->own_ip4 = rec->own_ip6 = NULL;
|
||||
rec->own_ip = NULL;
|
||||
}
|
||||
|
||||
value = g_hash_table_lookup(optlist, "usermode");
|
||||
|
@ -264,12 +264,12 @@ GIOChannel *dcc_connect_ip(IPADDR *ip, int port)
|
||||
}
|
||||
|
||||
if (own_ip == NULL)
|
||||
own_ip = IPADDR_IS_V6(ip) ? source_host_ip6 : source_host_ip4;
|
||||
own_ip = &source_host_ip;
|
||||
|
||||
handle = net_connect_ip(ip, port, own_ip);
|
||||
if (handle == NULL && errno == EADDRNOTAVAIL && own_ip != NULL) {
|
||||
/* dcc_own_ip is external address */
|
||||
own_ip = IPADDR_IS_V6(ip) ? source_host_ip6 : source_host_ip4;
|
||||
own_ip = &source_host_ip;
|
||||
handle = net_connect_ip(ip, port, own_ip);
|
||||
}
|
||||
return handle;
|
||||
|
@ -585,7 +585,7 @@ static LISTEN_REC *find_listen(const char *ircnet, int port)
|
||||
static void add_listen(const char *ircnet, int port)
|
||||
{
|
||||
LISTEN_REC *rec;
|
||||
IPADDR ip4, ip6, *my_ip;
|
||||
IPADDR ip, *my_ip;
|
||||
|
||||
if (port <= 0 || *ircnet == '\0')
|
||||
return;
|
||||
@ -593,16 +593,13 @@ static void add_listen(const char *ircnet, int port)
|
||||
/* bind to specific host/ip? */
|
||||
my_ip = NULL;
|
||||
if (*settings_get_str("irssiproxy_bind") != '\0') {
|
||||
if (net_gethostbyname(settings_get_str("irssiproxy_bind"),
|
||||
&ip4, &ip6) != 0) {
|
||||
if (net_gethostbyname(settings_get_str("irssiproxy_bind"), &ip) != 0) {
|
||||
printtext(NULL, NULL, MSGLEVEL_CLIENTERROR,
|
||||
"Proxy: can not resolve '%s' - aborting",
|
||||
settings_get_str("irssiproxy_bind"));
|
||||
return;
|
||||
}
|
||||
|
||||
my_ip = ip6.family == 0 ? &ip4 : ip4.family == 0 ||
|
||||
settings_get_bool("resolve_prefer_ipv6") ? &ip6 : &ip4;
|
||||
my_ip = &ip;
|
||||
}
|
||||
|
||||
rec = g_new0(LISTEN_REC, 1);
|
||||
|
Loading…
Reference in New Issue
Block a user