diff options
author | 2007-09-28 13:05:28 +0000 | |
---|---|---|
committer | 2007-09-28 13:05:28 +0000 | |
commit | da64262532382eab40c13b9a9352066098c2052f (patch) | |
tree | 59a6a25523bf61b6cd95f27c8dd41fcf383b2f67 | |
parent | sort options; (diff) | |
download | wireguard-openbsd-da64262532382eab40c13b9a9352066098c2052f.tar.xz wireguard-openbsd-da64262532382eab40c13b9a9352066098c2052f.zip |
Change the ssl_privsep code to work on char buffers.
The fd based code introduced weirdness since all children were accessing
the same fd at once. This will also greatly facilitate reloading, no
fd-passing will be involved between the parent and relay children.
While there, cleanup the code diverting from the original ssl_rsa.c code
a bit more.
Weird behavior discovery by pascoe@.
-rw-r--r-- | usr.sbin/hoststated/hoststated.h | 12 | ||||
-rw-r--r-- | usr.sbin/hoststated/relay.c | 30 | ||||
-rw-r--r-- | usr.sbin/hoststated/ssl_privsep.c | 107 | ||||
-rw-r--r-- | usr.sbin/relayd/relay.c | 30 | ||||
-rw-r--r-- | usr.sbin/relayd/relayd.h | 12 | ||||
-rw-r--r-- | usr.sbin/relayd/ssl_privsep.c | 107 |
6 files changed, 152 insertions, 146 deletions
diff --git a/usr.sbin/hoststated/hoststated.h b/usr.sbin/hoststated/hoststated.h index a93a426a0a6..94daced59f3 100644 --- a/usr.sbin/hoststated/hoststated.h +++ b/usr.sbin/hoststated/hoststated.h @@ -1,4 +1,4 @@ -/* $OpenBSD: hoststated.h,v 1.62 2007/09/27 13:34:21 pyr Exp $ */ +/* $OpenBSD: hoststated.h,v 1.63 2007/09/28 13:05:28 pyr Exp $ */ /* * Copyright (c) 2006, 2007 Pierre-Yves Ritschard <pyr@spootnik.org> @@ -524,8 +524,10 @@ struct relay_config { struct relay { TAILQ_ENTRY(relay) entry; - int cert_fd; - int key_fd; + char *ssl_cert; + off_t ssl_cert_len; + char *ssl_key; + off_t ssl_key_len; struct relay_config conf; int up; @@ -739,8 +741,8 @@ SSL_CTX *ssl_ctx_create(struct hoststated *); void ssl_error(const char *, const char *); /* ssl_privsep.c */ -int ssl_ctx_use_private_key(SSL_CTX *, int); -int ssl_ctx_use_certificate_chain(SSL_CTX *, int); +int ssl_ctx_use_private_key(SSL_CTX *, char *, off_t); +int ssl_ctx_use_certificate_chain(SSL_CTX *, char *, off_t); /* hoststated.c */ struct host *host_find(struct hoststated *, objid_t); diff --git a/usr.sbin/hoststated/relay.c b/usr.sbin/hoststated/relay.c index 8b3bd624197..45da99fff9a 100644 --- a/usr.sbin/hoststated/relay.c +++ b/usr.sbin/hoststated/relay.c @@ -1,4 +1,4 @@ -/* $OpenBSD: relay.c,v 1.46 2007/09/27 13:50:40 pyr Exp $ */ +/* $OpenBSD: relay.c,v 1.47 2007/09/28 13:05:28 pyr Exp $ */ /* * Copyright (c) 2006, 2007 Reyk Floeter <reyk@openbsd.org> @@ -19,6 +19,7 @@ #include <sys/queue.h> #include <sys/param.h> #include <sys/types.h> +#include <sys/mman.h> #include <sys/time.h> #include <sys/stat.h> #include <sys/socket.h> @@ -2016,6 +2017,8 @@ relay_dispatch_parent(int fd, short event, void * ptr) int relay_ssl_ctx_init(struct relay *rlay) { + int fd; + off_t len; char certfile[PATH_MAX]; char hbuf[sizeof("ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255")]; @@ -2025,15 +2028,29 @@ relay_ssl_ctx_init(struct relay *rlay) if (snprintf(certfile, sizeof(certfile), "/etc/ssl/%s.crt", hbuf) == -1) return -1; - if ((rlay->cert_fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + if ((fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) return -1; + if ((len = lseek(fd, 0, SEEK_END)) == -1) + return -1; + if ((rlay->ssl_cert = mmap(NULL, len, PROT_READ, MAP_FILE|MAP_PRIVATE, + fd, 0)) == MAP_FAILED) + return -1; + rlay->ssl_cert_len = len; + close(fd); log_debug("relay_ssl_ctx_init: using certificate %s", certfile); if (snprintf(certfile, sizeof(certfile), "/etc/ssl/private/%s.key", hbuf) == -1) return -1; - if ((rlay->key_fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + if ((fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + return -1; + if ((len = lseek(fd, 0, SEEK_END)) == -1) + return -1; + if ((rlay->ssl_key = mmap(NULL, len, PROT_READ, MAP_FILE|MAP_PRIVATE, + fd, 0)) == MAP_FAILED) return -1; + rlay->ssl_key_len = len; + close(fd); log_debug("relay_ssl_ctx_init: using private key %s", certfile); return (0); @@ -2077,12 +2094,15 @@ relay_ssl_ctx_create(struct relay *rlay) goto err; log_debug("relay_ssl_ctx_create: loading certificate"); - if (!ssl_ctx_use_certificate_chain(ctx, rlay->cert_fd)) + if (!ssl_ctx_use_certificate_chain(ctx, + rlay->ssl_cert, rlay->ssl_cert_len)) goto err; + munmap(rlay->ssl_cert, rlay->ssl_cert_len); log_debug("relay_ssl_ctx_create: loading private key"); - if (!ssl_ctx_use_private_key(ctx, rlay->key_fd)) + if (!ssl_ctx_use_private_key(ctx, rlay->ssl_key, rlay->ssl_key_len)) goto err; + munmap(rlay->ssl_key, rlay->ssl_key_len); if (!SSL_CTX_check_private_key(ctx)) goto err; diff --git a/usr.sbin/hoststated/ssl_privsep.c b/usr.sbin/hoststated/ssl_privsep.c index 8c01196a111..22cff346e95 100644 --- a/usr.sbin/hoststated/ssl_privsep.c +++ b/usr.sbin/hoststated/ssl_privsep.c @@ -70,29 +70,21 @@ #include <openssl/pem.h> #include <openssl/ssl.h> -int ssl_ctx_use_private_key(SSL_CTX *, int); -int ssl_ctx_use_certificate_chain(SSL_CTX *, int); +int ssl_ctx_use_private_key(SSL_CTX *, char *, off_t); +int ssl_ctx_use_certificate_chain(SSL_CTX *, char *, off_t); int -ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) +ssl_ctx_use_private_key(SSL_CTX *ctx, char *buf, off_t len) { int ret; - FILE *fp; BIO *in; EVP_PKEY *pkey; ret = 0; - pkey = NULL; - if (lseek(fd, 0, SEEK_SET) == -1) - return (ret); - if ((fp = fdopen(fd, "r")) == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_SYS_LIB); - return (ret); - } - if ((in = BIO_new_fp(fp, BIO_NOCLOSE)) == NULL) { + if ((in = BIO_new_mem_buf(buf, len)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_BUF_LIB); - goto end; + return 0; } pkey = PEM_read_bio_PrivateKey(in, NULL, @@ -100,8 +92,7 @@ ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) ctx->default_passwd_callback_userdata); if (pkey == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, - ERR_R_PEM_LIB); + SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_PEM_LIB); goto end; } ret = SSL_CTX_use_PrivateKey(ctx, pkey); @@ -109,75 +100,65 @@ ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) end: if (in != NULL) BIO_free(in); - return(ret); + return ret; } int -ssl_ctx_use_certificate_chain(SSL_CTX *ctx, int fd) +ssl_ctx_use_certificate_chain(SSL_CTX *ctx, char *buf, off_t len) { - int ret; - BIO *in; - X509 *x; - FILE *fp; + int ret; + BIO *in; + X509 *x; + X509 *ca; + unsigned long err; ret = 0; - x = NULL; - if (lseek(fd, 0, SEEK_SET) == -1) - return (ret); + x = ca = NULL; - if ((fp = fdopen(fd, "r")) == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_SYS_LIB); - return (ret); - } - if ((in = BIO_new_fp(fp, BIO_NOCLOSE)) == NULL) { + if ((in = BIO_new_mem_buf(buf, len)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_BUF_LIB); goto end; } - x = PEM_read_bio_X509(in, NULL, + if ((x = PEM_read_bio_X509(in, NULL, ctx->default_passwd_callback, - ctx->default_passwd_callback_userdata); - if (x == NULL) { + ctx->default_passwd_callback_userdata)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_PEM_LIB); goto end; } - ret = SSL_CTX_use_certificate(ctx, x); - if (ERR_peek_error() != 0) - ret = 0; - if (ret) { - /* If we could set up our certificate, now proceed to - * the CA certificates. - */ - X509 *ca; - int r; - unsigned long err; + if (!SSL_CTX_use_certificate(ctx, x) || ERR_peek_error() != 0) + goto end; + + /* If we could set up our certificate, now proceed to + * the CA certificates. + */ - if (ctx->extra_certs != NULL) { - sk_X509_pop_free(ctx->extra_certs, X509_free); - ctx->extra_certs = NULL; - } - - while ((ca = PEM_read_bio_X509(in, NULL, - ctx->default_passwd_callback, - ctx->default_passwd_callback_userdata)) != NULL) { - r = SSL_CTX_add_extra_chain_cert(ctx, ca); - if (!r) { - X509_free(ca); - ret = 0; - goto end; - } - } - err = ERR_peek_last_error(); - if (ERR_GET_LIB(err) == ERR_LIB_PEM && - ERR_GET_REASON(err) == PEM_R_NO_START_LINE) - ERR_clear_error(); - else - ret = 0; + if (ctx->extra_certs != NULL) { + sk_X509_pop_free(ctx->extra_certs, X509_free); + ctx->extra_certs = NULL; } + while ((ca = PEM_read_bio_X509(in, NULL, + ctx->default_passwd_callback, + ctx->default_passwd_callback_userdata)) != NULL) { + + if (!SSL_CTX_add_extra_chain_cert(ctx, ca)) + goto end; + } + + err = ERR_peek_last_error(); + if (ERR_GET_LIB(err) == ERR_LIB_PEM && + ERR_GET_REASON(err) == PEM_R_NO_START_LINE) + ERR_clear_error(); + else + goto end; + + ret = 1; end: + if (ca != NULL) + X509_free(ca); if (x != NULL) X509_free(x); if (in != NULL) diff --git a/usr.sbin/relayd/relay.c b/usr.sbin/relayd/relay.c index 8b3bd624197..45da99fff9a 100644 --- a/usr.sbin/relayd/relay.c +++ b/usr.sbin/relayd/relay.c @@ -1,4 +1,4 @@ -/* $OpenBSD: relay.c,v 1.46 2007/09/27 13:50:40 pyr Exp $ */ +/* $OpenBSD: relay.c,v 1.47 2007/09/28 13:05:28 pyr Exp $ */ /* * Copyright (c) 2006, 2007 Reyk Floeter <reyk@openbsd.org> @@ -19,6 +19,7 @@ #include <sys/queue.h> #include <sys/param.h> #include <sys/types.h> +#include <sys/mman.h> #include <sys/time.h> #include <sys/stat.h> #include <sys/socket.h> @@ -2016,6 +2017,8 @@ relay_dispatch_parent(int fd, short event, void * ptr) int relay_ssl_ctx_init(struct relay *rlay) { + int fd; + off_t len; char certfile[PATH_MAX]; char hbuf[sizeof("ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255")]; @@ -2025,15 +2028,29 @@ relay_ssl_ctx_init(struct relay *rlay) if (snprintf(certfile, sizeof(certfile), "/etc/ssl/%s.crt", hbuf) == -1) return -1; - if ((rlay->cert_fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + if ((fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) return -1; + if ((len = lseek(fd, 0, SEEK_END)) == -1) + return -1; + if ((rlay->ssl_cert = mmap(NULL, len, PROT_READ, MAP_FILE|MAP_PRIVATE, + fd, 0)) == MAP_FAILED) + return -1; + rlay->ssl_cert_len = len; + close(fd); log_debug("relay_ssl_ctx_init: using certificate %s", certfile); if (snprintf(certfile, sizeof(certfile), "/etc/ssl/private/%s.key", hbuf) == -1) return -1; - if ((rlay->key_fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + if ((fd = open(certfile, O_RDONLY|O_NONBLOCK)) == -1) + return -1; + if ((len = lseek(fd, 0, SEEK_END)) == -1) + return -1; + if ((rlay->ssl_key = mmap(NULL, len, PROT_READ, MAP_FILE|MAP_PRIVATE, + fd, 0)) == MAP_FAILED) return -1; + rlay->ssl_key_len = len; + close(fd); log_debug("relay_ssl_ctx_init: using private key %s", certfile); return (0); @@ -2077,12 +2094,15 @@ relay_ssl_ctx_create(struct relay *rlay) goto err; log_debug("relay_ssl_ctx_create: loading certificate"); - if (!ssl_ctx_use_certificate_chain(ctx, rlay->cert_fd)) + if (!ssl_ctx_use_certificate_chain(ctx, + rlay->ssl_cert, rlay->ssl_cert_len)) goto err; + munmap(rlay->ssl_cert, rlay->ssl_cert_len); log_debug("relay_ssl_ctx_create: loading private key"); - if (!ssl_ctx_use_private_key(ctx, rlay->key_fd)) + if (!ssl_ctx_use_private_key(ctx, rlay->ssl_key, rlay->ssl_key_len)) goto err; + munmap(rlay->ssl_key, rlay->ssl_key_len); if (!SSL_CTX_check_private_key(ctx)) goto err; diff --git a/usr.sbin/relayd/relayd.h b/usr.sbin/relayd/relayd.h index 5456334f7cb..f261e2a63be 100644 --- a/usr.sbin/relayd/relayd.h +++ b/usr.sbin/relayd/relayd.h @@ -1,4 +1,4 @@ -/* $OpenBSD: relayd.h,v 1.62 2007/09/27 13:34:21 pyr Exp $ */ +/* $OpenBSD: relayd.h,v 1.63 2007/09/28 13:05:28 pyr Exp $ */ /* * Copyright (c) 2006, 2007 Pierre-Yves Ritschard <pyr@spootnik.org> @@ -524,8 +524,10 @@ struct relay_config { struct relay { TAILQ_ENTRY(relay) entry; - int cert_fd; - int key_fd; + char *ssl_cert; + off_t ssl_cert_len; + char *ssl_key; + off_t ssl_key_len; struct relay_config conf; int up; @@ -739,8 +741,8 @@ SSL_CTX *ssl_ctx_create(struct hoststated *); void ssl_error(const char *, const char *); /* ssl_privsep.c */ -int ssl_ctx_use_private_key(SSL_CTX *, int); -int ssl_ctx_use_certificate_chain(SSL_CTX *, int); +int ssl_ctx_use_private_key(SSL_CTX *, char *, off_t); +int ssl_ctx_use_certificate_chain(SSL_CTX *, char *, off_t); /* hoststated.c */ struct host *host_find(struct hoststated *, objid_t); diff --git a/usr.sbin/relayd/ssl_privsep.c b/usr.sbin/relayd/ssl_privsep.c index 8c01196a111..22cff346e95 100644 --- a/usr.sbin/relayd/ssl_privsep.c +++ b/usr.sbin/relayd/ssl_privsep.c @@ -70,29 +70,21 @@ #include <openssl/pem.h> #include <openssl/ssl.h> -int ssl_ctx_use_private_key(SSL_CTX *, int); -int ssl_ctx_use_certificate_chain(SSL_CTX *, int); +int ssl_ctx_use_private_key(SSL_CTX *, char *, off_t); +int ssl_ctx_use_certificate_chain(SSL_CTX *, char *, off_t); int -ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) +ssl_ctx_use_private_key(SSL_CTX *ctx, char *buf, off_t len) { int ret; - FILE *fp; BIO *in; EVP_PKEY *pkey; ret = 0; - pkey = NULL; - if (lseek(fd, 0, SEEK_SET) == -1) - return (ret); - if ((fp = fdopen(fd, "r")) == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_SYS_LIB); - return (ret); - } - if ((in = BIO_new_fp(fp, BIO_NOCLOSE)) == NULL) { + if ((in = BIO_new_mem_buf(buf, len)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_BUF_LIB); - goto end; + return 0; } pkey = PEM_read_bio_PrivateKey(in, NULL, @@ -100,8 +92,7 @@ ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) ctx->default_passwd_callback_userdata); if (pkey == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, - ERR_R_PEM_LIB); + SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_PEM_LIB); goto end; } ret = SSL_CTX_use_PrivateKey(ctx, pkey); @@ -109,75 +100,65 @@ ssl_ctx_use_private_key(SSL_CTX *ctx, int fd) end: if (in != NULL) BIO_free(in); - return(ret); + return ret; } int -ssl_ctx_use_certificate_chain(SSL_CTX *ctx, int fd) +ssl_ctx_use_certificate_chain(SSL_CTX *ctx, char *buf, off_t len) { - int ret; - BIO *in; - X509 *x; - FILE *fp; + int ret; + BIO *in; + X509 *x; + X509 *ca; + unsigned long err; ret = 0; - x = NULL; - if (lseek(fd, 0, SEEK_SET) == -1) - return (ret); + x = ca = NULL; - if ((fp = fdopen(fd, "r")) == NULL) { - SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_SYS_LIB); - return (ret); - } - if ((in = BIO_new_fp(fp, BIO_NOCLOSE)) == NULL) { + if ((in = BIO_new_mem_buf(buf, len)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_BUF_LIB); goto end; } - x = PEM_read_bio_X509(in, NULL, + if ((x = PEM_read_bio_X509(in, NULL, ctx->default_passwd_callback, - ctx->default_passwd_callback_userdata); - if (x == NULL) { + ctx->default_passwd_callback_userdata)) == NULL) { SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_PEM_LIB); goto end; } - ret = SSL_CTX_use_certificate(ctx, x); - if (ERR_peek_error() != 0) - ret = 0; - if (ret) { - /* If we could set up our certificate, now proceed to - * the CA certificates. - */ - X509 *ca; - int r; - unsigned long err; + if (!SSL_CTX_use_certificate(ctx, x) || ERR_peek_error() != 0) + goto end; + + /* If we could set up our certificate, now proceed to + * the CA certificates. + */ - if (ctx->extra_certs != NULL) { - sk_X509_pop_free(ctx->extra_certs, X509_free); - ctx->extra_certs = NULL; - } - - while ((ca = PEM_read_bio_X509(in, NULL, - ctx->default_passwd_callback, - ctx->default_passwd_callback_userdata)) != NULL) { - r = SSL_CTX_add_extra_chain_cert(ctx, ca); - if (!r) { - X509_free(ca); - ret = 0; - goto end; - } - } - err = ERR_peek_last_error(); - if (ERR_GET_LIB(err) == ERR_LIB_PEM && - ERR_GET_REASON(err) == PEM_R_NO_START_LINE) - ERR_clear_error(); - else - ret = 0; + if (ctx->extra_certs != NULL) { + sk_X509_pop_free(ctx->extra_certs, X509_free); + ctx->extra_certs = NULL; } + while ((ca = PEM_read_bio_X509(in, NULL, + ctx->default_passwd_callback, + ctx->default_passwd_callback_userdata)) != NULL) { + + if (!SSL_CTX_add_extra_chain_cert(ctx, ca)) + goto end; + } + + err = ERR_peek_last_error(); + if (ERR_GET_LIB(err) == ERR_LIB_PEM && + ERR_GET_REASON(err) == PEM_R_NO_START_LINE) + ERR_clear_error(); + else + goto end; + + ret = 1; end: + if (ca != NULL) + X509_free(ca); if (x != NULL) X509_free(x); if (in != NULL) |