summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAndrew Potter <agpotter@gmail.com>2014-01-09 12:48:54 +0100
committerSebastien Helleu <flashcode@flashtux.org>2014-01-09 12:48:54 +0100
commit144dc60d0ab062aa5b3943d57f8f6515310f2dd5 (patch)
tree06c0e13ad72be462a3b018cf9905c5af5921ff07 /src
parent9040dfbf521b12b675b6f7d5d93bb10767a40f90 (diff)
downloadweechat-144dc60d0ab062aa5b3943d57f8f6515310f2dd5.zip
xfer: add support of IPv6 for DCC chat/file (patch #7992)
Diffstat (limited to 'src')
-rw-r--r--src/core/wee-network.c88
-rw-r--r--src/core/wee-network.h7
-rw-r--r--src/plugins/irc/irc-command.c28
-rw-r--r--src/plugins/irc/irc-server.c44
-rw-r--r--src/plugins/weechat-plugin.h15
-rw-r--r--src/plugins/xfer/xfer-buffer.c11
-rw-r--r--src/plugins/xfer/xfer-chat.c7
-rw-r--r--src/plugins/xfer/xfer-command.c7
-rw-r--r--src/plugins/xfer/xfer-dcc.c6
-rw-r--r--src/plugins/xfer/xfer-network.c59
-rw-r--r--src/plugins/xfer/xfer.c353
-rw-r--r--src/plugins/xfer/xfer.h11
12 files changed, 393 insertions, 243 deletions
diff --git a/src/core/wee-network.c b/src/core/wee-network.c
index 49b258d49..1066d2ba9 100644
--- a/src/core/wee-network.c
+++ b/src/core/wee-network.c
@@ -645,56 +645,84 @@ network_connect (int sock, const struct sockaddr *addr, socklen_t addrlen)
* process.
*
* Returns:
- * 1: OK
- * 0: error
+ * >= 0: connected socket fd
+ * -1: error
*/
int
-network_connect_to (const char *proxy, int sock,
- unsigned long address, int port)
+network_connect_to (const char *proxy, struct sockaddr *address,
+ socklen_t address_length)
{
struct t_proxy *ptr_proxy;
- struct sockaddr_in addr;
- struct hostent *hostent;
- char *ip4;
+ struct addrinfo *proxy_addrinfo, hints;
+ char str_port[16], ip[NI_MAXHOST];
+ int port, sock;
+
+ sock = -1;
+ proxy_addrinfo = NULL;
ptr_proxy = NULL;
if (proxy && proxy[0])
{
ptr_proxy = proxy_search (proxy);
if (!ptr_proxy)
- return 0;
+ return -1;
}
if (ptr_proxy)
{
- memset (&addr, 0, sizeof (addr));
- addr.sin_addr.s_addr = htonl (address);
- ip4 = inet_ntoa(addr.sin_addr);
-
- memset (&addr, 0, sizeof (addr));
- addr.sin_port = htons (CONFIG_INTEGER(ptr_proxy->options[PROXY_OPTION_PORT]));
- addr.sin_family = AF_INET;
- hostent = gethostbyname (CONFIG_STRING(ptr_proxy->options[PROXY_OPTION_ADDRESS]));
- if (!hostent)
- return 0;
- memcpy(&(addr.sin_addr), *(hostent->h_addr_list), sizeof(struct in_addr));
- if (!network_connect (sock, (struct sockaddr *) &addr, sizeof (addr)))
- return 0;
- if (!network_pass_proxy (proxy, sock, ip4, port))
- return 0;
+ /* get IP address/port */
+ if (getnameinfo (address, address_length, ip, sizeof (ip),
+ str_port, sizeof (str_port),
+ NI_NUMERICHOST | NI_NUMERICSERV) != 0)
+ {
+ goto error;
+ }
+ port = atoi (str_port);
+
+ /* get sockaddr for proxy */
+ memset (&hints, 0, sizeof (hints));
+ hints.ai_family = AF_UNSPEC;
+ hints.ai_socktype = SOCK_STREAM;
+ hints.ai_flags = AI_NUMERICSERV;
+ snprintf (str_port, sizeof (str_port), "%d",
+ CONFIG_INTEGER(ptr_proxy->options[PROXY_OPTION_PORT]));
+ if (getaddrinfo (CONFIG_STRING(ptr_proxy->options[PROXY_OPTION_ADDRESS]),
+ str_port, &hints, &proxy_addrinfo) != 0)
+ {
+ goto error;
+ }
+
+ /* connect and pass address to proxy */
+ sock = socket (proxy_addrinfo->ai_family, SOCK_STREAM, 0);
+ if (sock == -1)
+ goto error;
+ if (!network_connect (sock, proxy_addrinfo->ai_addr,
+ proxy_addrinfo->ai_addrlen))
+ goto error;
+ if (!network_pass_proxy (proxy, sock, ip, port))
+ goto error;
}
else
{
- memset (&addr, 0, sizeof (addr));
- addr.sin_port = htons (port);
- addr.sin_family = AF_INET;
- addr.sin_addr.s_addr = htonl (address);
- if (!network_connect (sock, (struct sockaddr *) &addr, sizeof (addr)))
- return 0;
+ sock = socket (address->sa_family, SOCK_STREAM, 0);
+ if (sock == -1)
+ goto error;
+ if (!network_connect (sock, address, address_length))
+ goto error;
}
- return 1;
+ if (proxy_addrinfo)
+ freeaddrinfo (proxy_addrinfo);
+
+ return sock;
+
+error:
+ if (sock >= 0)
+ close (sock);
+ if (proxy_addrinfo)
+ freeaddrinfo (proxy_addrinfo);
+ return -1;
}
/*
diff --git a/src/core/wee-network.h b/src/core/wee-network.h
index 59ba9c455..c1b1c96b7 100644
--- a/src/core/wee-network.h
+++ b/src/core/wee-network.h
@@ -20,6 +20,9 @@
#ifndef __WEECHAT_NETWORK_H
#define __WEECHAT_NETWORK_H 1
+#include <sys/types.h>
+#include <sys/socket.h>
+
struct t_hook;
struct t_network_socks4
@@ -48,8 +51,8 @@ extern void network_init_gnutls ();
extern void network_end ();
extern int network_pass_proxy (const char *proxy, int sock,
const char *address, int port);
-extern int network_connect_to (const char *proxy, int sock,
- unsigned long address, int port);
+extern int network_connect_to (const char *proxy, struct sockaddr *address,
+ socklen_t address_length);
extern void network_connect_with_fork (struct t_hook *hook_connect);
#endif /* __WEECHAT_NETWORK_H */
diff --git a/src/plugins/irc/irc-command.c b/src/plugins/irc/irc-command.c
index 3b643036e..82b5cd4fa 100644
--- a/src/plugins/irc/irc-command.c
+++ b/src/plugins/irc/irc-command.c
@@ -29,6 +29,7 @@
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
+#include <netdb.h>
#include "../weechat-plugin.h"
#include "irc.h"
@@ -1380,12 +1381,12 @@ int
irc_command_dcc (void *data, struct t_gui_buffer *buffer, int argc,
char **argv, char **argv_eol)
{
- struct sockaddr_in addr;
+ struct sockaddr_storage addr;
socklen_t length;
- unsigned long address;
struct t_infolist *infolist;
struct t_infolist_item *item;
- char str_address[128], charset_modifier[256];
+ char str_address[NI_MAXHOST], charset_modifier[256];
+ int rc;
IRC_BUFFER_GET_SERVER_CHANNEL(buffer);
IRC_COMMAND_CHECK_SERVER("dcc", 1);
@@ -1396,11 +1397,20 @@ irc_command_dcc (void *data, struct t_gui_buffer *buffer, int argc,
if (argc > 1)
{
/* use the local interface, from the server socket */
- memset (&addr, 0, sizeof (struct sockaddr_in));
+ memset (&addr, 0, sizeof (addr));
length = sizeof (addr);
- getsockname (ptr_server->sock, (struct sockaddr *) &addr, &length);
- addr.sin_family = AF_INET;
- address = ntohl (addr.sin_addr.s_addr);
+ getsockname (ptr_server->sock, (struct sockaddr *)&addr, &length);
+ rc = getnameinfo ((struct sockaddr *)&addr, length, str_address,
+ sizeof (str_address), NULL, 0, NI_NUMERICHOST);
+ if (rc != 0)
+ {
+ weechat_printf (ptr_server->buffer,
+ _("%s%s: unable to resolve local address of server "
+ "socket: error %d %s"),
+ weechat_prefix ("error"), IRC_PLUGIN_NAME,
+ rc, gai_strerror (rc));
+ return WEECHAT_RC_OK;
+ }
/* DCC SEND file */
if (weechat_strcasecmp (argv[1], "send") == 0)
@@ -1422,8 +1432,6 @@ irc_command_dcc (void *data, struct t_gui_buffer *buffer, int argc,
weechat_infolist_new_var_string (item, "remote_nick", argv[2]);
weechat_infolist_new_var_string (item, "local_nick", ptr_server->nick);
weechat_infolist_new_var_string (item, "filename", argv_eol[3]);
- snprintf (str_address, sizeof (str_address),
- "%lu", address);
weechat_infolist_new_var_string (item, "local_address", str_address);
weechat_infolist_new_var_integer (item, "socket", ptr_server->sock);
weechat_hook_signal_send ("xfer_add",
@@ -1454,8 +1462,6 @@ irc_command_dcc (void *data, struct t_gui_buffer *buffer, int argc,
snprintf (charset_modifier, sizeof (charset_modifier),
"irc.%s.%s", ptr_server->name, argv[2]);
weechat_infolist_new_var_string (item, "charset_modifier", charset_modifier);
- snprintf (str_address, sizeof (str_address),
- "%lu", address);
weechat_infolist_new_var_string (item, "local_address", str_address);
weechat_hook_signal_send ("xfer_add",
WEECHAT_HOOK_SIGNAL_POINTER,
diff --git a/src/plugins/irc/irc-server.c b/src/plugins/irc/irc-server.c
index b8acff11a..05e78fca3 100644
--- a/src/plugins/irc/irc-server.c
+++ b/src/plugins/irc/irc-server.c
@@ -36,6 +36,9 @@
#include <sys/socket.h>
#include <sys/time.h>
#endif
+#include <sys/types.h>
+#include <netdb.h>
+#include <arpa/inet.h>
#ifdef HAVE_GNUTLS
#include <gnutls/gnutls.h>
@@ -4402,8 +4405,11 @@ irc_server_xfer_send_ready_cb (void *data, const char *signal,
{
struct t_infolist *infolist;
struct t_irc_server *ptr_server;
- const char *plugin_name, *plugin_id, *type, *filename;
- int spaces_in_name;
+ const char *plugin_name, *plugin_id, *type, *filename, *local_address;
+ char converted_addr[NI_MAXHOST];
+ struct addrinfo *ainfo;
+ struct sockaddr_in *saddr;
+ int spaces_in_name, rc;
/* make C compiler happy */
(void) data;
@@ -4416,14 +4422,40 @@ irc_server_xfer_send_ready_cb (void *data, const char *signal,
{
plugin_name = weechat_infolist_string (infolist, "plugin_name");
plugin_id = weechat_infolist_string (infolist, "plugin_id");
- if (plugin_name && (strcmp (plugin_name, IRC_PLUGIN_NAME) == 0) && plugin_id)
+ if (plugin_name && (strcmp (plugin_name, IRC_PLUGIN_NAME) == 0)
+ && plugin_id)
{
ptr_server = irc_server_search (plugin_id);
if (ptr_server)
{
+ converted_addr[0] = '\0';
+ local_address = weechat_infolist_string (infolist,
+ "local_address");
+ if (local_address)
+ {
+ rc = getaddrinfo (local_address, NULL, NULL, &ainfo);
+ if ((rc == 0) && ainfo && ainfo->ai_addr)
+ {
+ if (ainfo->ai_family == AF_INET)
+ {
+ /* transform dotted 4 IP address to ulong string */
+ saddr = (struct sockaddr_in *)ainfo->ai_addr;
+ snprintf (converted_addr, sizeof (converted_addr),
+ "%lu",
+ (unsigned long)ntohl (saddr->sin_addr.s_addr));
+ }
+ else
+ {
+ snprintf (converted_addr, sizeof (converted_addr),
+ "%s", local_address);
+ }
+ }
+ }
+
type = weechat_infolist_string (infolist, "type_string");
- if (type)
+ if (type && converted_addr[0])
{
+ /* send DCC PRIVMSG */
if (strcmp (type, "file_send") == 0)
{
filename = weechat_infolist_string (infolist, "filename");
@@ -4436,7 +4468,7 @@ irc_server_xfer_send_ready_cb (void *data, const char *signal,
(spaces_in_name) ? "\"" : "",
filename,
(spaces_in_name) ? "\"" : "",
- weechat_infolist_string (infolist, "local_address"),
+ converted_addr,
weechat_infolist_integer (infolist, "port"),
weechat_infolist_string (infolist, "size"));
}
@@ -4446,7 +4478,7 @@ irc_server_xfer_send_ready_cb (void *data, const char *signal,
IRC_SERVER_SEND_OUTQ_PRIO_HIGH, NULL,
"PRIVMSG %s :\01DCC CHAT chat %s %d\01",
weechat_infolist_string (infolist, "remote_nick"),
- weechat_infolist_string (infolist, "local_address"),
+ converted_addr,
weechat_infolist_integer (infolist, "port"));
}
}
diff --git a/src/plugins/weechat-plugin.h b/src/plugins/weechat-plugin.h
index 00d5ca826..10452126f 100644
--- a/src/plugins/weechat-plugin.h
+++ b/src/plugins/weechat-plugin.h
@@ -27,6 +27,7 @@ extern "C" {
#endif
#include <sys/types.h>
+#include <sys/socket.h>
/* some systems like GNU/Hurd do not define PATH_MAX */
#ifndef PATH_MAX
@@ -56,7 +57,7 @@ struct timeval;
* please change the date with current one; for a second change at same
* date, increment the 01, otherwise please keep 01.
*/
-#define WEECHAT_PLUGIN_API_VERSION "20140105-01"
+#define WEECHAT_PLUGIN_API_VERSION "20140109-01"
/* macros for defining plugin infos */
#define WEECHAT_PLUGIN_NAME(__name) \
@@ -807,8 +808,9 @@ struct t_weechat_plugin
/* network */
int (*network_pass_proxy) (const char *proxy, int sock,
const char *address, int port);
- int (*network_connect_to) (const char *proxy, int sock,
- unsigned long address, int port);
+ int (*network_connect_to) (const char *proxy,
+ struct sockaddr *address,
+ socklen_t address_length);
/* infos */
const char *(*info_get) (struct t_weechat_plugin *plugin,
@@ -1587,9 +1589,10 @@ extern int weechat_plugin_end (struct t_weechat_plugin *plugin);
#define weechat_network_pass_proxy(__proxy, __sock, __address, __port) \
weechat_plugin->network_pass_proxy(__proxy, __sock, __address, \
__port)
-#define weechat_network_connect_to(__proxy, __sock, __address, __port) \
- weechat_plugin->network_connect_to(__proxy, __sock, __address, \
- __port)
+#define weechat_network_connect_to(__proxy, __address, \
+ __address_length) \
+ weechat_plugin->network_connect_to(__proxy, __address, \
+ __address_length)
/* infos */
#define weechat_info_get(__info_name, __arguments) \
diff --git a/src/plugins/xfer/xfer-buffer.c b/src/plugins/xfer/xfer-buffer.c
index 7a88c2e82..7f356b105 100644
--- a/src/plugins/xfer/xfer-buffer.c
+++ b/src/plugins/xfer/xfer-buffer.c
@@ -44,7 +44,7 @@ xfer_buffer_refresh (const char *hotlist)
{
struct t_xfer *ptr_xfer, *xfer_selected;
char str_color[256], suffix[32], status[64], date[128], eta[128];
- char str_ip[32], str_hash[128];
+ char str_ip[128], str_hash[128];
char *progress_bar, *str_pos, *str_total, *str_bytes_per_sec;
int i, length, line, progress_bar_size, num_bars;
unsigned long long pos, pct_complete;
@@ -93,14 +93,11 @@ xfer_buffer_refresh (const char *hotlist)
weechat_config_string (xfer_config_color_text_bg));
str_ip[0] = '\0';
- if (ptr_xfer->remote_address != 0)
+ if (ptr_xfer->remote_address_str)
{
snprintf (str_ip, sizeof (str_ip),
- " (%ld.%ld.%ld.%ld)",
- ptr_xfer->remote_address >> 24,
- (ptr_xfer->remote_address >> 16) & 0xff,
- (ptr_xfer->remote_address >> 8) & 0xff,
- ptr_xfer->remote_address & 0xff);
+ " (%s)",
+ ptr_xfer->remote_address_str);
}
str_hash[0] = '\0';
diff --git a/src/plugins/xfer/xfer-chat.c b/src/plugins/xfer/xfer-chat.c
index cf9b5202b..c465d4f22 100644
--- a/src/plugins/xfer/xfer-chat.c
+++ b/src/plugins/xfer/xfer-chat.c
@@ -372,14 +372,11 @@ xfer_chat_open_buffer (struct t_xfer *xfer)
}
weechat_printf (xfer->buffer,
- _("%s%s: connected to %s (%ld.%ld.%ld.%ld)"),
+ _("%s%s: connected to %s (%s) via xfer chat"),
weechat_prefix ("network"),
XFER_PLUGIN_NAME,
xfer->remote_nick,
- xfer->remote_address >> 24,
- (xfer->remote_address >> 16) & 0xff,
- (xfer->remote_address >> 8) & 0xff,
- xfer->remote_address & 0xff);
+ xfer->remote_address_str);
free (name);
}
diff --git a/src/plugins/xfer/xfer-command.c b/src/plugins/xfer/xfer-command.c
index 3a08774f0..dd6cb6693 100644
--- a/src/plugins/xfer/xfer-command.c
+++ b/src/plugins/xfer/xfer-command.c
@@ -157,15 +157,12 @@ xfer_command_xfer_list (int full)
weechat_printf (NULL,
_(" plugin: %s (id: %s), file: %llu "
"bytes (position: %llu), address: "
- "%ld.%ld.%ld.%ld (port %d)"),
+ "%s (port %d)"),
ptr_xfer->plugin_name,
ptr_xfer->plugin_id,
ptr_xfer->size,
ptr_xfer->pos,
- ptr_xfer->remote_address >> 24,
- (ptr_xfer->remote_address >> 16) & 0xff,
- (ptr_xfer->remote_address >> 8) & 0xff,
- ptr_xfer->remote_address & 0xff,
+ ptr_xfer->remote_address_str,
ptr_xfer->port);
date[0] = '\0';
date_tmp = localtime (&(ptr_xfer->start_transfer));
diff --git a/src/plugins/xfer/xfer-dcc.c b/src/plugins/xfer/xfer-dcc.c
index 8060ac8b8..113dc7765 100644
--- a/src/plugins/xfer/xfer-dcc.c
+++ b/src/plugins/xfer/xfer-dcc.c
@@ -327,8 +327,10 @@ xfer_dcc_recv_file_child (struct t_xfer *xfer)
}
/* first connect to sender (blocking) */
- if (!weechat_network_connect_to (xfer->proxy, xfer->sock,
- xfer->remote_address, xfer->port))
+ xfer->sock = weechat_network_connect_to (xfer->proxy,
+ xfer->remote_address,
+ xfer->remote_address_length);
+ if (xfer->sock == -1)
{
xfer_network_write_pipe (xfer, XFER_STATUS_FAILED,
XFER_ERROR_CONNECT_SENDER);
diff --git a/src/plugins/xfer/xfer-network.c b/src/plugins/xfer/xfer-network.c
index 57d163f92..fb9b18ac8 100644
--- a/src/plugins/xfer/xfer-network.c
+++ b/src/plugins/xfer/xfer-network.c
@@ -253,14 +253,11 @@ xfer_network_send_file_fork (struct t_xfer *xfer)
}
weechat_printf (NULL,
- _("%s: sending file to %s (%ld.%ld.%ld.%ld, %s.%s), "
+ _("%s: sending file to %s (%s, %s.%s), "
"name: %s (local filename: %s), %llu bytes (protocol: %s)"),
XFER_PLUGIN_NAME,
xfer->remote_nick,
- xfer->remote_address >> 24,
- (xfer->remote_address >> 16) & 0xff,
- (xfer->remote_address >> 8) & 0xff,
- xfer->remote_address & 0xff,
+ xfer->remote_address_str,
xfer->plugin_name,
xfer->plugin_id,
xfer->filename,
@@ -375,12 +372,15 @@ xfer_network_fd_cb (void *arg_xfer, int fd)
{
struct t_xfer *xfer;
int sock, flags, error;
- struct sockaddr_in addr;
+ struct sockaddr_storage addr;
socklen_t length;
+ char str_address[NI_MAXHOST];
/* make C compiler happy */
(void) fd;
+ length = sizeof (addr);
+ memset (&addr, 0, length);
xfer = (struct t_xfer *)arg_xfer;
if (xfer->status == XFER_STATUS_CONNECTING)
@@ -388,7 +388,6 @@ xfer_network_fd_cb (void *arg_xfer, int fd)
if (xfer->type == XFER_TYPE_FILE_SEND)
{
xfer->last_activity = time (NULL);
- length = sizeof (addr);
sock = accept (xfer->sock,
(struct sockaddr *) &addr, &length);
error = errno;
@@ -422,7 +421,15 @@ xfer_network_fd_cb (void *arg_xfer, int fd)
xfer_buffer_refresh (WEECHAT_HOTLIST_MESSAGE);
return WEECHAT_RC_OK;
}
- xfer->remote_address = ntohl (addr.sin_addr.s_addr);
+ error = getnameinfo ((struct sockaddr *)&addr, length, str_address,
+ sizeof (str_address), NULL, 0, NI_NUMERICHOST);
+ if (error != 0)
+ {
+ snprintf (str_address, sizeof (str_address),
+ "error: %s", gai_strerror (error));
+ }
+ xfer_set_remote_address (xfer, (struct sockaddr *)&addr, length,
+ str_address);
xfer->status = XFER_STATUS_ACTIVE;
xfer->start_transfer = time (NULL);
xfer_buffer_refresh (WEECHAT_HOTLIST_MESSAGE);
@@ -467,7 +474,15 @@ xfer_network_fd_cb (void *arg_xfer, int fd)
xfer_buffer_refresh (WEECHAT_HOTLIST_MESSAGE);
return WEECHAT_RC_OK;
}
- xfer->remote_address = ntohl (addr.sin_addr.s_addr);
+ error = getnameinfo ((struct sockaddr *)&addr, length, str_address,
+ sizeof (str_address), NULL, 0, NI_NUMERICHOST);
+ if (error != 0)
+ {
+ snprintf (str_address, sizeof (str_address),
+ "error: %s", gai_strerror (error));
+ }
+ xfer_set_remote_address (xfer, (struct sockaddr *)&addr, length,
+ str_address);
xfer->status = XFER_STATUS_ACTIVE;
xfer_buffer_refresh (WEECHAT_HOTLIST_MESSAGE);
xfer->hook_fd = weechat_hook_fd (xfer->sock,
@@ -528,15 +543,17 @@ xfer_network_connect (struct t_xfer *xfer)
else
xfer->status = XFER_STATUS_CONNECTING;
- if (xfer->sock < 0)
+ if (XFER_IS_SEND(xfer->type))
{
- xfer->sock = socket (AF_INET, SOCK_STREAM, 0);
+ /* create socket */
if (xfer->sock < 0)
- return 0;
- }
+ {
+ xfer->sock = socket (xfer->remote_address->sa_family, SOCK_STREAM,
+ 0);
+ if (xfer->sock < 0)
+ return 0;
+ }
- if (XFER_IS_SEND(xfer->type))
- {
/* listen to socket */
flags = fcntl (xfer->sock, F_GETFL);
if (flags == -1)
@@ -566,13 +583,21 @@ xfer_network_connect (struct t_xfer *xfer)
/* for chat receiving, connect to listening host */
if (xfer->type == XFER_TYPE_CHAT_RECV)
{
+ xfer->sock = weechat_network_connect_to (xfer->proxy,
+ xfer->remote_address,
+ xfer->remote_address_length);
+ if (xfer->sock < 0)
+ return 0;
+
flags = fcntl (xfer->sock, F_GETFL);
if (flags == -1)
flags = 0;
if (fcntl (xfer->sock, F_SETFL, flags | O_NONBLOCK) == -1)
+ {
+ close (xfer->sock);
+ xfer->sock = -1;
return 0;
- weechat_network_connect_to (xfer->proxy, xfer->sock,
- xfer->remote_address, xfer->port);
+ }
xfer->hook_fd = weechat_hook_fd (xfer->sock,
1, 0, 0,
diff --git a/src/plugins/xfer/xfer.c b/src/plugins/xfer/xfer.c
index 9233701df..51621d82c 100644
--- a/src/plugins/xfer/xfer.c
+++ b/src/plugins/xfer/xfer.c
@@ -31,6 +31,7 @@
#include <netinet/in.h>
#include <netdb.h>
#include <gcrypt.h>
+#include <arpa/inet.h>
#include "../weechat-plugin.h"
#include "xfer.h"
@@ -300,16 +301,13 @@ xfer_close (struct t_xfer *xfer, enum t_xfer_status status)
if (XFER_IS_FILE(xfer->type))
{
weechat_printf (NULL,
- _("%s%s: file %s %s %s (%ld.%ld.%ld.%ld): %s"),
+ _("%s%s: file %s %s %s (%s): %s"),
(xfer->status == XFER_STATUS_DONE) ? "" : weechat_prefix ("error"),
XFER_PLUGIN_NAME,
xfer->filename,
(xfer->type == XFER_TYPE_FILE_SEND) ? _("sent to") : _("received from"),
xfer->remote_nick,
- xfer->remote_address >> 24,
- (xfer->remote_address >> 16) & 0xff,
- (xfer->remote_address >> 8) & 0xff,
- xfer->remote_address & 0xff,
+ xfer->remote_address_str,
(xfer->status == XFER_STATUS_DONE) ? _("OK") : _("FAILED"));
xfer_network_child_kill (xfer);
}
@@ -320,14 +318,11 @@ xfer_close (struct t_xfer *xfer, enum t_xfer_status status)
{
weechat_printf (xfer->buffer,
_("%s%s: chat closed with %s "
- "(%ld.%ld.%ld.%ld)"),
+ "(%s)"),
weechat_prefix ("network"),
XFER_PLUGIN_NAME,
xfer->remote_nick,
- xfer->remote_address >> 24,
- (xfer->remote_address >> 16) & 0xff,
- (xfer->remote_address >> 8) & 0xff,
- xfer->remote_address & 0xff);
+ xfer->remote_address_str);
}
}
@@ -457,8 +452,12 @@ xfer_alloc ()
/* default values */
new_xfer->filename = NULL;
new_xfer->size = 0;
- new_xfer->local_address = 0;
- new_xfer->remote_address = 0;
+ new_xfer->local_address = NULL;
+ new_xfer->local_address_length = 0;
+ new_xfer->local_address_str = NULL;
+ new_xfer->remote_address = NULL;
+ new_xfer->remote_address_length = 0;
+ new_xfer->remote_address_str = NULL;
new_xfer->port = 0;
new_xfer->remote_nick = NULL;
new_xfer->local_nick = NULL;
@@ -616,11 +615,14 @@ xfer_new (const char *plugin_name, const char *plugin_id,
enum t_xfer_type type, enum t_xfer_protocol protocol,
const char *remote_nick, const char *local_nick,
const char *charset_modifier, const char *filename,
- unsigned long long size, const char *proxy, unsigned long address,
- int port, int sock, const char *local_filename)
+ unsigned long long size, const char *proxy, struct sockaddr *address,
+ socklen_t address_length, int port, int sock,
+ const char *local_filename)
{
struct t_xfer *new_xfer;
const char *ptr_color, *ptr_crc32;
+ char str_address[NI_MAXHOST];
+ int rc;
new_xfer = xfer_alloc ();
if (!new_xfer)
@@ -653,17 +655,36 @@ xfer_new (const char *plugin_name, const char *plugin_id,
new_xfer->filename = strdup (_("xfer chat"));
new_xfer->size = size;
new_xfer->proxy = (proxy) ? strdup (proxy) : NULL;
+ new_xfer->port = port;
+
+ rc = getnameinfo ((struct sockaddr *)address, address_length, str_address,
+ sizeof (str_address), NULL, 0, NI_NUMERICHOST);
+ if (rc != 0)
+ {
+ weechat_printf (NULL,
+ _("%s%s: unable to interpret address: error %d %s"),
+ weechat_prefix ("error"), XFER_PLUGIN_NAME,
+ rc, gai_strerror (rc));
+ snprintf (str_address, sizeof (str_address), "?");
+ }
+
+ new_xfer->local_address = calloc (1, sizeof (struct sockaddr_storage));
+ new_xfer->local_address_length = sizeof (struct sockaddr_storage);
+ new_xfer->remote_address = calloc (1, sizeof (struct sockaddr_storage));
+ new_xfer->remote_address_length = sizeof (struct sockaddr_storage);
+
if (XFER_IS_RECV(type))
{
- new_xfer->local_address = 0;
- new_xfer->remote_address = address;
+ new_xfer->local_address_str = strdup ("");
+ new_xfer->remote_address_str = strdup (str_address);
+ memcpy (new_xfer->remote_address, address, address_length);
}
else
{
- new_xfer->local_address = address;
- new_xfer->remote_address = 0;
+ new_xfer->local_address_str = strdup (str_address);
+ memcpy (new_xfer->local_address, address, address_length);
+ new_xfer->remote_address_str = strdup ("");
}
- new_xfer->port = port;
new_xfer->status = XFER_STATUS_WAITING;
new_xfer->sock = sock;
@@ -708,14 +729,11 @@ xfer_new (const char *plugin_name, const char *plugin_id,
case XFER_TYPE_FILE_RECV:
weechat_printf (NULL,
_("%s: incoming file from %s "
- "(%ld.%ld.%ld.%ld, %s.%s), name: %s, %llu bytes "
+ "(%s, %s.%s), name: %s, %llu bytes "
"(protocol: %s)"),
XFER_PLUGIN_NAME,
remote_nick,
- address >> 24,
- (address >> 16) & 0xff,
- (address >> 8) & 0xff,
- address & 0xff,
+ str_address,
plugin_name,
plugin_id,
filename,
@@ -740,13 +758,10 @@ xfer_new (const char *plugin_name, const char *plugin_id,
case XFER_TYPE_CHAT_RECV:
weechat_printf (NULL,
_("%s: incoming chat request from %s "
- "(%ld.%ld.%ld.%ld, %s.%s)"),
+ "(%s, %s.%s)"),
XFER_PLUGIN_NAME,
remote_nick,
- address >> 24,
- (address >> 16) & 0xff,
- (address >> 8) & 0xff,
- address & 0xff,
+ str_address,
plugin_name,
plugin_id);
xfer_buffer_refresh (WEECHAT_HOTLIST_MESSAGE);
@@ -815,6 +830,25 @@ xfer_new (const char *plugin_name, const char *plugin_id,
}
/*
+ * Sets the remote address field.
+ */
+
+void
+xfer_set_remote_address (struct t_xfer *xfer, struct sockaddr *address,
+ socklen_t length, char *address_str)
+{
+ if (xfer->remote_address)
+ free (xfer->remote_address);
+ xfer->remote_address = calloc (1, length);
+ xfer->remote_address_length = length;
+ memcpy (xfer->remote_address, address, length);
+
+ if (xfer->remote_address_str)
+ free (xfer->remote_address_str);
+ xfer->remote_address_str = strdup ((address_str) ? address_str : "");
+}
+
+/*
* Frees xfer struct and removes it from list.
*/
@@ -850,6 +884,14 @@ xfer_free (struct t_xfer *xfer)
free (xfer->charset_modifier);
if (xfer->filename)
free (xfer->filename);
+ if (xfer->local_address)
+ free (xfer->local_address);
+ if (xfer->local_address_str)
+ free (xfer->local_address_str);
+ if (xfer->remote_address)
+ free (xfer->remote_address);
+ if (xfer->remote_address_str)
+ free (xfer->remote_address_str);
if (xfer->remote_nick_color)
free (xfer->remote_nick_color);
if (xfer->unterminated_message)
@@ -884,15 +926,13 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
struct t_infolist *infolist;
const char *plugin_name, *plugin_id, *str_type, *str_protocol;
const char *remote_nick, *local_nick, *charset_modifier, *filename, *proxy;
- int type, protocol, args, port_start, port_end, sock, port;
- const char *weechat_dir;
- char *dir1, *dir2, *filename2, *short_filename, *pos;
+ const char *weechat_dir, *str_address, *str_port;
+ int type, protocol, args, port_start, port_end, sock, port, rc, own_ip_used;
+ char *dir1, *dir2, *filename2, *short_filename, *pos, str_port_temp[16];
struct stat st;
- struct hostent *host;
- struct sockaddr_in addr;
+ struct addrinfo *ainfo, hints;
+ struct sockaddr_storage addr;
socklen_t length;
- struct in_addr tmpaddr;
- unsigned long local_addr;
unsigned long long file_size;
struct t_xfer *ptr_xfer;
@@ -921,6 +961,7 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
filename2 = NULL;
short_filename = NULL;
+ file_size = 0;
sock = -1;
port = 0;
@@ -974,10 +1015,6 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
}
}
- filename2 = NULL;
- file_size = 0;
- port = 0;
-
if (type == XFER_TYPE_FILE_RECV)
{
filename2 = strdup (filename);
@@ -1029,10 +1066,8 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
if (filename2[strlen (filename2) - 1] != DIR_SEPARATOR_CHAR)
strcat (filename2, DIR_SEPARATOR);
strcat (filename2, filename);
- if (dir1)
- free (dir1);
- if (dir2)
- free (dir2);
+ free (dir1);
+ free (dir2);
}
#endif
/* check if file exists */
@@ -1042,66 +1077,75 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
_("%s%s: cannot access file \"%s\""),
weechat_prefix ("error"), XFER_PLUGIN_NAME,
filename2);
- if (filename2)
- free (filename2);
goto error;
}
file_size = st.st_size;
}
+ port = weechat_infolist_integer (infolist, "port");
+
+ /* set address */
+ memset (&hints, 0, sizeof (struct addrinfo));
+ hints.ai_flags = AI_NUMERICHOST | AI_NUMERICSERV;
+ hints.ai_family = AF_UNSPEC; /* allow IPv4 or IPv6 */
+ hints.ai_socktype = SOCK_STREAM;
+ hints.ai_protocol = 0;
+ hints.ai_canonname = NULL;
+ hints.ai_addr = NULL;
+ hints.ai_next = NULL;
+
+ own_ip_used = 0;
if (XFER_IS_RECV(type))
{
- sscanf (weechat_infolist_string (infolist, "remote_address"), "%lu", &local_addr);
- port = weechat_infolist_integer (infolist, "port");
+ str_address = weechat_infolist_string (infolist, "remote_address");
+ snprintf (str_port_temp, sizeof (str_port_temp), "%d", port);
+ str_port = str_port_temp;
}
else
{
- /* get local IP address */
- sscanf (weechat_infolist_string (infolist, "local_address"), "%lu", &local_addr);
-
- memset (&addr, 0, sizeof (struct sockaddr_in));
- addr.sin_family = AF_INET;
- addr.sin_addr.s_addr = htonl (local_addr);
-
- /* look up the IP address from network_own_ip, if set */
- if (weechat_config_string(xfer_config_network_own_ip)
- && weechat_config_string(xfer_config_network_own_ip)[0])
+ str_port = NULL;
+ if (weechat_config_string (xfer_config_network_own_ip)
+ && weechat_config_string (xfer_config_network_own_ip)[0])
{
- host = gethostbyname (weechat_config_string (xfer_config_network_own_ip));
- if (host)
- {
- memcpy (&tmpaddr, host->h_addr_list[0], sizeof(struct in_addr));
- local_addr = ntohl (tmpaddr.s_addr);
-
- sock = weechat_infolist_integer (infolist, "socket");
- if (sock > 0)
- {
- memset (&addr, 0, sizeof (struct sockaddr_in));
- length = sizeof (addr);
- getsockname (sock, (struct sockaddr *) &addr, &length);
- addr.sin_family = AF_INET;
- }
- }
- else
- {
- weechat_printf (NULL,
- _("%s%s: could not find address for \"%s\", "
- "falling back to local IP"),
- weechat_prefix ("error"), XFER_PLUGIN_NAME,
- weechat_config_string (xfer_config_network_own_ip));
- }
+ str_address = weechat_config_string (xfer_config_network_own_ip);
+ hints.ai_flags = AI_NUMERICSERV;
+ own_ip_used = 1;
}
+ else
+ str_address = weechat_infolist_string (infolist, "local_address");
+ }
+
+ rc = getaddrinfo (str_address, str_port, &hints, &ainfo);
+ if ((rc == 0) && ainfo && ainfo->ai_addr)
+ {
+ memset (&addr, 0, sizeof (addr));
+ memcpy (&addr, ainfo->ai_addr, ainfo->ai_addrlen);
+ length = ainfo->ai_addrlen;
+ freeaddrinfo (ainfo);
+ }
+ else
+ {
+ weechat_printf (NULL,
+ (own_ip_used) ?
+ _("%s%s: invalid address \"%s\" (option "
+ "xfer.network.own_ip): error %d %s") :
+ _("%s%s: unable to find address for \"%s\": "
+ "error %d %s"),
+ weechat_prefix ("error"), XFER_PLUGIN_NAME,
+ str_address, rc, gai_strerror (rc));
+ goto error;
+ }
+ if (XFER_IS_SEND(type))
+ {
/* open socket for xfer */
- sock = socket (AF_INET, SOCK_STREAM, 0);
+ sock = socket (addr.ss_family, SOCK_STREAM, 0);
if (sock < 0)
{
weechat_printf (NULL,
_("%s%s: cannot create socket for xfer: error %d %s"),
weechat_prefix ("error"), XFER_PLUGIN_NAME,
errno, strerror (errno));
- if (filename2)
- free (filename2);
goto error;
}
@@ -1126,8 +1170,11 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
if (!xfer_port_in_use (port))
{
/* attempt to bind to the free port */
- addr.sin_port = htons (port);
- if (bind (sock, (struct sockaddr *) &addr, sizeof (addr)) == 0)
+ if (addr.ss_family == AF_INET)
+ ((struct sockaddr_in *)&addr)->sin_port = htons (port);
+ else
+ ((struct sockaddr_in6 *)&addr)->sin6_port = htons (port);
+ if (bind (sock, (struct sockaddr *)&addr, length) == 0)
break;
}
port++;
@@ -1141,12 +1188,13 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
if (port == 0)
{
/* find port automatically */
- addr.sin_port = 0;
- if (bind (sock, (struct sockaddr *) &addr, sizeof (addr)) == 0)
+ if (bind (sock, (struct sockaddr *)&addr, length) == 0)
{
- length = sizeof (addr);
- getsockname (sock, (struct sockaddr *) &addr, &length);
- port = ntohs (addr.sin_port);
+ getsockname (sock, (struct sockaddr *)&addr, &length);
+ if (addr.ss_family == AF_INET)
+ port = ntohs (((struct sockaddr_in *)&addr)->sin_port);
+ else
+ port = ntohs (((struct sockaddr_in6 *)&addr)->sin6_port);
}
else
port = -1;
@@ -1159,8 +1207,6 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
_("%s%s: cannot find available port for xfer"),
weechat_prefix ("error"), XFER_PLUGIN_NAME);
close (sock);
- if (filename2)
- free (filename2);
goto error;
}
}
@@ -1198,14 +1244,20 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
/* add xfer entry and listen to socket if type is file or chat "send" */
if (XFER_IS_FILE(type))
+ {
ptr_xfer = xfer_new (plugin_name, plugin_id, type, protocol,
remote_nick, local_nick, charset_modifier,
- short_filename, file_size, proxy, local_addr,
- port, sock, filename2);
+ short_filename, file_size, proxy,
+ (struct sockaddr *)&addr, length, port, sock,
+ filename2);
+ }
else
+ {
ptr_xfer = xfer_new (plugin_name, plugin_id, type, protocol,
remote_nick, local_nick, charset_modifier, NULL,
- 0, proxy, local_addr, port, sock, NULL);
+ 0, proxy, (struct sockaddr *)&addr, length,
+ port, sock, NULL);
+ }
if (!ptr_xfer)
{
@@ -1213,10 +1265,6 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
_("%s%s: error creating xfer"),
weechat_prefix ("error"), XFER_PLUGIN_NAME);
close (sock);
- if (short_filename)
- free (short_filename);
- if (filename2)
- free (filename2);
goto error;
}
@@ -1224,15 +1272,18 @@ xfer_add_cb (void *data, const char *signal, const char *type_data,
if (XFER_IS_SEND(ptr_xfer->type) && !XFER_HAS_ENDED(ptr_xfer->status))
xfer_send_signal (ptr_xfer, "xfer_send_ready");
- if (short_filename)
- free (short_filename);
if (filename2)
free (filename2);
-
+ if (short_filename)
+ free (short_filename);
weechat_infolist_reset_item_cursor (infolist);
return WEECHAT_RC_OK;
error:
+ if (filename2)
+ free (filename2);
+ if (short_filename)
+ free (short_filename);
weechat_infolist_reset_item_cursor (infolist);
return WEECHAT_RC_ERROR;
}
@@ -1458,11 +1509,9 @@ xfer_add_to_infolist (struct t_infolist *infolist, struct t_xfer *xfer)
return 0;
if (!weechat_infolist_new_var_string (ptr_item, "proxy", xfer->proxy))
return 0;
- snprintf (value, sizeof (value), "%lu", xfer->local_address);
- if (!weechat_infolist_new_var_string (ptr_item, "local_address", value))
+ if (!weechat_infolist_new_var_string (ptr_item, "local_address", xfer->local_address_str))
return 0;
- snprintf (value, sizeof (value), "%lu", xfer->remote_address);
- if (!weechat_infolist_new_var_string (ptr_item, "remote_address", value))
+ if (!weechat_infolist_new_var_string (ptr_item, "remote_address", xfer->remote_address_str))
return 0;
if (!weechat_infolist_new_var_integer (ptr_item, "port", xfer->port))
return 0;
@@ -1548,57 +1597,61 @@ xfer_print_log ()
{
weechat_log_printf ("");
weechat_log_printf ("[xfer (addr:0x%lx)]", ptr_xfer);
- weechat_log_printf (" plugin_name . . . . : '%s'", ptr_xfer->plugin_name);
- weechat_log_printf (" plugin_id . . . . . : '%s'", ptr_xfer->plugin_id);
- weechat_log_printf (" type. . . . . . . . : %d (%s)",
+ weechat_log_printf (" plugin_name . . . . . . : '%s'", ptr_xfer->plugin_name);
+ weechat_log_printf (" plugin_id . . . . . . . : '%s'", ptr_xfer->plugin_id);
+ weechat_log_printf (" type. . . . . . . . . . : %d (%s)",
ptr_xfer->type,
xfer_type_string[ptr_xfer->type]);
- weechat_log_printf (" protocol. . . . . . : %d (%s)",
+ weechat_log_printf (" protocol. . . . . . . . : %d (%s)",
ptr_xfer->protocol,
xfer_protocol_string[ptr_xfer->protocol]);
- weechat_log_printf (" remote_nick . . . . : '%s'", ptr_xfer->remote_nick);
- weechat_log_printf (" local_nick. . . . . : '%s'", ptr_xfer->local_nick);
- weechat_log_printf (" charset_modifier. . : '%s'", ptr_xfer->charset_modifier);
- weechat_log_printf (" filename. . . . . . : '%s'", ptr_xfer->filename);
- weechat_log_printf (" size. . . . . . . . : %llu", ptr_xfer->size);
- weechat_log_printf (" proxy . . . . . . . : '%s'", ptr_xfer->proxy);
- weechat_log_printf (" local_address . . . : %lu", ptr_xfer->local_address);
- weechat_log_printf (" remote_address. . . : %lu", ptr_xfer->remote_address);
- weechat_log_printf (" port. . . . . . . . : %d", ptr_xfer->port);
-
- weechat_log_printf (" status. . . . . . . : %d (%s)",
+ weechat_log_printf (" remote_nick . . . . . . : '%s'", ptr_xfer->remote_nick);
+ weechat_log_printf (" local_nick. . . . . . . : '%s'", ptr_xfer->local_nick);
+ weechat_log_printf (" charset_modifier. . . . : '%s'", ptr_xfer->charset_modifier);
+ weechat_log_printf (" filename. . . . . . . . : '%s'", ptr_xfer->filename);
+ weechat_log_printf (" size. . . . . . . . . . : %llu", ptr_xfer->size);
+ weechat_log_printf (" proxy . . . . . . . . . : '%s'", ptr_xfer->proxy);
+ weechat_log_printf (" local_address . . . . . : 0x%lx", ptr_xfer->local_address);
+ weechat_log_printf (" local_address_length. . : %d", ptr_xfer->local_address_length);
+ weechat_log_printf (" local_address_str . . . : '%s'" , ptr_xfer->local_address_str);
+ weechat_log_printf (" remote_address. . . . . : 0x%lx", ptr_xfer->remote_address);
+ weechat_log_printf (" remote_address_length . : %d", ptr_xfer->remote_address_length);
+ weechat_log_printf (" remote_address_str. . . : '%s'", ptr_xfer->remote_address_str);
+ weechat_log_printf (" port. . . . . . . . . . : %d", ptr_xfer->port);
+
+ weechat_log_printf (" status. . . . . . . . . : %d (%s)",
ptr_xfer->status,
xfer_status_string[ptr_xfer->status]);
- weechat_log_printf (" buffer. . . . . . . : 0x%lx", ptr_xfer->buffer);
- weechat_log_printf (" remote_nick_color . : '%s'", ptr_xfer->remote_nick_color);
- weechat_log_printf (" fast_send . . . . . : %d", ptr_xfer->fast_send);
- weechat_log_printf (" blocksize . . . . . : %d", ptr_xfer->blocksize);
- weechat_log_printf (" start_time. . . . . : %ld", ptr_xfer->start_time);
- weechat_log_printf (" start_transfer. . . : %ld", ptr_xfer->start_transfer);
- weechat_log_printf (" sock. . . . . . . . : %d", ptr_xfer->sock);
- weechat_log_printf (" child_pid . . . . . : %d", ptr_xfer->child_pid);
- weechat_log_printf (" child_read. . . . . : %d", ptr_xfer->child_read);
- weechat_log_printf (" child_write . . . . : %d", ptr_xfer->child_write);
- weechat_log_printf (" hook_fd . . . . . . : 0x%lx", ptr_xfer->hook_fd);
- weechat_log_printf (" hook_timer. . . . . : 0x%lx", ptr_xfer->hook_timer);
- weechat_log_printf (" unterminated_message: '%s'", ptr_xfer->unterminated_message);
- weechat_log_printf (" file. . . . . . . . : %d", ptr_xfer->file);
- weechat_log_printf (" local_filename. . . : '%s'", ptr_xfer->local_filename);
- weechat_log_printf (" filename_suffix . . : %d", ptr_xfer->filename_suffix);
- weechat_log_printf (" pos . . . . . . . . : %llu", ptr_xfer->pos);
- weechat_log_printf (" ack . . . . . . . . : %llu", ptr_xfer->ack);
- weechat_log_printf (" start_resume. . . . : %llu", ptr_xfer->start_resume);
- weechat_log_printf (" last_check_time . . : %ld", ptr_xfer->last_check_time);
- weechat_log_printf (" last_check_pos. . . : %llu", ptr_xfer->last_check_pos);
- weechat_log_printf (" last_activity . . . : %ld", ptr_xfer->last_activity);
- weechat_log_printf (" bytes_per_sec . . . : %llu", ptr_xfer->bytes_per_sec);
- weechat_log_printf (" eta . . . . . . . . : %llu", ptr_xfer->eta);
- weechat_log_printf (" hash_target . . . . : '%s'", ptr_xfer->hash_target);
- weechat_log_printf (" hash_status . . . . : %d (%s)",
+ weechat_log_printf (" buffer. . . . . . . . . : 0x%lx", ptr_xfer->buffer);
+ weechat_log_printf (" remote_nick_color . . . : '%s'", ptr_xfer->remote_nick_color);
+ weechat_log_printf (" fast_send . . . . . . . : %d", ptr_xfer->fast_send);
+ weechat_log_printf (" blocksize . . . . . . . : %d", ptr_xfer->blocksize);
+ weechat_log_printf (" start_time. . . . . . . : %ld", ptr_xfer->start_time);
+ weechat_log_printf (" start_transfer. . . . . : %ld", ptr_xfer->start_transfer);
+ weechat_log_printf (" sock. . . . . . . . . . : %d", ptr_xfer->sock);
+ weechat_log_printf (" child_pid . . . . . . . : %d", ptr_xfer->child_pid);
+ weechat_log_printf (" child_read. . . . . . . : %d", ptr_xfer->child_read);
+ weechat_log_printf (" child_write . . . . . . : %d", ptr_xfer->child_write);
+ weechat_log_printf (" hook_fd . . . . . . . . : 0x%lx", ptr_xfer->hook_fd);
+ weechat_log_printf (" hook_timer. . . . . . . : 0x%lx", ptr_xfer->hook_timer);
+ weechat_log_printf (" unterminated_message. . : '%s'", ptr_xfer->unterminated_message);
+ weechat_log_printf (" file. . . . . . . . . . : %d", ptr_xfer->file);
+ weechat_log_printf (" local_filename. . . . . : '%s'", ptr_xfer->local_filename);
+ weechat_log_printf (" filename_suffix . . . . : %d", ptr_xfer->filename_suffix);
+ weechat_log_printf (" pos . . . . . . . . . . : %llu", ptr_xfer->pos);
+ weechat_log_printf (" ack . . . . . . . . . . : %llu", ptr_xfer->ack);
+ weechat_log_printf (" start_resume. . . . . . : %llu", ptr_xfer->start_resume);
+ weechat_log_printf (" last_check_time . . . . : %ld", ptr_xfer->last_check_time);
+ weechat_log_printf (" last_check_pos. . . . . : %llu", ptr_xfer->last_check_pos);
+ weechat_log_printf (" last_activity . . . . . : %ld", ptr_xfer->last_activity);
+ weechat_log_printf (" bytes_per_sec . . . . . : %llu", ptr_xfer->bytes_per_sec);
+ weechat_log_printf (" eta . . . . . . . . . . : %llu", ptr_xfer->eta);
+ weechat_log_printf (" hash_target . . . . . . : '%s'", ptr_xfer->hash_target);
+ weechat_log_printf (" hash_status . . . . . . : %d (%s)",
ptr_xfer->hash_status,
xfer_hash_status_string[ptr_xfer->hash_status]);
- weechat_log_printf (" prev_xfer . . . . . : 0x%lx", ptr_xfer->prev_xfer);
- weechat_log_printf (" next_xfer . . . . . : 0x%lx", ptr_xfer->next_xfer);
+ weechat_log_printf (" prev_xfer . . . . . . . : 0x%lx", ptr_xfer->prev_xfer);
+ weechat_log_printf (" next_xfer . . . . . . . : 0x%lx", ptr_xfer->next_xfer);
}
}
diff --git a/src/plugins/xfer/xfer.h b/src/plugins/xfer/xfer.h
index 2afbd50b3..c4f9758d4 100644
--- a/src/plugins/xfer/xfer.h
+++ b/src/plugins/xfer/xfer.h
@@ -140,8 +140,12 @@ struct t_xfer
char *filename; /* filename */
unsigned long long size; /* file size */
char *proxy; /* proxy to use (optional) */
- unsigned long local_address; /* local IP address */
- unsigned long remote_address; /* remote IP address */
+ struct sockaddr *local_address; /* local IP address */
+ socklen_t local_address_length; /* local sockaddr length */
+ char *local_address_str; /* local IP address as string */
+ struct sockaddr *remote_address; /* remote IP address */
+ socklen_t remote_address_length; /* remote sockaddr length */
+ char *remote_address_str; /* remote IP address as string */
int port; /* remote port */
/* internal data */
@@ -191,6 +195,9 @@ extern struct t_xfer *xfer_search_by_number (int number);
extern struct t_xfer *xfer_search_by_buffer (struct t_gui_buffer *buffer);
extern void xfer_close (struct t_xfer *xfer, enum t_xfer_status status);
extern void xfer_send_signal (struct t_xfer *xfer, const char *signal);
+extern void xfer_set_remote_address (struct t_xfer *xfer,
+ struct sockaddr *address, socklen_t length,
+ char *address_str);
extern void xfer_free (struct t_xfer *xfer);
extern int xfer_add_to_infolist (struct t_infolist *infolist,
struct t_xfer *xfer);