diff options
Diffstat (limited to 'src/fe-common')
-rw-r--r-- | src/fe-common/core/Makefile.am | 2 | ||||
-rw-r--r-- | src/fe-common/core/fe-common-core.c | 5 | ||||
-rw-r--r-- | src/fe-common/core/fe-server.c | 71 | ||||
-rw-r--r-- | src/fe-common/core/fe-tls.c | 94 | ||||
-rw-r--r-- | src/fe-common/core/fe-tls.h | 25 | ||||
-rw-r--r-- | src/fe-common/core/module-formats.c | 13 | ||||
-rw-r--r-- | src/fe-common/core/module-formats.h | 14 | ||||
-rw-r--r-- | src/fe-common/irc/fe-irc-server.c | 34 |
8 files changed, 219 insertions, 39 deletions
diff --git a/src/fe-common/core/Makefile.am b/src/fe-common/core/Makefile.am index 63f91fa6..6efff411 100644 --- a/src/fe-common/core/Makefile.am +++ b/src/fe-common/core/Makefile.am @@ -24,6 +24,7 @@ libfe_common_core_a_SOURCES = \ fe-queries.c \ fe-server.c \ fe-settings.c \ + fe-tls.c \ formats.c \ hilight-text.c \ keyboard.c \ @@ -48,6 +49,7 @@ pkginc_fe_common_core_HEADERS = \ fe-exec.h \ fe-messages.h \ fe-queries.h \ + fe-tls.h \ formats.h \ hilight-text.h \ keyboard.h \ diff --git a/src/fe-common/core/fe-common-core.c b/src/fe-common/core/fe-common-core.c index 1b2ab1e2..fd0e6cf0 100644 --- a/src/fe-common/core/fe-common-core.c +++ b/src/fe-common/core/fe-common-core.c @@ -88,6 +88,9 @@ void fe_server_deinit(void); void fe_settings_init(void); void fe_settings_deinit(void); +void fe_tls_init(void); +void fe_tls_deinit(void); + void window_commands_init(void); void window_commands_deinit(void); @@ -176,6 +179,7 @@ void fe_common_core_init(void) fe_modules_init(); fe_server_init(); fe_settings_init(); + fe_tls_init(); windows_init(); window_activity_init(); window_commands_init(); @@ -217,6 +221,7 @@ void fe_common_core_deinit(void) fe_modules_deinit(); fe_server_deinit(); fe_settings_deinit(); + fe_tls_deinit(); windows_deinit(); window_activity_deinit(); window_commands_deinit(); diff --git a/src/fe-common/core/fe-server.c b/src/fe-common/core/fe-server.c index 468cb707..f4c1d3ee 100644 --- a/src/fe-common/core/fe-server.c +++ b/src/fe-common/core/fe-server.c @@ -154,42 +154,66 @@ static void cmd_server_add_modify(const char *data, gboolean add) else if (g_hash_table_lookup(optlist, "4")) rec->family = AF_INET; - if (g_hash_table_lookup(optlist, "ssl")) - rec->use_ssl = TRUE; + if (g_hash_table_lookup(optlist, "tls") || g_hash_table_lookup(optlist, "ssl")) + rec->use_tls = TRUE; - value = g_hash_table_lookup(optlist, "ssl_cert"); + value = g_hash_table_lookup(optlist, "tls_cert"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_cert"); if (value != NULL && *value != '\0') - rec->ssl_cert = g_strdup(value); + rec->tls_cert = g_strdup(value); - value = g_hash_table_lookup(optlist, "ssl_pkey"); + value = g_hash_table_lookup(optlist, "tls_pkey"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_pkey"); if (value != NULL && *value != '\0') - rec->ssl_pkey = g_strdup(value); + rec->tls_pkey = g_strdup(value); - value = g_hash_table_lookup(optlist, "ssl_pass"); + value = g_hash_table_lookup(optlist, "tls_pass"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_pass"); if (value != NULL && *value != '\0') - rec->ssl_pass = g_strdup(value); + rec->tls_pass = g_strdup(value); - if (g_hash_table_lookup(optlist, "ssl_verify")) - rec->ssl_verify = TRUE; + if (g_hash_table_lookup(optlist, "tls_verify") || g_hash_table_lookup(optlist, "ssl_verify")) + rec->tls_verify = TRUE; - value = g_hash_table_lookup(optlist, "ssl_cafile"); + value = g_hash_table_lookup(optlist, "tls_cafile"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_cafile"); if (value != NULL && *value != '\0') - rec->ssl_cafile = g_strdup(value); + rec->tls_cafile = g_strdup(value); - value = g_hash_table_lookup(optlist, "ssl_capath"); + value = g_hash_table_lookup(optlist, "tls_capath"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_capath"); if (value != NULL && *value != '\0') - rec->ssl_capath = g_strdup(value); + rec->tls_capath = g_strdup(value); - value = g_hash_table_lookup(optlist, "ssl_ciphers"); + value = g_hash_table_lookup(optlist, "tls_ciphers"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_ciphers"); if (value != NULL && *value != '\0') - rec->ssl_ciphers = g_strdup(value); + rec->tls_ciphers = g_strdup(value); - if ((rec->ssl_cafile != NULL && rec->ssl_cafile[0] != '\0') - || (rec->ssl_capath != NULL && rec->ssl_capath[0] != '\0')) - rec->ssl_verify = TRUE; + value = g_hash_table_lookup(optlist, "tls_pinned_cert"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_pinned_cert"); + if (value != NULL && *value != '\0') + rec->tls_pinned_cert = g_strdup(value); + + value = g_hash_table_lookup(optlist, "tls_pinned_pubkey"); + if (value == NULL) + value = g_hash_table_lookup(optlist, "ssl_pinned_pubkey"); + if (value != NULL && *value != '\0') + rec->tls_pinned_pubkey = g_strdup(value); - if ((rec->ssl_cert != NULL && rec->ssl_cert[0] != '\0') || rec->ssl_verify == TRUE) - rec->use_ssl = TRUE; + if ((rec->tls_cafile != NULL && rec->tls_cafile[0] != '\0') + || (rec->tls_capath != NULL && rec->tls_capath[0] != '\0')) + rec->tls_verify = TRUE; + + if ((rec->tls_cert != NULL && rec->tls_cert[0] != '\0') || rec->tls_verify == TRUE) + rec->use_tls = TRUE; if (g_hash_table_lookup(optlist, "auto")) rec->autoconnect = TRUE; if (g_hash_table_lookup(optlist, "noauto")) rec->autoconnect = FALSE; @@ -409,8 +433,9 @@ void fe_server_init(void) command_bind("server remove", NULL, (SIGNAL_FUNC) cmd_server_remove); command_bind_first("server", NULL, (SIGNAL_FUNC) server_command); command_bind_first("disconnect", NULL, (SIGNAL_FUNC) server_command); - command_set_options("server add", "4 6 !! ssl +ssl_cert +ssl_pkey +ssl_pass ssl_verify +ssl_cafile +ssl_capath +ssl_ciphers auto noauto proxy noproxy -host -port noautosendcmd"); - command_set_options("server modify", "4 6 !! ssl +ssl_cert +ssl_pkey +ssl_pass ssl_verify +ssl_cafile +ssl_capath +ssl_ciphers auto noauto proxy noproxy -host -port noautosendcmd"); + + command_set_options("server add", "4 6 !! ssl +ssl_cert +ssl_pkey +ssl_pass ssl_verify +ssl_cafile +ssl_capath +ssl_ciphers +ssl_fingerprint tls +tls_cert +tls_pkey +tls_pass tls_verify +tls_cafile +tls_capath +tls_ciphers +tls_pinned_cert +tls_pinned_pubkey auto noauto proxy noproxy -host -port noautosendcmd"); + command_set_options("server modify", "4 6 !! ssl +ssl_cert +ssl_pkey +ssl_pass ssl_verify +ssl_cafile +ssl_capath +ssl_ciphers +ssl_fingerprint tls +tls_cert +tls_pkey +tls_pass tls_verify +tls_cafile +tls_capath +tls_ciphers +tls_pinned_cert +tls_pinned_pubkey auto noauto proxy noproxy -host -port noautosendcmd"); signal_add("server looking", (SIGNAL_FUNC) sig_server_looking); signal_add("server connecting", (SIGNAL_FUNC) sig_server_connecting); diff --git a/src/fe-common/core/fe-tls.c b/src/fe-common/core/fe-tls.c new file mode 100644 index 00000000..ed206d18 --- /dev/null +++ b/src/fe-common/core/fe-tls.c @@ -0,0 +1,94 @@ +/* + * Copyright (c) 2015 Alexander Færøy <ahf@irssi.org> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the Free + * Software Foundation; either version 2 of the License, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along with + * this program; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301,USA + */ + +#include "module.h" +#include "signals.h" +#include "settings.h" +#include "levels.h" +#include "tls.h" + +#include "module-formats.h" +#include "printtext.h" + +#include "fe-tls.h" + +static void tls_handshake_finished(SERVER_REC *server, TLS_REC *tls) +{ + GSList *certs = NULL; + GSList *subject = NULL; + GSList *issuer = NULL; + GString *str = NULL; + TLS_CERT_ENTRY_REC *data = NULL; + + if (! settings_get_bool("tls_verbose_connect")) + return; + + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_CERT_HEADER); + + for (certs = tls->certs; certs != NULL; certs = certs->next) { + TLS_CERT_REC *tls_cert_rec = certs->data; + str = g_string_new(NULL); + + for (subject = tls_cert_rec->subject; subject != NULL; subject = subject->next) { + data = subject->data; + g_string_append_printf(str, "%s: %s, ", data->name, data->value); + } + + if (str->len > 1) + g_string_truncate(str, str->len - 2); + + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_CERT_SUBJECT, str->str); + g_string_free(str, TRUE); + + str = g_string_new(NULL); + + for (issuer = tls_cert_rec->issuer; issuer != NULL; issuer = issuer->next) { + data = issuer->data; + g_string_append_printf(str, "%s: %s, ", data->name, data->value); + } + + if (str->len > 1) + g_string_truncate(str, str->len - 2); + + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_CERT_ISSUER, str->str); + g_string_free(str, TRUE); + } + + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_PROTOCOL_VERSION, tls->protocol_version, tls->cipher_size, tls->cipher); + + if (tls->ephemeral_key_algorithm != NULL) + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_EPHEMERAL_KEY, tls->ephemeral_key_size, tls->ephemeral_key_algorithm); + else + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_EPHEMERAL_KEY_UNAVAILBLE); + + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_PUBKEY, tls->public_key_size, tls->public_key_algorithm, tls->not_before, tls->not_after); + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_PUBKEY_FINGERPRINT, tls->public_key_fingerprint, tls->public_key_fingerprint_algorithm); + printformat(server, NULL, MSGLEVEL_CLIENTNOTICE, TXT_TLS_CERT_FINGERPRINT, tls->certificate_fingerprint, tls->certificate_fingerprint_algorithm); +} + +void fe_tls_init(void) +{ + settings_add_bool("lookandfeel", "tls_verbose_connect", TRUE); + + signal_add("tls handshake finished", (SIGNAL_FUNC)tls_handshake_finished); +} + +void fe_tls_deinit(void) +{ + signal_remove("tls handshake finished", (SIGNAL_FUNC)tls_handshake_finished); +} diff --git a/src/fe-common/core/fe-tls.h b/src/fe-common/core/fe-tls.h new file mode 100644 index 00000000..f0082477 --- /dev/null +++ b/src/fe-common/core/fe-tls.h @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2015 Alexander Færøy <ahf@irssi.org> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the Free + * Software Foundation; either version 2 of the License, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along with + * this program; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301,USA + */ + +#ifndef __FE_TLS_H +#define __FE_TLS_H + +void fe_tls_init(void); +void fe_tls_deinit(void); + +#endif diff --git a/src/fe-common/core/module-formats.c b/src/fe-common/core/module-formats.c index 5c07f14c..da9705be 100644 --- a/src/fe-common/core/module-formats.c +++ b/src/fe-common/core/module-formats.c @@ -291,5 +291,18 @@ FORMAT_REC fecommon_core_formats[] = { { "completion_line", "%#$[10]0 $[!40]1 $2", 3, { 0, 0, 0 } }, { "completion_footer", "", 0 }, + /* ---- */ + { NULL, "TLS", 0 }, + + { "tls_ephemeral_key", "EDH Key: {hilight $0} bit {hilight $1}", 2, { 1, 0 } }, + { "tls_ephemeral_key_unavailable", "EDH Key: {error N/A}", 0 }, + { "tls_pubkey", "Public Key: {hilight $0} bit {hilight $1}, valid from {hilight $2} to {hilight $3}", 4, { 1, 0, 0, 0 } }, + { "tls_cert_header", "Certificate Chain:", 0 }, + { "tls_cert_subject", " Subject: {hilight $0}", 1, { 0 } }, + { "tls_cert_issuer", " Issuer: {hilight $0}", 1, { 0 } }, + { "tls_pubkey_fingerprint", "Public Key Fingerprint: {hilight $0} ({hilight $1})", 2, { 0, 0 } }, + { "tls_cert_fingerprint", "Certificate Fingerprint: {hilight $0} ({hilight $1})", 2, { 0, 0 } }, + { "tls_protocol_version", "Protocol: {hilight $0} ({hilight $1} bit, {hilight $2})", 3, { 0, 1, 0 } }, + { NULL, NULL, 0 } }; diff --git a/src/fe-common/core/module-formats.h b/src/fe-common/core/module-formats.h index 2b45ff6b..a9ed28c5 100644 --- a/src/fe-common/core/module-formats.h +++ b/src/fe-common/core/module-formats.h @@ -254,7 +254,19 @@ enum { TXT_COMPLETION_REMOVED, TXT_COMPLETION_HEADER, TXT_COMPLETION_LINE, - TXT_COMPLETION_FOOTER + TXT_COMPLETION_FOOTER, + + TLS_FILL_15, + + TXT_TLS_EPHEMERAL_KEY, + TXT_TLS_EPHEMERAL_KEY_UNAVAILBLE, + TXT_TLS_PUBKEY, + TXT_TLS_CERT_HEADER, + TXT_TLS_CERT_SUBJECT, + TXT_TLS_CERT_ISSUER, + TXT_TLS_PUBKEY_FINGERPRINT, + TXT_TLS_CERT_FINGERPRINT, + TXT_TLS_PROTOCOL_VERSION }; extern FORMAT_REC fecommon_core_formats[]; diff --git a/src/fe-common/irc/fe-irc-server.c b/src/fe-common/irc/fe-irc-server.c index 2e22d6f2..c4435d8f 100644 --- a/src/fe-common/irc/fe-irc-server.c +++ b/src/fe-common/irc/fe-irc-server.c @@ -108,23 +108,27 @@ static void cmd_server_list(const char *data) g_string_append(str, "autoconnect, "); if (rec->no_proxy) g_string_append(str, "noproxy, "); - if (rec->use_ssl) { - g_string_append(str, "ssl, "); - if (rec->ssl_cert) { - g_string_append_printf(str, "ssl_cert: %s, ", rec->ssl_cert); - if (rec->ssl_pkey) - g_string_append_printf(str, "ssl_pkey: %s, ", rec->ssl_pkey); - if (rec->ssl_pass) + if (rec->use_tls) { + g_string_append(str, "tls, "); + if (rec->tls_cert) { + g_string_append_printf(str, "tls_cert: %s, ", rec->tls_cert); + if (rec->tls_pkey) + g_string_append_printf(str, "tls_pkey: %s, ", rec->tls_pkey); + if (rec->tls_pass) g_string_append_printf(str, "(pass), "); } - if (rec->ssl_verify) - g_string_append(str, "ssl_verify, "); - if (rec->ssl_cafile) - g_string_append_printf(str, "ssl_cafile: %s, ", rec->ssl_cafile); - if (rec->ssl_capath) - g_string_append_printf(str, "ssl_capath: %s, ", rec->ssl_capath); - if (rec->ssl_ciphers) - g_string_append_printf(str, "ssl_ciphers: %s, ", rec->ssl_ciphers); + if (rec->tls_verify) + g_string_append(str, "tls_verify, "); + if (rec->tls_cafile) + g_string_append_printf(str, "tls_cafile: %s, ", rec->tls_cafile); + if (rec->tls_capath) + g_string_append_printf(str, "tls_capath: %s, ", rec->tls_capath); + if (rec->tls_ciphers) + g_string_append_printf(str, "tls_ciphers: %s, ", rec->tls_ciphers); + if (rec->tls_pinned_cert) + g_string_append_printf(str, "tls_pinned_cert: %s, ", rec->tls_pinned_cert); + if (rec->tls_pinned_pubkey) + g_string_append_printf(str, "tls_pinned_pubkey: %s, ", rec->tls_pinned_pubkey); } if (rec->max_cmds_at_once > 0) |