int listen_sslctx_setup(void* ctxt) { #ifdef HAVE_SSL SSL_CTX* ctx = (SSL_CTX*)ctxt; /* no SSLv2, SSLv3 because has defects */ if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv2) & SSL_OP_NO_SSLv2) != SSL_OP_NO_SSLv2){ log_crypto_err("could not set SSL_OP_NO_SSLv2"); return 0; } if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv3) & SSL_OP_NO_SSLv3) != SSL_OP_NO_SSLv3){ log_crypto_err("could not set SSL_OP_NO_SSLv3"); return 0; } #if defined(SSL_OP_NO_TLSv1) && defined(SSL_OP_NO_TLSv1_1) /* if we have tls 1.1 disable 1.0 */ if((SSL_CTX_set_options(ctx, SSL_OP_NO_TLSv1) & SSL_OP_NO_TLSv1) != SSL_OP_NO_TLSv1){ log_crypto_err("could not set SSL_OP_NO_TLSv1"); return 0; } #endif #if defined(SSL_OP_NO_TLSv1_1) && defined(SSL_OP_NO_TLSv1_2) /* if we have tls 1.2 disable 1.1 */ if((SSL_CTX_set_options(ctx, SSL_OP_NO_TLSv1_1) & SSL_OP_NO_TLSv1_1) != SSL_OP_NO_TLSv1_1){ log_crypto_err("could not set SSL_OP_NO_TLSv1_1"); return 0; } #endif #if defined(SHA256_DIGEST_LENGTH) && defined(USE_ECDSA) /* if we have sha256, set the cipher list to have no known vulns */ if(!SSL_CTX_set_cipher_list(ctx, "TLS13-CHACHA20-POLY1305-SHA256:TLS13-AES-256-GCM-SHA384:TLS13-AES-128-GCM-SHA256:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256")) log_crypto_err("could not set cipher list with SSL_CTX_set_cipher_list"); #endif if((SSL_CTX_set_options(ctx, SSL_OP_CIPHER_SERVER_PREFERENCE) & SSL_OP_CIPHER_SERVER_PREFERENCE) != SSL_OP_CIPHER_SERVER_PREFERENCE) { log_crypto_err("could not set SSL_OP_CIPHER_SERVER_PREFERENCE"); return 0; } #ifdef HAVE_SSL_CTX_SET_SECURITY_LEVEL SSL_CTX_set_security_level(ctx, 0); #endif #else (void)ctxt; #endif /* HAVE_SSL */ return 1; }
/** setup SSL context */ static SSL_CTX* setup_ctx(struct config_file* cfg) { char* s_cert=NULL, *c_key=NULL, *c_cert=NULL; SSL_CTX* ctx; if(cfg->remote_control_use_cert) { s_cert = fname_after_chroot(cfg->server_cert_file, cfg, 1); c_key = fname_after_chroot(cfg->control_key_file, cfg, 1); c_cert = fname_after_chroot(cfg->control_cert_file, cfg, 1); if(!s_cert || !c_key || !c_cert) fatal_exit("out of memory"); } ctx = SSL_CTX_new(SSLv23_client_method()); if(!ctx) ssl_err("could not allocate SSL_CTX pointer"); if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv2) & SSL_OP_NO_SSLv2) != SSL_OP_NO_SSLv2) ssl_err("could not set SSL_OP_NO_SSLv2"); if(cfg->remote_control_use_cert) { if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv3) & SSL_OP_NO_SSLv3) != SSL_OP_NO_SSLv3) ssl_err("could not set SSL_OP_NO_SSLv3"); if(!SSL_CTX_use_certificate_chain_file(ctx,c_cert) || !SSL_CTX_use_PrivateKey_file(ctx,c_key,SSL_FILETYPE_PEM) || !SSL_CTX_check_private_key(ctx)) ssl_err("Error setting up SSL_CTX client key and cert"); if (SSL_CTX_load_verify_locations(ctx, s_cert, NULL) != 1) ssl_err("Error setting up SSL_CTX verify, server cert"); SSL_CTX_set_verify(ctx, SSL_VERIFY_PEER, NULL); free(s_cert); free(c_key); free(c_cert); } else { /* Use ciphers that don't require authentication */ #if defined(SSL_OP_NO_TLSv1_3) /* in openssl 1.1.1, negotiation code for tls 1.3 does * not allow the unauthenticated aNULL and eNULL ciphers */ SSL_CTX_set_options(ctx, SSL_OP_NO_TLSv1_3); #endif #ifdef HAVE_SSL_CTX_SET_SECURITY_LEVEL SSL_CTX_set_security_level(ctx, 0); #endif if(!SSL_CTX_set_cipher_list(ctx, "aNULL:eNULL")) ssl_err("Error setting NULL cipher!"); } return ctx; }
int main(void) { SSL_CTX *ctx = SSL_CTX_new(DTLS_method()); STACK_OF(SSL_CIPHER) *ciphers; int i, rv = 0; SSL_CTX_set_psk_server_callback(ctx, srvr_psk_callback); SSL_CTX_set_psk_client_callback(ctx, clnt_psk_callback); SSL_CTX_set_security_level(ctx, 0); /* We only care about iterating over each enc/mac; we don't * want to repeat the test for each auth/kx variant. * So keep life simple and only do (non-DH) PSK. */ if (!SSL_CTX_set_cipher_list(ctx, "PSK")) { fprintf(stderr, "Failed to set PSK cipher list\n"); goto out; } ciphers = SSL_CTX_get_ciphers(ctx); for (i = 0; i < sk_SSL_CIPHER_num(ciphers); i++) { const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(ciphers, i); const char *cipher_name = SSL_CIPHER_get_name(cipher); /* As noted above, only one test for each enc/mac variant. */ if (strncmp(cipher_name, "PSK-", 4)) continue; rv = mtu_test(ctx, cipher_name, 0); if (!rv) break; printf("DTLS MTU test OK for %s\n", cipher_name); if (rv == 1) continue; /* mtu_test() returns 2 if it used Encrypt-then-MAC */ rv = mtu_test(ctx, cipher_name, 1); if (!rv) break; printf("DTLS MTU test OK for %s without Encrypt-then-MAC\n", cipher_name); } out: SSL_CTX_free(ctx); return !rv; }
TLS_APPL_STATE *tls_client_init(const TLS_CLIENT_INIT_PROPS *props) { long off = 0; int cachable; int scache_timeout; SSL_CTX *client_ctx; TLS_APPL_STATE *app_ctx; int log_mask; /* * Convert user loglevel to internal logmask. */ log_mask = tls_log_mask(props->log_param, props->log_level); if (log_mask & TLS_LOG_VERBOSE) msg_info("initializing the client-side TLS engine"); /* * Load (mostly cipher related) TLS-library internal main.cf parameters. */ tls_param_init(); /* * Detect mismatch between compile-time headers and run-time library. */ tls_check_version(); #if OPENSSL_VERSION_NUMBER < 0x10100000L /* * Initialize the OpenSSL library by the book! To start with, we must * initialize the algorithms. We want cleartext error messages instead of * just error codes, so we load the error_strings. */ SSL_load_error_strings(); OpenSSL_add_ssl_algorithms(); #endif /* * Create an application data index for SSL objects, so that we can * attach TLScontext information; this information is needed inside * tls_verify_certificate_callback(). */ if (TLScontext_index < 0) { if ((TLScontext_index = SSL_get_ex_new_index(0, 0, 0, 0, 0)) < 0) { msg_warn("Cannot allocate SSL application data index: " "disabling TLS support"); return (0); } } /* * If the administrator specifies an unsupported digest algorithm, fail * now, rather than in the middle of a TLS handshake. */ if (!tls_validate_digest(props->mdalg)) { msg_warn("disabling TLS support"); return (0); } /* * Initialize the PRNG (Pseudo Random Number Generator) with some seed * from external and internal sources. Don't enable TLS without some real * entropy. */ if (tls_ext_seed(var_tls_daemon_rand_bytes) < 0) { msg_warn("no entropy for TLS key generation: disabling TLS support"); return (0); } tls_int_seed(); /* * The SSL/TLS specifications require the client to send a message in the * oldest specification it understands with the highest level it * understands in the message. RFC2487 is only specified for TLSv1, but * we want to be as compatible as possible, so we will start off with a * SSLv2 greeting allowing the best we can offer: TLSv1. We can restrict * this with the options setting later, anyhow. */ ERR_clear_error(); client_ctx = SSL_CTX_new(TLS_client_method()); if (client_ctx == 0) { msg_warn("cannot allocate client SSL_CTX: disabling TLS support"); tls_print_errors(); return (0); } #ifdef SSL_SECOP_PEER /* Backwards compatible security as a base for opportunistic TLS. */ SSL_CTX_set_security_level(client_ctx, 0); #endif /* * See the verify callback in tls_verify.c */ SSL_CTX_set_verify_depth(client_ctx, props->verifydepth + 1); /* * Protocol selection is destination dependent, so we delay the protocol * selection options to the per-session SSL object. */ off |= tls_bug_bits(); SSL_CTX_set_options(client_ctx, off); /* * Set the call-back routine for verbose logging. */ if (log_mask & TLS_LOG_DEBUG) SSL_CTX_set_info_callback(client_ctx, tls_info_callback); /* * Load the CA public key certificates for both the client cert and for * the verification of server certificates. As provided by OpenSSL we * support two types of CA certificate handling: One possibility is to * add all CA certificates to one large CAfile, the other possibility is * a directory pointed to by CApath, containing separate files for each * CA with softlinks named after the hash values of the certificate. The * first alternative has the advantage that the file is opened and read * at startup time, so that you don't have the hassle to maintain another * copy of the CApath directory for chroot-jail. */ if (tls_set_ca_certificate_info(client_ctx, props->CAfile, props->CApath) < 0) { /* tls_set_ca_certificate_info() already logs a warning. */ SSL_CTX_free(client_ctx); /* 200411 */ return (0); } /* * We do not need a client certificate, so the certificates are only * loaded (and checked) if supplied. A clever client would handle * multiple client certificates and decide based on the list of * acceptable CAs, sent by the server, which certificate to submit. * OpenSSL does however not do this and also has no call-back hooks to * easily implement it. * * Load the client public key certificate and private key from file and * check whether the cert matches the key. We can use RSA certificates * ("cert") DSA certificates ("dcert") or ECDSA certificates ("eccert"). * All three can be made available at the same time. The CA certificates * for all three are handled in the same setup already finished. Which * one is used depends on the cipher negotiated (that is: the first * cipher listed by the client which does match the server). The client * certificate is presented after the server chooses the session cipher, * so we will just present the right cert for the chosen cipher (if it * uses certificates). */ if (tls_set_my_certificate_key_info(client_ctx, props->cert_file, props->key_file, props->dcert_file, props->dkey_file, props->eccert_file, props->eckey_file) < 0) { /* tls_set_my_certificate_key_info() already logs a warning. */ SSL_CTX_free(client_ctx); /* 200411 */ return (0); } /* * 2015-12-05: Ephemeral RSA removed from OpenSSL 1.1.0-dev */ #if OPENSSL_VERSION_NUMBER < 0x10100000L /* * According to the OpenSSL documentation, temporary RSA key is needed * export ciphers are in use. We have to provide one, so well, we just do * it. */ SSL_CTX_set_tmp_rsa_callback(client_ctx, tls_tmp_rsa_cb); #endif /* * With OpenSSL 1.0.2 and later the client EECDH curve list becomes * configurable with the preferred curve negotiated via the supported * curves extension. */ tls_auto_eecdh_curves(client_ctx); /* * Finally, the setup for the server certificate checking, done "by the * book". */ SSL_CTX_set_verify(client_ctx, SSL_VERIFY_NONE, tls_verify_certificate_callback); /* * Initialize the session cache. * * Since the client does not search an internal cache, we simply disable it. * It is only useful for expiring old sessions, but we do that in the * tlsmgr(8). * * This makes SSL_CTX_remove_session() not useful for flushing broken * sessions from the external cache, so we must delete them directly (not * via a callback). */ if (tls_mgr_policy(props->cache_type, &cachable, &scache_timeout) != TLS_MGR_STAT_OK) scache_timeout = 0; if (scache_timeout <= 0) cachable = 0; /* * Allocate an application context, and populate with mandatory protocol * and cipher data. */ app_ctx = tls_alloc_app_context(client_ctx, log_mask); /* * The external session cache is implemented by the tlsmgr(8) process. */ if (cachable) { app_ctx->cache_type = mystrdup(props->cache_type); /* * OpenSSL does not use callbacks to load sessions from a client * cache, so we must invoke that function directly. Apparently, * OpenSSL does not provide a way to pass session names from here to * call-back routines that do session lookup. * * OpenSSL can, however, automatically save newly created sessions for * us by callback (we create the session name in the call-back * function). * * XXX gcc 2.95 can't compile #ifdef .. #endif in the expansion of * SSL_SESS_CACHE_CLIENT | SSL_SESS_CACHE_NO_INTERNAL_STORE | * SSL_SESS_CACHE_NO_AUTO_CLEAR. */ #ifndef SSL_SESS_CACHE_NO_INTERNAL_STORE #define SSL_SESS_CACHE_NO_INTERNAL_STORE 0 #endif SSL_CTX_set_session_cache_mode(client_ctx, SSL_SESS_CACHE_CLIENT | SSL_SESS_CACHE_NO_INTERNAL_STORE | SSL_SESS_CACHE_NO_AUTO_CLEAR); SSL_CTX_sess_set_new_cb(client_ctx, new_client_session_cb); /* * OpenSSL ignores timed-out sessions. We need to set the internal * cache timeout at least as high as the external cache timeout. This * applies even if no internal cache is used. We set the session to * twice the cache lifetime. This way a session always lasts longer * than its lifetime in the cache. */ SSL_CTX_set_timeout(client_ctx, 2 * scache_timeout); } return (app_ctx); }