From 3c351ba018703de0639d64030c07aeba02962799 Mon Sep 17 00:00:00 2001 From: dequis Date: Sat, 27 Jun 2015 11:33:55 -0300 Subject: [PATCH 1/5] Initial irssiproxy SSL support Patch by "Christian Sachs" from FS#645, rebased to current head. http://bugs.irssi.org/index.php?do=details&task_id=645 --- src/irc/proxy/dump.c | 40 +++++++++++++++- src/irc/proxy/listen.c | 101 ++++++++++++++++++++++++++++++++++++++--- src/irc/proxy/module.h | 3 ++ src/irc/proxy/proxy.c | 16 ++++++- src/irc/proxy/proxy.h | 17 +++++++ 5 files changed, 167 insertions(+), 10 deletions(-) diff --git a/src/irc/proxy/dump.c b/src/irc/proxy/dump.c index e39c21a6..0ca9ebb4 100644 --- a/src/irc/proxy/dump.c +++ b/src/irc/proxy/dump.c @@ -29,6 +29,42 @@ #include "irc-channels.h" #include "irc-nicklist.h" #include "modes.h" +#include "line-split.h" + +void proxy_send(CLIENT_REC *client, char *d, int l) +{ +#ifdef HAVE_OPENSSL + if(client->listen->use_ssl) { + SSL_write(client->ssl, d, l); + } else +#endif + net_sendbuffer_send(client->handle, d, l); +} + +int proxy_readline(CLIENT_REC *client, char **str) +{ +#ifdef HAVE_OPENSSL + if(client->listen->use_ssl) { + char tmpbuf[2048]; + int recvlen = 0; + + recvlen = SSL_read(client->ssl, tmpbuf, sizeof(tmpbuf)); + if(recvlen > 0) { + return line_split(tmpbuf, recvlen, str, &client->handle->readbuffer); + } else { + int err; + err = SSL_get_error(client->ssl, recvlen); + /* READ/WRITE are not really errors, they just indicate that atm + OpenSSL is waiting for more data */ + if(err == SSL_ERROR_WANT_READ || err == SSL_ERROR_WANT_WRITE) { + return line_split(tmpbuf, 0, str, &client->handle->readbuffer); + } + return recvlen; /* if any other error occurs, this will quit the connection */ + } + } else +#endif + return net_sendbuffer_receive_line(client->handle, str, 1); +} void proxy_outdata(CLIENT_REC *client, const char *data, ...) { @@ -41,7 +77,7 @@ void proxy_outdata(CLIENT_REC *client, const char *data, ...) va_start(args, data); str = g_strdup_vprintf(data, args); - net_sendbuffer_send(client->handle, str, strlen(str)); + proxy_send(client, str, strlen(str)); g_free(str); va_end(args); @@ -65,7 +101,7 @@ void proxy_outdata_all(IRC_SERVER_REC *server, const char *data, ...) CLIENT_REC *rec = tmp->data; if (rec->connected && rec->server == server) - net_sendbuffer_send(rec->handle, str, len); + proxy_send(rec, str, len); } g_free(str); diff --git a/src/irc/proxy/listen.c b/src/irc/proxy/listen.c index dcc94e6b..55d66efb 100644 --- a/src/irc/proxy/listen.c +++ b/src/irc/proxy/listen.c @@ -50,6 +50,11 @@ static void remove_client(CLIENT_REC *rec) printtext(rec->server, NULL, MSGLEVEL_CLIENTNOTICE, "Proxy: Client %s:%d disconnected", rec->host, rec->port); +#ifdef HAVE_OPENSSL + if(rec->listen->use_ssl) { + SSL_free(rec->ssl); + } +#endif g_free(rec->proxy_address); net_sendbuffer_destroy(rec->handle, TRUE); g_source_remove(rec->recv_tag); @@ -133,6 +138,13 @@ static void handle_client_connect_cmd(CLIENT_REC *client, "Proxy: Client %s:%d connected", client->host, client->port); client->connected = TRUE; +#ifdef HAVE_OPENSSL + if(client->listen->use_ssl) { + printtext(NULL, NULL, MSGLEVEL_CLIENTNOTICE, + "Proxy: Client connected from %s using encryption %s and logged in!", client->host, SSL_get_cipher(client->ssl)); + } +#endif + proxy_dump_data(client); } } @@ -310,7 +322,7 @@ static void sig_listen_client(CLIENT_REC *client) g_return_if_fail(client != NULL); while (g_slist_find(proxy_clients, client) != NULL) { - ret = net_sendbuffer_receive_line(client->handle, &str, 1); + ret = proxy_readline(client, &str); if (ret == -1) { /* connection lost */ remove_client(client); @@ -350,6 +362,26 @@ static void sig_listen(LISTEN_REC *listen) net_ip2host(&ip, host); sendbuf = net_sendbuffer_create(handle, 0); rec = g_new0(CLIENT_REC, 1); + +#ifdef HAVE_OPENSSL + if(listen->use_ssl) { + rec->ssl = SSL_new(listen->ssl_ctx); + SSL_set_fd(rec->ssl, g_io_channel_unix_get_fd(handle)); + int sslerror = SSL_accept(rec->ssl); /* handle error! */ + if(sslerror <= 0) { + /* The Handshake might take longer and the client might not be ready yet + so if such an error occurs, we just ignore it, SSL_read and SSL_write + should continue with the handshake. */ + if(SSL_get_error(rec->ssl, sslerror) != SSL_ERROR_WANT_READ) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, + "Proxy: An error occured while accepting SSL connection!"); + g_free(rec); + return; + } + } + } +#endif + rec->listen = listen; rec->handle = sendbuf; rec->host = g_strdup(host); @@ -416,7 +448,7 @@ static void sig_server_event(IRC_SERVER_REC *server, const char *line, if (sscanf(signal+6, "%p", &client) == 1) { /* send it to specific client only */ if (g_slist_find(proxy_clients, client) != NULL) - net_sendbuffer_send(((CLIENT_REC *) client)->handle, next_line->str, next_line->len); + proxy_send((CLIENT_REC *) client, next_line->str, next_line->len); g_free(event); signal_stop(); return; @@ -433,7 +465,7 @@ static void sig_server_event(IRC_SERVER_REC *server, const char *line, if (rec->want_ctcp == 1) { /* only CTCP for the chatnet where client is connected to will be forwarded */ if (strstr(rec->proxy_address, server->connrec->chatnet) != NULL) { - net_sendbuffer_send(rec->handle, + proxy_send(rec, next_line->str, next_line->len); signal_stop(); } @@ -582,7 +614,7 @@ static LISTEN_REC *find_listen(const char *ircnet, int port) return NULL; } -static void add_listen(const char *ircnet, int port) +static void add_listen(const char *ircnet, int port, char *sslcert) { LISTEN_REC *rec; IPADDR ip4, ip6, *my_ip; @@ -620,6 +652,51 @@ static void add_listen(const char *ircnet, int port) return; } + if(sslcert != NULL) { +#ifdef HAVE_OPENSSL + rec->use_ssl = TRUE; + rec->ssl_method = SSLv3_server_method(); /* let's start with 3 */ + rec->ssl_ctx = SSL_CTX_new(rec->ssl_method); + if(rec->ssl_ctx == NULL) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, + "Proxy: Error setting up SSL Context for port %d failed.", + rec->port); + g_free(rec->ircnet); + g_free(rec); + return; + } + + if(SSL_CTX_use_certificate_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading certificate."); + SSL_CTX_free(rec->ssl_ctx); + g_free(rec->ircnet); + g_free(rec); + return; + } + + if(SSL_CTX_use_PrivateKey_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading private key."); + SSL_CTX_free(rec->ssl_ctx); + g_free(rec->ircnet); + g_free(rec); + return; + } + + if(!SSL_CTX_check_private_key(rec->ssl_ctx)) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading checking certificate agains private key."); + SSL_CTX_free(rec->ssl_ctx); + g_free(rec->ircnet); + g_free(rec); + return; + } + +#else + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, + "Proxy: Specified SSL certificate/private key but irssi compiled WITHOUT OpenSSL!"); +#endif + + } + rec->tag = g_input_add(rec->handle, G_INPUT_READ, (GInputFunction) sig_listen, rec); @@ -634,6 +711,11 @@ static void remove_listen(LISTEN_REC *rec) remove_client(rec->clients->data); net_disconnect(rec->handle); +#ifdef HAVE_OPENSSL + if(rec->use_ssl) { + SSL_CTX_free(rec->ssl_ctx); + } +#endif g_source_remove(rec->tag); g_free(rec->ircnet); g_free(rec); @@ -644,7 +726,7 @@ static void read_settings(void) LISTEN_REC *rec; GSList *remove_listens = NULL; GSList *add_listens = NULL; - char **ports, **tmp, *ircnet, *port; + char **ports, **tmp, *ircnet, *port, *sslfile; int portnum; remove_listens = g_slist_copy(proxy_listens); @@ -657,6 +739,13 @@ static void read_settings(void) continue; *port++ = '\0'; + + sslfile = strchr(port, ':'); + + if (sslfile != NULL) { + *sslfile++ = '\0'; + } + portnum = atoi(port); if (portnum <= 0) continue; @@ -680,7 +769,7 @@ static void read_settings(void) while (add_listens != NULL) { rec = add_listens->data; - add_listen(rec->ircnet, rec->port); + add_listen(rec->ircnet, rec->port, sslfile); g_free(rec); add_listens = g_slist_remove(add_listens, add_listens->data); } diff --git a/src/irc/proxy/module.h b/src/irc/proxy/module.h index ff95227f..74b43df6 100644 --- a/src/irc/proxy/module.h +++ b/src/irc/proxy/module.h @@ -24,3 +24,6 @@ void proxy_outdata_all(IRC_SERVER_REC *server, const char *data, ...); void proxy_outserver(CLIENT_REC *client, const char *data, ...); void proxy_outserver_all(IRC_SERVER_REC *server, const char *data, ...); void proxy_outserver_all_except(CLIENT_REC *client, const char *data, ...); + +void proxy_send(CLIENT_REC *client, char *d, int l); +int proxy_readline(CLIENT_REC *client, char **str); diff --git a/src/irc/proxy/proxy.c b/src/irc/proxy/proxy.c index ce79e2b7..841263eb 100644 --- a/src/irc/proxy/proxy.c +++ b/src/irc/proxy/proxy.c @@ -78,6 +78,11 @@ void irc_proxy_init(void) settings_add_str("irssiproxy", "irssiproxy_bind", ""); settings_add_bool("irssiproxy", "irssiproxy", TRUE); +#ifdef HAVE_OPENSSL + SSL_load_error_strings(); + OpenSSL_add_ssl_algorithms(); +#endif + if (*settings_get_str("irssiproxy_password") == '\0') { /* no password - bad idea! */ signal_emit("gui dialog", 2, "warning", @@ -87,9 +92,16 @@ void irc_proxy_init(void) } if (*settings_get_str("irssiproxy_ports") == '\0') { signal_emit("gui dialog", 2, "warning", - "No proxy ports specified. Use /SET " + "No proxy ports specified. Use /set " +#ifdef HAVE_OPENSSL + "irssiproxy_ports = =: " + "... to set them. You can add :filename.pem to secure the proxy with SSL." + " (Should contain a cert and key in PEM format)"); +#else "irssiproxy_ports = = " "... to set them."); +#endif + } command_bind("irssiproxy", NULL, (SIGNAL_FUNC) cmd_irssiproxy); @@ -101,7 +113,7 @@ void irc_proxy_init(void) proxy_listen_init(); } settings_check(); - module_register("proxy", "irc"); + module_register("proxy", "irc"); } void irc_proxy_deinit(void) diff --git a/src/irc/proxy/proxy.h b/src/irc/proxy/proxy.h index 158b0675..e2ca67b2 100644 --- a/src/irc/proxy/proxy.h +++ b/src/irc/proxy/proxy.h @@ -7,6 +7,15 @@ #include "irc.h" #include "irc-servers.h" +#ifdef HAVE_OPENSSL +#include +#include +#include +#include +#include +#include +#endif + typedef struct { int port; char *ircnet; @@ -15,6 +24,11 @@ typedef struct { GIOChannel *handle; GSList *clients; +#ifdef HAVE_OPENSSL + unsigned int use_ssl; + SSL_CTX *ssl_ctx; + SSL_METHOD *ssl_method; +#endif } LISTEN_REC; typedef struct { @@ -29,6 +43,9 @@ typedef struct { unsigned int user_sent:1; unsigned int connected:1; unsigned int want_ctcp:1; +#ifdef HAVE_OPENSSL + SSL *ssl; +#endif } CLIENT_REC; #endif From 87542831fe73f2dc44550d20faf7f608e67008bb Mon Sep 17 00:00:00 2001 From: dequis Date: Sat, 27 Jun 2015 11:59:41 -0300 Subject: [PATCH 2/5] irssiproxy: Remove openssl ifdefs, and several style fixes --- src/irc/proxy/dump.c | 17 ++++------ src/irc/proxy/listen.c | 73 +++++++++++++++++------------------------- src/irc/proxy/proxy.c | 7 ---- src/irc/proxy/proxy.h | 6 ---- 4 files changed, 36 insertions(+), 67 deletions(-) diff --git a/src/irc/proxy/dump.c b/src/irc/proxy/dump.c index 0ca9ebb4..432eadc0 100644 --- a/src/irc/proxy/dump.c +++ b/src/irc/proxy/dump.c @@ -33,37 +33,34 @@ void proxy_send(CLIENT_REC *client, char *d, int l) { -#ifdef HAVE_OPENSSL if(client->listen->use_ssl) { SSL_write(client->ssl, d, l); - } else -#endif - net_sendbuffer_send(client->handle, d, l); + return; + } + net_sendbuffer_send(client->handle, d, l); } int proxy_readline(CLIENT_REC *client, char **str) { -#ifdef HAVE_OPENSSL if(client->listen->use_ssl) { char tmpbuf[2048]; int recvlen = 0; - + recvlen = SSL_read(client->ssl, tmpbuf, sizeof(tmpbuf)); if(recvlen > 0) { return line_split(tmpbuf, recvlen, str, &client->handle->readbuffer); } else { int err; err = SSL_get_error(client->ssl, recvlen); - /* READ/WRITE are not really errors, they just indicate that atm + /* READ/WRITE are not really errors, they just indicate that atm OpenSSL is waiting for more data */ if(err == SSL_ERROR_WANT_READ || err == SSL_ERROR_WANT_WRITE) { return line_split(tmpbuf, 0, str, &client->handle->readbuffer); } return recvlen; /* if any other error occurs, this will quit the connection */ } - } else -#endif - return net_sendbuffer_receive_line(client->handle, str, 1); + } + return net_sendbuffer_receive_line(client->handle, str, 1); } void proxy_outdata(CLIENT_REC *client, const char *data, ...) diff --git a/src/irc/proxy/listen.c b/src/irc/proxy/listen.c index 55d66efb..72d2a0dd 100644 --- a/src/irc/proxy/listen.c +++ b/src/irc/proxy/listen.c @@ -50,11 +50,9 @@ static void remove_client(CLIENT_REC *rec) printtext(rec->server, NULL, MSGLEVEL_CLIENTNOTICE, "Proxy: Client %s:%d disconnected", rec->host, rec->port); -#ifdef HAVE_OPENSSL if(rec->listen->use_ssl) { - SSL_free(rec->ssl); + SSL_free(rec->ssl); } -#endif g_free(rec->proxy_address); net_sendbuffer_destroy(rec->handle, TRUE); g_source_remove(rec->recv_tag); @@ -138,12 +136,10 @@ static void handle_client_connect_cmd(CLIENT_REC *client, "Proxy: Client %s:%d connected", client->host, client->port); client->connected = TRUE; -#ifdef HAVE_OPENSSL - if(client->listen->use_ssl) { - printtext(NULL, NULL, MSGLEVEL_CLIENTNOTICE, - "Proxy: Client connected from %s using encryption %s and logged in!", client->host, SSL_get_cipher(client->ssl)); - } -#endif + if(client->listen->use_ssl) { + printtext(NULL, NULL, MSGLEVEL_CLIENTNOTICE, + "Proxy: Client connected from %s using encryption %s and logged in!", client->host, SSL_get_cipher(client->ssl)); + } proxy_dump_data(client); } @@ -362,8 +358,7 @@ static void sig_listen(LISTEN_REC *listen) net_ip2host(&ip, host); sendbuf = net_sendbuffer_create(handle, 0); rec = g_new0(CLIENT_REC, 1); - -#ifdef HAVE_OPENSSL + if(listen->use_ssl) { rec->ssl = SSL_new(listen->ssl_ctx); SSL_set_fd(rec->ssl, g_io_channel_unix_get_fd(handle)); @@ -376,12 +371,11 @@ static void sig_listen(LISTEN_REC *listen) printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: An error occured while accepting SSL connection!"); g_free(rec); - return; + return; } } } -#endif - + rec->listen = listen; rec->handle = sendbuf; rec->host = g_strdup(host); @@ -653,7 +647,6 @@ static void add_listen(const char *ircnet, int port, char *sslcert) } if(sslcert != NULL) { -#ifdef HAVE_OPENSSL rec->use_ssl = TRUE; rec->ssl_method = SSLv3_server_method(); /* let's start with 3 */ rec->ssl_ctx = SSL_CTX_new(rec->ssl_method); @@ -662,39 +655,33 @@ static void add_listen(const char *ircnet, int port, char *sslcert) "Proxy: Error setting up SSL Context for port %d failed.", rec->port); g_free(rec->ircnet); - g_free(rec); - return; + g_free(rec); + return; } - + if(SSL_CTX_use_certificate_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading certificate."); SSL_CTX_free(rec->ssl_ctx); g_free(rec->ircnet); - g_free(rec); - return; + g_free(rec); + return; } - + if(SSL_CTX_use_PrivateKey_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading private key."); - SSL_CTX_free(rec->ssl_ctx); + SSL_CTX_free(rec->ssl_ctx); g_free(rec->ircnet); - g_free(rec); - return; - } - - if(!SSL_CTX_check_private_key(rec->ssl_ctx)) { - printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading checking certificate agains private key."); - SSL_CTX_free(rec->ssl_ctx); - g_free(rec->ircnet); - g_free(rec); - return; + g_free(rec); + return; } -#else - printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, - "Proxy: Specified SSL certificate/private key but irssi compiled WITHOUT OpenSSL!"); -#endif - + if(!SSL_CTX_check_private_key(rec->ssl_ctx)) { + printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading checking certificate agains private key."); + SSL_CTX_free(rec->ssl_ctx); + g_free(rec->ircnet); + g_free(rec); + return; + } } rec->tag = g_input_add(rec->handle, G_INPUT_READ, @@ -711,11 +698,9 @@ static void remove_listen(LISTEN_REC *rec) remove_client(rec->clients->data); net_disconnect(rec->handle); -#ifdef HAVE_OPENSSL if(rec->use_ssl) { - SSL_CTX_free(rec->ssl_ctx); + SSL_CTX_free(rec->ssl_ctx); } -#endif g_source_remove(rec->tag); g_free(rec->ircnet); g_free(rec); @@ -739,13 +724,13 @@ static void read_settings(void) continue; *port++ = '\0'; - + sslfile = strchr(port, ':'); - + if (sslfile != NULL) { - *sslfile++ = '\0'; + *sslfile++ = '\0'; } - + portnum = atoi(port); if (portnum <= 0) continue; diff --git a/src/irc/proxy/proxy.c b/src/irc/proxy/proxy.c index 841263eb..3e537f5c 100644 --- a/src/irc/proxy/proxy.c +++ b/src/irc/proxy/proxy.c @@ -78,10 +78,8 @@ void irc_proxy_init(void) settings_add_str("irssiproxy", "irssiproxy_bind", ""); settings_add_bool("irssiproxy", "irssiproxy", TRUE); -#ifdef HAVE_OPENSSL SSL_load_error_strings(); OpenSSL_add_ssl_algorithms(); -#endif if (*settings_get_str("irssiproxy_password") == '\0') { /* no password - bad idea! */ @@ -93,14 +91,9 @@ void irc_proxy_init(void) if (*settings_get_str("irssiproxy_ports") == '\0') { signal_emit("gui dialog", 2, "warning", "No proxy ports specified. Use /set " -#ifdef HAVE_OPENSSL "irssiproxy_ports = =: " "... to set them. You can add :filename.pem to secure the proxy with SSL." " (Should contain a cert and key in PEM format)"); -#else - "irssiproxy_ports = = " - "... to set them."); -#endif } diff --git a/src/irc/proxy/proxy.h b/src/irc/proxy/proxy.h index e2ca67b2..ea53d7d9 100644 --- a/src/irc/proxy/proxy.h +++ b/src/irc/proxy/proxy.h @@ -7,14 +7,12 @@ #include "irc.h" #include "irc-servers.h" -#ifdef HAVE_OPENSSL #include #include #include #include #include #include -#endif typedef struct { int port; @@ -24,11 +22,9 @@ typedef struct { GIOChannel *handle; GSList *clients; -#ifdef HAVE_OPENSSL unsigned int use_ssl; SSL_CTX *ssl_ctx; SSL_METHOD *ssl_method; -#endif } LISTEN_REC; typedef struct { @@ -43,9 +39,7 @@ typedef struct { unsigned int user_sent:1; unsigned int connected:1; unsigned int want_ctcp:1; -#ifdef HAVE_OPENSSL SSL *ssl; -#endif } CLIENT_REC; #endif From e2dfd6d165958e9136a0af75f6fef250bfaee617 Mon Sep 17 00:00:00 2001 From: dequis Date: Sat, 27 Jun 2015 12:22:09 -0300 Subject: [PATCH 3/5] irssiproxy: use a single goto for error handling in add_listen() --- src/irc/proxy/listen.c | 27 ++++++++++++--------------- 1 file changed, 12 insertions(+), 15 deletions(-) diff --git a/src/irc/proxy/listen.c b/src/irc/proxy/listen.c index 72d2a0dd..519666bd 100644 --- a/src/irc/proxy/listen.c +++ b/src/irc/proxy/listen.c @@ -654,33 +654,22 @@ static void add_listen(const char *ircnet, int port, char *sslcert) printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error setting up SSL Context for port %d failed.", rec->port); - g_free(rec->ircnet); - g_free(rec); - return; + goto error; } if(SSL_CTX_use_certificate_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading certificate."); - SSL_CTX_free(rec->ssl_ctx); - g_free(rec->ircnet); - g_free(rec); - return; + goto error; } if(SSL_CTX_use_PrivateKey_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading private key."); - SSL_CTX_free(rec->ssl_ctx); - g_free(rec->ircnet); - g_free(rec); - return; + goto error; } if(!SSL_CTX_check_private_key(rec->ssl_ctx)) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading checking certificate agains private key."); - SSL_CTX_free(rec->ssl_ctx); - g_free(rec->ircnet); - g_free(rec); - return; + goto error; } } @@ -688,6 +677,14 @@ static void add_listen(const char *ircnet, int port, char *sslcert) (GInputFunction) sig_listen, rec); proxy_listens = g_slist_append(proxy_listens, rec); + + return; +error: + if (rec->ssl_ctx != NULL) { + SSL_CTX_free(rec->ssl_ctx); + } + g_free(rec->ircnet); + g_free(rec); } static void remove_listen(LISTEN_REC *rec) From b68c81f767e699cd39cb1a2aa4f99b36c947a08d Mon Sep 17 00:00:00 2001 From: dequis Date: Sat, 27 Jun 2015 13:13:03 -0300 Subject: [PATCH 4/5] irssiproxy: Use TLS 1.0/1.1/1.2, disable SSLv2 and SSLv3 --- src/irc/proxy/listen.c | 4 ++-- src/irc/proxy/proxy.h | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/src/irc/proxy/listen.c b/src/irc/proxy/listen.c index 519666bd..6e3ab115 100644 --- a/src/irc/proxy/listen.c +++ b/src/irc/proxy/listen.c @@ -648,14 +648,14 @@ static void add_listen(const char *ircnet, int port, char *sslcert) if(sslcert != NULL) { rec->use_ssl = TRUE; - rec->ssl_method = SSLv3_server_method(); /* let's start with 3 */ - rec->ssl_ctx = SSL_CTX_new(rec->ssl_method); + rec->ssl_ctx = SSL_CTX_new(SSLv23_server_method()); if(rec->ssl_ctx == NULL) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error setting up SSL Context for port %d failed.", rec->port); goto error; } + SSL_CTX_set_options(rec->ssl_ctx, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3); if(SSL_CTX_use_certificate_file(rec->ssl_ctx, sslcert, SSL_FILETYPE_PEM) <= 0) { printtext(NULL, NULL, MSGLEVEL_CLIENTERROR, "Proxy: Error loading certificate."); diff --git a/src/irc/proxy/proxy.h b/src/irc/proxy/proxy.h index ea53d7d9..0b6b9385 100644 --- a/src/irc/proxy/proxy.h +++ b/src/irc/proxy/proxy.h @@ -24,7 +24,6 @@ typedef struct { GSList *clients; unsigned int use_ssl; SSL_CTX *ssl_ctx; - SSL_METHOD *ssl_method; } LISTEN_REC; typedef struct { From 7e57e3415a375ac3a51032257efd61f506c8d608 Mon Sep 17 00:00:00 2001 From: dequis Date: Tue, 6 Oct 2015 08:05:11 -0300 Subject: [PATCH 5/5] irssiproxy: Fix warning about uninitalized value --- src/irc/proxy/listen.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/irc/proxy/listen.c b/src/irc/proxy/listen.c index 6e3ab115..8db84e15 100644 --- a/src/irc/proxy/listen.c +++ b/src/irc/proxy/listen.c @@ -708,7 +708,8 @@ static void read_settings(void) LISTEN_REC *rec; GSList *remove_listens = NULL; GSList *add_listens = NULL; - char **ports, **tmp, *ircnet, *port, *sslfile; + char **ports, **tmp, *ircnet, *port; + char *sslfile = NULL; int portnum; remove_listens = g_slist_copy(proxy_listens);