tls_config_set_session_id
tls_config_set_session_lifetime
tls_config_set_verify_depth
+tls_config_skip_private_key_check
tls_config_verify
tls_config_verify_client
tls_config_verify_client_optional
-/* $OpenBSD: tls.c,v 1.59 2017/01/26 12:56:37 jsing Exp $ */
+/* $OpenBSD: tls.c,v 1.60 2017/04/05 03:13:53 beck Exp $ */
/*
* Copyright (c) 2014 Joel Sing <jsing@openbsd.org>
*
return (0);
}
+int
+tls_cert_hash(X509 *cert, char **hash)
+{
+ char d[EVP_MAX_MD_SIZE], *dhex = NULL;
+ int dlen, rv = -1;
+
+ *hash = NULL;
+ if (X509_digest(cert, EVP_sha256(), d, &dlen) != 1)
+ goto err;
+
+ if (tls_hex_string(d, dlen, &dhex, NULL) != 0)
+ goto err;
+
+ if (asprintf(hash, "SHA256:%s", dhex) == -1) {
+ *hash = NULL;
+ goto err;
+ }
+
+ rv = 0;
+ err:
+ free(dhex);
+
+ return (rv);
+}
+
+static int
+tls_keypair_cert_hash(struct tls_keypair *keypair, char **hash)
+{
+ BIO *membio = NULL;
+ X509 *cert = NULL;
+ int rv = -1;
+
+ *hash = NULL;
+
+ if ((membio = BIO_new_mem_buf(keypair->cert_mem, keypair->cert_len))
+ == NULL)
+ goto err;
+
+ if ((cert = PEM_read_bio_X509_AUX(membio, NULL, NULL, NULL)) == NULL)
+ goto err;
+
+ rv = tls_cert_hash(cert, hash);
+ err:
+ BIO_free(membio);
+
+ return (rv);
+}
+
+
int
tls_configure_ssl_keypair(struct tls *ctx, SSL_CTX *ssl_ctx,
struct tls_keypair *keypair, int required)
tls_set_errorx(ctx, "failed to load certificate");
goto err;
}
+ if (tls_keypair_cert_hash(keypair, &keypair->cert_hash) == -1)
+ goto err;
cert = NULL;
}
+
if (keypair->key_mem != NULL) {
if (keypair->key_len > INT_MAX) {
tls_set_errorx(ctx, "key too long");
tls_set_errorx(ctx, "failed to read private key");
goto err;
}
+
+ if (keypair->cert_hash != NULL) {
+ RSA *rsa;
+ /* XXX only RSA for now for relayd privsep */
+ if ((rsa = EVP_PKEY_get1_RSA(pkey)) != NULL) {
+ RSA_set_ex_data(rsa, 0, keypair->cert_hash);
+ RSA_free(rsa);
+ }
+ }
+
if (SSL_CTX_use_PrivateKey(ssl_ctx, pkey) != 1) {
tls_set_errorx(ctx, "failed to load private key");
goto err;
pkey = NULL;
}
- if (SSL_CTX_check_private_key(ssl_ctx) != 1) {
+ if (!ctx->config->skip_private_key_check &&
+ SSL_CTX_check_private_key(ssl_ctx) != 1) {
tls_set_errorx(ctx, "private/public key mismatch");
goto err;
}
-/* $OpenBSD: tls_config.c,v 1.36 2017/01/31 16:18:57 beck Exp $ */
+/* $OpenBSD: tls_config.c,v 1.37 2017/04/05 03:13:53 beck Exp $ */
/*
* Copyright (c) 2014 Joel Sing <jsing@openbsd.org>
*
free(keypair->cert_mem);
free(keypair->key_mem);
free(keypair->ocsp_staple);
+ free(keypair->cert_hash);
free(keypair);
}
config->verify_client = 2;
}
+void
+tls_config_skip_private_key_check(struct tls_config *config)
+{
+ config->skip_private_key_check = 1;
+}
+
int
tls_config_set_ocsp_staple_file(struct tls_config *config, const char *staple_file)
{
-/* $OpenBSD: tls_conninfo.c,v 1.13 2017/01/09 15:31:20 jsing Exp $ */
+/* $OpenBSD: tls_conninfo.c,v 1.14 2017/04/05 03:13:53 beck Exp $ */
/*
* Copyright (c) 2015 Joel Sing <jsing@openbsd.org>
* Copyright (c) 2015 Bob Beck <beck@openbsd.org>
#include <tls.h>
#include "tls_internal.h"
-static int
+int
tls_hex_string(const unsigned char *in, size_t inlen, char **out,
size_t *outlen)
{
static int
tls_get_peer_cert_hash(struct tls *ctx, char **hash)
{
- char d[EVP_MAX_MD_SIZE], *dhex = NULL;
- int dlen, rv = -1;
-
*hash = NULL;
if (ctx->ssl_peer_cert == NULL)
return (0);
- if (X509_digest(ctx->ssl_peer_cert, EVP_sha256(), d, &dlen) != 1) {
- tls_set_errorx(ctx, "digest failed");
- goto err;
- }
-
- if (tls_hex_string(d, dlen, &dhex, NULL) != 0) {
- tls_set_errorx(ctx, "digest hex string failed");
- goto err;
- }
-
- if (asprintf(hash, "SHA256:%s", dhex) == -1) {
- tls_set_errorx(ctx, "out of memory");
+ if (tls_cert_hash(ctx->ssl_peer_cert, hash) == -1) {
+ tls_set_errorx(ctx, "unable to compute peer certificate hash - out of memory");
*hash = NULL;
- goto err;
+ return -1;
}
-
- rv = 0;
-
-err:
- free(dhex);
-
- return (rv);
+ return 0;
}
static int
return (NULL);
return (ctx->conninfo->version);
}
+
-/* $OpenBSD: tls_internal.h,v 1.53 2017/01/29 17:52:11 beck Exp $ */
+/* $OpenBSD: tls_internal.h,v 1.54 2017/04/05 03:13:53 beck Exp $ */
/*
* Copyright (c) 2014 Jeremie Courreges-Anglas <jca@openbsd.org>
* Copyright (c) 2014 Joel Sing <jsing@openbsd.org>
size_t key_len;
char *ocsp_staple;
size_t ocsp_staple_len;
+ char *cert_hash;
};
#define TLS_MIN_SESSION_TIMEOUT (4)
int verify_depth;
int verify_name;
int verify_time;
+ int skip_private_key_check;
};
struct tls_conninfo {
int tls_ocsp_stapling_cb(SSL *ssl, void *arg);
void tls_ocsp_free(struct tls_ocsp *ctx);
struct tls_ocsp *tls_ocsp_setup_from_peer(struct tls *ctx);
+int tls_hex_string(const unsigned char *_in, size_t _inlen, char **_out,
+ size_t *_outlen);
+int tls_cert_hash(X509 *_cert, char **_hash);
__END_HIDDEN_DECLS