* 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
return 1;
}
+static const char *
+get_ssl_error(unsigned long err)
+{
+ static char buf[512];
+
+ ERR_error_string_n(err, buf, sizeof buf);
+ return buf;
+}
+
int
rb_init_ssl(void)
{
if(ssl_server_ctx == NULL)
{
rb_lib_log("rb_init_openssl: Unable to initialize OpenSSL server context: %s",
- ERR_error_string(ERR_get_error(), NULL));
+ get_ssl_error(ERR_get_error()));
ret = 0;
}
/* Disable SSLv2, make the client use our settings */
- SSL_CTX_set_options(ssl_server_ctx, SSL_OP_NO_SSLv2 | SSL_OP_CIPHER_SERVER_PREFERENCE);
+ SSL_CTX_set_options(ssl_server_ctx, SSL_OP_NO_SSLv2 | SSL_OP_CIPHER_SERVER_PREFERENCE
+#ifdef SSL_OP_SINGLE_DH_USE
+ | SSL_OP_SINGLE_DH_USE
+#endif
+ );
SSL_CTX_set_verify(ssl_server_ctx, SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE, verify_accept_all_cb);
+ SSL_CTX_set_session_id_context(ssl_server_ctx,
+ (const unsigned char *)"libratbox", 9);
+ SSL_CTX_set_cipher_list(ssl_server_ctx, "EECDH+HIGH:EDH+HIGH:HIGH:!aNULL");
+
+ /* Set ECDHE on OpenSSL 1.00+, but make sure it's actually available because redhat are dicks
+ and bastardise their OpenSSL for stupid reasons... */
+ #if (OPENSSL_VERSION_NUMBER >= 0x10000000) && defined(NID_secp384r1)
+ EC_KEY *key = EC_KEY_new_by_curve_name(NID_secp384r1);
+ if (key) {
+ SSL_CTX_set_tmp_ecdh(ssl_server_ctx, key);
+ EC_KEY_free(key);
+ }
+#ifdef SSL_OP_SINGLE_ECDH_USE
+ SSL_CTX_set_options(ssl_server_ctx, SSL_OP_SINGLE_ECDH_USE);
+#endif
+ #endif
ssl_client_ctx = SSL_CTX_new(TLSv1_client_method());
if(ssl_client_ctx == NULL)
{
rb_lib_log("rb_init_openssl: Unable to initialize OpenSSL client context: %s",
- ERR_error_string(ERR_get_error(), NULL));
+ get_ssl_error(ERR_get_error()));
ret = 0;
}
return ret;
rb_lib_log("rb_setup_ssl_server: No certificate file");
return 0;
}
- if(!SSL_CTX_use_certificate_chain_file(ssl_server_ctx, cert))
+ if(!SSL_CTX_use_certificate_chain_file(ssl_server_ctx, cert) || !SSL_CTX_use_certificate_chain_file(ssl_client_ctx, cert))
{
err = ERR_get_error();
rb_lib_log("rb_setup_ssl_server: Error loading certificate file [%s]: %s", cert,
- ERR_error_string(err, NULL));
+ get_ssl_error(err));
return 0;
}
}
- if(!SSL_CTX_use_PrivateKey_file(ssl_server_ctx, keyfile, SSL_FILETYPE_PEM))
+ if(!SSL_CTX_use_PrivateKey_file(ssl_server_ctx, keyfile, SSL_FILETYPE_PEM) || !SSL_CTX_use_PrivateKey_file(ssl_client_ctx, keyfile, SSL_FILETYPE_PEM))
{
err = ERR_get_error();
rb_lib_log("rb_setup_ssl_server: Error loading keyfile [%s]: %s", keyfile,
- ERR_error_string(err, NULL));
+ get_ssl_error(err));
return 0;
}
err = ERR_get_error();
rb_lib_log
("rb_setup_ssl_server: Error loading DH params file [%s]: %s",
- dhfile, ERR_error_string(err, NULL));
+ dhfile, get_ssl_error(err));
BIO_free(bio);
return 0;
}
{
err = ERR_get_error();
rb_lib_log("rb_setup_ssl_server: Error loading DH params file [%s]: %s",
- dhfile, ERR_error_string(err, NULL));
+ dhfile, get_ssl_error(err));
}
}
return 1;
}
int
-rb_ssl_listen(rb_fde_t *F, int backlog)
+rb_ssl_listen(rb_fde_t *F, int backlog, int defer_accept)
{
+ int result;
+
+ result = rb_listen(F, backlog, defer_accept);
F->type = RB_FD_SOCKET | RB_FD_LISTEN | RB_FD_SSL;
- return listen(F->fd, backlog);
+
+ return result;
}
struct ssl_connect
const char *
rb_get_ssl_strerror(rb_fde_t *F)
{
- return ERR_error_string(F->ssl_errno, NULL);
+ return get_ssl_error(F->ssl_errno);
}
int
res == X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT)
{
memcpy(certfp, cert->sha1_hash, RB_SSL_CERTFP_LEN);
+ X509_free(cert);
return 1;
}
+ X509_free(cert);
}
return 0;
void
rb_get_ssl_info(char *buf, size_t len)
{
- rb_snprintf(buf, len, "Using SSL: %s compiled: 0x%lx, library 0x%lx",
- SSLeay_version(SSLEAY_VERSION), OPENSSL_VERSION_NUMBER, SSLeay());
+ rb_snprintf(buf, len, "Using SSL: %s compiled: 0x%lx, library 0x%lx",
+ SSLeay_version(SSLEAY_VERSION),
+ (long)OPENSSL_VERSION_NUMBER, SSLeay());
}