diff options
author | Laurent Bercot <ska-skaware@skarnet.org> | 2021-05-20 10:55:18 +0000 |
---|---|---|
committer | Laurent Bercot <ska-skaware@skarnet.org> | 2021-05-20 10:55:18 +0000 |
commit | 4aae040b1a8aecddcd0e1e959c77bb262fe6b850 (patch) | |
tree | 37c985cc6ff250ec486c3eaa09428eb5bf08cdb2 /src | |
parent | 6780eee3e0dbe37640f72ed1e37a95c506e23f8c (diff) | |
download | s6-networking-4aae040b1a8aecddcd0e1e959c77bb262fe6b850.tar.xz |
Add an x509 engine wrapping minimal. NOT FUNCTIONAL, FOR TESTING.
Diffstat (limited to 'src')
-rw-r--r-- | src/include/s6-networking/sbearssl.h | 54 | ||||
-rw-r--r-- | src/sbearssl/deps-lib/sbearssl | 3 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_client_init_and_run.c | 20 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_run.c | 6 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_send_environment.c | 118 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_server_init_and_run.c | 13 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_x509_minimal_init_with_engine.c | 25 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_x509_minimal_set_tai.c | 2 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_x509_small_init_full.c | 40 | ||||
-rw-r--r-- | src/sbearssl/sbearssl_x509_small_vtable.c | 79 | ||||
-rw-r--r-- | src/tls/s6-tlsc-io.c | 8 | ||||
-rw-r--r-- | src/tls/s6-tlsd-io.c | 8 |
12 files changed, 310 insertions, 66 deletions
diff --git a/src/include/s6-networking/sbearssl.h b/src/include/s6-networking/sbearssl.h index e473e12..6a0f67a 100644 --- a/src/include/s6-networking/sbearssl.h +++ b/src/include/s6-networking/sbearssl.h @@ -32,11 +32,40 @@ extern int sbearssl_isder (unsigned char const *, size_t) ; - /* x509 QoL functions */ + /* x509 functions */ + +typedef struct sbearssl_dn_s sbearssl_dn, *sbearssl_dn_ref ; +struct sbearssl_dn_s +{ + char c[3] ; + char st[129] ; + char l[129] ; + char o[65] ; + char ou[65] ; + char cn[65] ; +} ; +#define SBEARSSL_DN_ZERO { .c = "", .st = "", .l = "", .o = "", .ou = "", .cn = "" } + +typedef struct sbearssl_x509_small_context_s sbearssl_x509_small_context, *sbearssl_x509_small_context_ref ; +struct sbearssl_x509_small_context_s +{ + br_x509_class const *vtable ; + br_x509_minimal_context minimal ; + br_sha256_context hashctx ; + unsigned int i ; + br_name_element elts[6] ; + sbearssl_dn *eedn ; + uint8_t *eltstatus ; + char *eehash ; +} ; extern int sbearssl_x509_minimal_set_tai (br_x509_minimal_context *, tai_t const *) ; #define sbearssl_x509_minimal_set_tain(ctx, a) sbearssl_x509_minimal_set_tai(ctx, tain_secp(a)) -extern void sbearssl_x509_minimal_init_with_engine (br_x509_minimal_context *, br_ssl_engine_context *, br_x509_trust_anchor const *, size_t) ; +#define sbearssl_x509_small_set_tai(ctx, t) sbearssl_x509_minimal_set_tai(&(ctx)->minimal, t) +#define sbearssl_x509_small_set_tain(ctx, a) sbearssl_x509_small_set_tai(ctx, tain_secp(a)) + +extern br_x509_class const sbearssl_x509_small_vtable ; +extern void sbearssl_x509_small_init_full (sbearssl_x509_small_context *, br_x509_trust_anchor *, size_t, sbearssl_dn *, uint8_t *, char *) ; /* Cipher suites */ @@ -216,22 +245,27 @@ extern char const *sbearssl_error_str (int) ; /* Engine */ -typedef struct sbearssl_handshake_cb_context_s sbearssl_handshake_cb_context_t, *sbearssl_handshake_cb_context_t_ref ; -struct sbearssl_handshake_cb_context_s +typedef struct sbearssl_handshake_cbarg_s sbearssl_handshake_cbarg, *sbearssl_handshake_cbarg_ref ; +struct sbearssl_handshake_cbarg_s { unsigned int notif ; + sbearssl_dn eedn ; + char eehash[32] ; + uint8_t eltstatus ; + uint8_t exportmask ; } ; +#define SBEARSSL_HANDSHAKE_CBARG_ZERO { .notif = 0, .eedn = SBEARSSL_DN_ZERO, .eehash = { 0 }, .eltstatus = 0, .exportmask = 0 } -typedef int sbearssl_handshake_cb_t (br_ssl_engine_context *, sbearssl_handshake_cb_context_t *) ; -typedef sbearssl_handshake_cb_t *sbearssl_handshake_cb_t_ref ; +typedef int sbearssl_handshake_cbfunc (br_ssl_engine_context *, sbearssl_handshake_cbarg *) ; +typedef sbearssl_handshake_cbfunc *sbearssl_handshake_cbfunc_ref ; -extern int sbearssl_send_environment (br_ssl_engine_context *, int) ; -extern void sbearssl_run (br_ssl_engine_context *, int *, tain_t const *, uint32_t, unsigned int, sbearssl_handshake_cb_t_ref, sbearssl_handshake_cb_context_t *) gccattr_noreturn ; +extern int sbearssl_send_environment (br_ssl_engine_context *, sbearssl_handshake_cbarg *) ; +extern void sbearssl_run (br_ssl_engine_context *, int *, tain_t const *, uint32_t, unsigned int, sbearssl_handshake_cbfunc_ref, sbearssl_handshake_cbarg *) gccattr_noreturn ; /* s6-tlsc-io and s6-tlsd-io implementations */ -extern void sbearssl_client_init_and_run (int *, tain_t const *, uint32_t, uint32_t, unsigned int, char const *, sbearssl_handshake_cb_t_ref, unsigned int) gccattr_noreturn ; -extern void sbearssl_server_init_and_run (int *, tain_t const *, uint32_t, uint32_t, unsigned int, sbearssl_handshake_cb_t_ref, unsigned int) gccattr_noreturn ; +extern void sbearssl_client_init_and_run (int *, tain_t const *, uint32_t, uint32_t, unsigned int, char const *, sbearssl_handshake_cbfunc_ref, sbearssl_handshake_cbarg *) gccattr_noreturn ; +extern void sbearssl_server_init_and_run (int *, tain_t const *, uint32_t, uint32_t, unsigned int, sbearssl_handshake_cbfunc_ref, sbearssl_handshake_cbarg *) gccattr_noreturn ; #endif diff --git a/src/sbearssl/deps-lib/sbearssl b/src/sbearssl/deps-lib/sbearssl index a1ccbb7..68b3ce1 100644 --- a/src/sbearssl/deps-lib/sbearssl +++ b/src/sbearssl/deps-lib/sbearssl @@ -40,7 +40,8 @@ sbearssl_ta_readfile.o sbearssl_ta_to.o sbearssl_x500_name_len.o sbearssl_x500_from_ta.o -sbearssl_x509_minimal_init_with_engine.o sbearssl_x509_minimal_set_tai.o +sbearssl_x509_small_init_full.o +sbearssl_x509_small_vtable.o -lbearssl -lskarnet diff --git a/src/sbearssl/sbearssl_client_init_and_run.c b/src/sbearssl/sbearssl_client_init_and_run.c index db68096..e139820 100644 --- a/src/sbearssl/sbearssl_client_init_and_run.c +++ b/src/sbearssl/sbearssl_client_init_and_run.c @@ -13,7 +13,7 @@ #include <s6-networking/sbearssl.h> #include "sbearssl-internal.h" -void sbearssl_client_init_and_run (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, char const *servername, sbearssl_handshake_cb_t_ref cb, unsigned int notif) +void sbearssl_client_init_and_run (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, char const *servername, sbearssl_handshake_cbfunc_ref cb, sbearssl_handshake_cbarg *cbarg) { sbearssl_skey skey ; genalloc certs = GENALLOC_ZERO ; /* sbearssl_cert */ @@ -26,10 +26,9 @@ void sbearssl_client_init_and_run (int *fds, tain_t const *tto, uint32_t preopti stralloc_shrink(&storage) ; { - sbearssl_handshake_cb_context_t cbarg = { .notif = notif } ; union br_skey_u key ; br_ssl_client_context cc ; - br_x509_minimal_context xc ; + sbearssl_x509_small_context xc ; br_x509_certificate chain[chainlen ? chainlen : 1] ; br_x509_trust_anchor btas[n] ; unsigned char buf[BR_SSL_BUFSIZE_BIDI] ; @@ -41,8 +40,15 @@ void sbearssl_client_init_and_run (int *fds, tain_t const *tto, uint32_t preopti for (size_t i = 0 ; i < n ; i++) sbearssl_ta_to(genalloc_s(sbearssl_ta, &tas) + i, btas + i, storage.s) ; genalloc_free(sbearssl_ta, &tas) ; - - br_ssl_client_init_full(&cc, &xc, btas, n) ; + { + br_x509_minimal_context dummy ; /* wasteful but the only simple API we have */ + br_ssl_client_init_full(&cc, &dummy, btas, n) ; + } + sbearssl_x509_small_init_full(&xc, btas, n, &cbarg->eedn, &cbarg->eltstatus, cbarg->eehash) ; + if (!sbearssl_x509_small_set_tain(&xc, &STAMP)) + strerr_diefu1sys(111, "initialize validation time") ; + br_ssl_engine_set_x509(&cc.eng, &xc.vtable) ; + cbarg->exportmask |= 3 ; if (chainlen) { @@ -78,11 +84,9 @@ void sbearssl_client_init_and_run (int *fds, tain_t const *tto, uint32_t preopti random_finish() ; br_ssl_engine_inject_entropy(&cc.eng, buf, 32) ; br_ssl_engine_set_buffer(&cc.eng, buf, sizeof(buf), 1) ; - if (!sbearssl_x509_minimal_set_tain(&xc, &STAMP)) - strerr_diefu1sys(111, "initialize validation time") ; if (!br_ssl_client_reset(&cc, servername, 0)) strerr_diefu2x(97, "reset client context: ", sbearssl_error_str(br_ssl_engine_last_error(&cc.eng))) ; - sbearssl_run(&cc.eng, fds, tto, options, verbosity, cb, &cbarg) ; + sbearssl_run(&cc.eng, fds, tto, options, verbosity, cb, cbarg) ; } } diff --git a/src/sbearssl/sbearssl_run.c b/src/sbearssl/sbearssl_run.c index fda9f3e..c440060 100644 --- a/src/sbearssl/sbearssl_run.c +++ b/src/sbearssl/sbearssl_run.c @@ -11,10 +11,12 @@ #include <skalibs/iopause.h> #include <skalibs/djbunix.h> +#include <skalibs/lolstdio.h> + #include <s6-networking/sbearssl.h> #include "sbearssl-internal.h" -void sbearssl_run (br_ssl_engine_context *ctx, int *fds, tain_t const *tto, uint32_t options, unsigned int verbosity, sbearssl_handshake_cb_t_ref cb, sbearssl_handshake_cb_context_t *cbarg) +void sbearssl_run (br_ssl_engine_context *ctx, int *fds, tain_t const *tto, uint32_t options, unsigned int verbosity, sbearssl_handshake_cbfunc_ref cb, sbearssl_handshake_cbarg *cbarg) { iopause_fd x[4] ; unsigned int xindex[4] ; @@ -27,6 +29,7 @@ void sbearssl_run (br_ssl_engine_context *ctx, int *fds, tain_t const *tto, uint || ndelay_on(fds[3]) < 0) strerr_diefu1sys(111, "set fds non-blocking") ; + LOLDEBUG("entering engine") ; for (;;) { tain_t deadline = TAIN_INFINITE ; @@ -48,6 +51,7 @@ void sbearssl_run (br_ssl_engine_context *ctx, int *fds, tain_t const *tto, uint xindex[0] = j++ ; if (!handshake_done) { + LOLDEBUG("handshake done, calling cb") ; if (!(*cb)(ctx, cbarg)) strerr_diefu1sys(111, "post-handshake callback failed") ; handshake_done = 1 ; diff --git a/src/sbearssl/sbearssl_send_environment.c b/src/sbearssl/sbearssl_send_environment.c index bb0fb35..a998ee9 100644 --- a/src/sbearssl/sbearssl_send_environment.c +++ b/src/sbearssl/sbearssl_send_environment.c @@ -1,21 +1,98 @@ /* ISC license. */ +#include <stddef.h> +#include <stdint.h> + #include <skalibs/bytestr.h> #include <skalibs/buffer.h> +#include <skalibs/fmtscan.h> #include <bearssl.h> #include <s6-networking/sbearssl.h> -int sbearssl_send_environment (br_ssl_engine_context *ctx, int fd) +static uint8_t class (char c) +{ + switch (c) + { + case '\0' : return 0 ; + case ' ' : return 1 ; + case ',' : + case '=' : + case '\n' : + case '+' : + case '<' : + case '>' : + case '#' : + case '\\' : return 2 ; + default : return 3 ; + } +} + +static int print_element (buffer *b, char const *s) +{ + static uint8_t const table[3][4] = + { + { 0x03, 0x00, 0x19, 0x09 }, + { 0x03, 0x62, 0x19, 0x09 }, + { 0x03, 0x42, 0x99, 0x89 } + } ; + size_t counter = 0 ; + uint8_t state = 0 ; + while (state < 3) + { + char ch = *s++ ; + uint8_t c = table[state][class(ch)] ; + state = c & 3 ; + if (c & 0x10) if (buffer_put(b, "\\", 1) < 0) return 0 ; + if (c & 0x20) counter = 0 ; + if (c & 0x40) counter++ ; + if (c & 0x80) while (counter--) if (buffer_put(b, " ", 1) < 0) return 0 ; + if (c & 0x08) if (buffer_put(b, &ch, 1) < 0) return 0 ; + } + return 1 ; +} + +struct eltinfo_s +{ + char const *keyword ; + size_t offset ; +} ; + + +static int print_dn (buffer *b, sbearssl_dn const *dn, uint8_t eltstatus) +{ + static struct eltinfo_s const eltinfo[6] = + { + { .keyword = "C", .offset = offsetof(sbearssl_dn, c) }, + { .keyword = "ST", .offset = offsetof(sbearssl_dn, st) }, + { .keyword = "L", .offset = offsetof(sbearssl_dn, l) }, + { .keyword = "O", .offset = offsetof(sbearssl_dn, o) }, + { .keyword = "OU", .offset = offsetof(sbearssl_dn, ou) }, + { .keyword = "CN", .offset = offsetof(sbearssl_dn, cn) } + } ; + int got = 0 ; + unsigned int mask = 1 ; + for (unsigned int i = 0 ; i < 6 ; i++, mask <<= 1) if (eltstatus & mask) + { + if ((got && buffer_puts(b, ", ") < 0) + || buffer_puts(b, eltinfo[i].keyword) < 0 + || buffer_put(b, "=", 1) < 0 + || !print_element(b, (char const *)dn + eltinfo[i].offset)) + return 0 ; + got = 1 ; + } + return 1 ; +} + +int sbearssl_send_environment (br_ssl_engine_context *ctx, sbearssl_handshake_cbarg *p) { char buf[4096] ; - buffer b = BUFFER_INIT(&buffer_write, fd, buf, 4096) ; + buffer b = BUFFER_INIT(&buffer_write, p->notif, buf, 4096) ; unsigned int v = br_ssl_engine_get_version(ctx) ; char const *name = br_ssl_engine_get_server_name(ctx) ; char const *suite ; br_ssl_session_parameters params ; - br_ssl_engine_get_session_parameters(ctx, ¶ms) ; suite = sbearssl_suite_name(¶ms) ; byte_zzero((char *)params.master_secret, 48) ; @@ -26,16 +103,39 @@ int sbearssl_send_environment (br_ssl_engine_context *ctx, int fd) || buffer_put(&b, "", 1) < 0 || buffer_puts(&b, "SSL_CIPHER=") < 0 || buffer_puts(&b, suite) < 0 - || buffer_put(&b, "", 1) < 0 - || buffer_puts(&b, "SSL_TLS_SNI_SERVERNAME") < 0) - return 0 ; + || buffer_put(&b, "", 1) < 0) return 0 ; + + if (buffer_puts(&b, "SSL_TLS_SNI_SERVERNAME") < 0) return 0 ; if (name[0]) { if (buffer_put(&b, "=", 1) < 0 || buffer_puts(&b, name) < 0) return 0 ; } - if (buffer_putflush(&b, "\0", 2) < 0) - return 0 ; - return 1 ; + if (buffer_put(&b, "", 1) < 0) return 0 ; + + if (buffer_puts(&b, "SSL_PEER_CERT_HASH") < 0) return 0 ; + if (p->exportmask & 1) + { + char eehash[64] ; + ucharn_fmt(eehash, p->eehash, 32) ; + if (buffer_puts(&b, "=SHA256:") < 0 + || buffer_put(&b, eehash, 64) < 0) + return 0 ; + } + if (buffer_put(&b, "", 1) < 0) return 0 ; + + if (buffer_puts(&b, "SSL_PEER_CERT_SUBJECT") < 0) return 0 ; + if (p->exportmask & 2 && p->eltstatus) + { + if (buffer_put(&b, "=", 1) < 0) return 0 ; + if (p->eltstatus & 128) + { + if (buffer_puts(&b, "<invalid>") < 0) return 0 ; + } + else if (!print_dn(&b, &p->eedn, p->eltstatus)) return 0 ; + } + if (buffer_put(&b, "", 1) < 0) return 0 ; + + return buffer_putflush(&b, "\0", 2) >= 0 ; } diff --git a/src/sbearssl/sbearssl_server_init_and_run.c b/src/sbearssl/sbearssl_server_init_and_run.c index e6df30e..428efb8 100644 --- a/src/sbearssl/sbearssl_server_init_and_run.c +++ b/src/sbearssl/sbearssl_server_init_and_run.c @@ -13,7 +13,7 @@ #include <s6-networking/sbearssl.h> #include "sbearssl-internal.h" -void sbearssl_server_init_and_run (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, sbearssl_handshake_cb_t_ref cb, unsigned int notif) +void sbearssl_server_init_and_run (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, sbearssl_handshake_cbfunc_ref cb, sbearssl_handshake_cbarg *cbarg) { sbearssl_skey skey ; genalloc certs = GENALLOC_ZERO ; /* sbearssl_cert */ @@ -26,10 +26,9 @@ void sbearssl_server_init_and_run (int *fds, tain_t const *tto, uint32_t preopti stralloc_shrink(&storage) ; { - sbearssl_handshake_cb_context_t cbarg = { .notif = notif } ; union br_skey_u key ; br_ssl_server_context sc ; - br_x509_minimal_context xc ; + sbearssl_x509_small_context xc ; br_x509_certificate chain[chainlen] ; br_x509_trust_anchor btas[n ? n : 1] ; unsigned char buf[BR_SSL_BUFSIZE_BIDI] ; @@ -75,10 +74,12 @@ void sbearssl_server_init_and_run (int *fds, tain_t const *tto, uint32_t preopti if (n) { - sbearssl_x509_minimal_init_with_engine(&xc, &sc.eng, btas, n) ; - if (!sbearssl_x509_minimal_set_tain(&xc, &STAMP)) + sbearssl_x509_small_init_full(&xc, btas, n, &cbarg->eedn, &cbarg->eltstatus, cbarg->eehash) ; + if (!sbearssl_x509_small_set_tain(&xc, &STAMP)) strerr_diefu1sys(111, "initialize validation time") ; + br_ssl_engine_set_x509(&sc.eng, &xc.vtable) ; br_ssl_server_set_trust_anchor_names_alt(&sc, btas, n) ; + cbarg->exportmask |= 3 ; } random_string((char *)buf, 32) ; @@ -88,6 +89,6 @@ void sbearssl_server_init_and_run (int *fds, tain_t const *tto, uint32_t preopti if (!br_ssl_server_reset(&sc)) strerr_diefu2x(97, "reset server context: ", sbearssl_error_str(br_ssl_engine_last_error(&sc.eng))) ; - sbearssl_run(&sc.eng, fds, tto, options, verbosity, cb, &cbarg) ; + sbearssl_run(&sc.eng, fds, tto, options, verbosity, cb, cbarg) ; } } diff --git a/src/sbearssl/sbearssl_x509_minimal_init_with_engine.c b/src/sbearssl/sbearssl_x509_minimal_init_with_engine.c deleted file mode 100644 index 1b5c7a5..0000000 --- a/src/sbearssl/sbearssl_x509_minimal_init_with_engine.c +++ /dev/null @@ -1,25 +0,0 @@ -/* ISC license. */ - -#include <bearssl.h> - -#include <s6-networking/sbearssl.h> - -void sbearssl_x509_minimal_init_with_engine (br_x509_minimal_context *xc, br_ssl_engine_context *eng, br_x509_trust_anchor const *btas, size_t n) -{ - static const br_hash_class *hashes[] = - { - &br_md5_vtable, - &br_sha1_vtable, - &br_sha224_vtable, - &br_sha256_vtable, - &br_sha384_vtable, - &br_sha512_vtable - } ; - - br_x509_minimal_init(xc, &br_sha256_vtable, btas, n) ; - br_x509_minimal_set_rsa(xc, br_ssl_engine_get_rsavrfy(eng)) ; - br_x509_minimal_set_ecdsa(xc, br_ssl_engine_get_ec(eng), br_ssl_engine_get_ecdsa(eng)) ; - for (unsigned int id = br_md5_ID ; id <= br_sha512_ID ; id++) - br_x509_minimal_set_hash(xc, id, hashes[id-1]) ; - br_ssl_engine_set_x509(eng, &xc->vtable) ; -} diff --git a/src/sbearssl/sbearssl_x509_minimal_set_tai.c b/src/sbearssl/sbearssl_x509_minimal_set_tai.c index 1d9de2a..381e9d3 100644 --- a/src/sbearssl/sbearssl_x509_minimal_set_tai.c +++ b/src/sbearssl/sbearssl_x509_minimal_set_tai.c @@ -1,9 +1,11 @@ /* ISC license. */ #include <bearssl.h> + #include <skalibs/uint64.h> #include <skalibs/tai.h> #include <skalibs/djbtime.h> + #include <s6-networking/sbearssl.h> int sbearssl_x509_minimal_set_tai (br_x509_minimal_context *ctx, tai_t const *t) diff --git a/src/sbearssl/sbearssl_x509_small_init_full.c b/src/sbearssl/sbearssl_x509_small_init_full.c new file mode 100644 index 0000000..31906e5 --- /dev/null +++ b/src/sbearssl/sbearssl_x509_small_init_full.c @@ -0,0 +1,40 @@ +/* ISC license. */ + +#include <stddef.h> +#include <stdint.h> + +#include <bearssl.h> + +#include <s6-networking/sbearssl.h> + +struct eltinfo_s +{ + size_t offset ; + size_t size ; + unsigned char oid[4] ; +} ; + +static struct eltinfo_s const eltinfo[6] = +{ + { .offset = offsetof(sbearssl_dn, c), .size = sizeof(((sbearssl_dn *)0)->c), .oid = "\x03\x55\x04\x06" }, + { .offset = offsetof(sbearssl_dn, st), .size = sizeof(((sbearssl_dn *)0)->st), .oid = "\x03\x55\x04\x08" }, + { .offset = offsetof(sbearssl_dn, l), .size = sizeof(((sbearssl_dn *)0)->l), .oid = "\x03\x55\x04\x07" }, + { .offset = offsetof(sbearssl_dn, o), .size = sizeof(((sbearssl_dn *)0)->o), .oid = "\x03\x55\x04\x0a" }, + { .offset = offsetof(sbearssl_dn, ou), .size = sizeof(((sbearssl_dn *)0)->ou), .oid = "\x03\x55\x04\x0b" }, + { .offset = offsetof(sbearssl_dn, cn), .size = sizeof(((sbearssl_dn *)0)->cn), .oid = "\x03\x55\x04\x03" } +} ; + +void sbearssl_x509_small_init_full (sbearssl_x509_small_context *ctx, br_x509_trust_anchor *btas, size_t n, sbearssl_dn *eedn, uint8_t *eltstatus, char *eehash) +{ + ctx->vtable = &sbearssl_x509_small_vtable ; + br_x509_minimal_init_full(&ctx->minimal, btas, n) ; + for (unsigned int i = 0 ; i < 6 ; i++) + { + ctx->elts[i].oid = eltinfo[i].oid ; + ctx->elts[i].buf = (char *)ctx->eedn + eltinfo[i].offset ; + ctx->elts[i].len = eltinfo[i].size ; + } + br_x509_minimal_set_name_elements(&ctx->minimal, ctx->elts, 6) ; + ctx->eltstatus = eltstatus ; + ctx->eehash = eehash ; +} diff --git a/src/sbearssl/sbearssl_x509_small_vtable.c b/src/sbearssl/sbearssl_x509_small_vtable.c new file mode 100644 index 0000000..9946e7a --- /dev/null +++ b/src/sbearssl/sbearssl_x509_small_vtable.c @@ -0,0 +1,79 @@ +/* ISC license. */ + +#include <skalibs/lolstdio.h> + +#include <bearssl.h> + +#include <s6-networking/sbearssl.h> + +#define INSTANCE(c) ((sbearssl_x509_small_context *)(c)) + +static void start_chain (br_x509_class const **c, char const *server_name) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + ctx->minimal.vtable->start_chain(&ctx->minimal.vtable, server_name) ; + + LOLDEBUG("small_context: start_chain") ; + ctx->i = 0 ; +} + +static void start_cert (br_x509_class const **c, uint32_t len) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + ctx->minimal.vtable->start_cert(&ctx->minimal.vtable, len) ; + + LOLDEBUG("small_context: start_cert %u", ctx->i) ; + if (!ctx->i) br_sha256_init(&ctx->hashctx) ; +} + +static void append (br_x509_class const **c, unsigned char const *s, size_t len) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + ctx->minimal.vtable->append(&ctx->minimal.vtable, s, len) ; + + LOLDEBUG("small_context: append") ; + if (!ctx->i) br_sha256_update(&ctx->hashctx, s, len) ; +} + +static void end_cert (br_x509_class const **c) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + ctx->minimal.vtable->end_cert(&ctx->minimal.vtable) ; + + LOLDEBUG("small_context: end_cert") ; + if (!ctx->i) br_sha256_out(&ctx->hashctx, ctx->eehash) ; + ctx->i++ ; +} + +static unsigned int end_chain (br_x509_class const **c) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + LOLDEBUG("small_context: end_chain") ; + unsigned int r = ctx->minimal.vtable->end_chain(&ctx->minimal.vtable) ; + if (!r) + { + uint8_t mask = 1 ; + for (unsigned int i = 0 ; i < 6 ; i++, mask <<= 1) + if (ctx->elts[i].status) + *ctx->eltstatus |= ctx->elts[i].status < 0 ? 128 : mask ; + } + return r ; +} + +static br_x509_pkey const *get_pkey(br_x509_class const *const *c, unsigned int *usages) +{ + sbearssl_x509_small_context *ctx = INSTANCE(c) ; + LOLDEBUG("small_context: get_pkey") ; + return ctx->minimal.vtable->get_pkey(&ctx->minimal.vtable, usages) ; +} + +br_x509_class const sbearssl_x509_small_vtable = +{ + .context_size = sizeof(sbearssl_x509_small_context), + .start_chain = &start_chain, + .start_cert = &start_cert, + .append = &append, + .end_cert = &end_cert, + .end_chain = &end_chain, + .get_pkey = &get_pkey, +} ; diff --git a/src/tls/s6-tlsc-io.c b/src/tls/s6-tlsc-io.c index 7c92d96..3c9df58 100644 --- a/src/tls/s6-tlsc-io.c +++ b/src/tls/s6-tlsc-io.c @@ -43,11 +43,11 @@ static inline void doit (int *fds, tain_t const *tto, uint32_t preoptions, uint3 #include <s6-networking/sbearssl.h> -static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cb_context_t *cbarg) +static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cbarg *cbarg) { if (cbarg->notif) { - if (!sbearssl_send_environment(ctx, cbarg->notif)) return 0 ; + if (!sbearssl_send_environment(ctx, cbarg)) return 0 ; fd_close(cbarg->notif) ; } return 1 ; @@ -55,8 +55,10 @@ static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cb_conte static inline void doit (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, char const *servername, unsigned int notif) { + sbearssl_handshake_cbarg cbarg = SBEARSSL_HANDSHAKE_CBARG_ZERO ; if (!random_init()) strerr_diefu1sys(111, "initialize random device") ; - sbearssl_client_init_and_run(fds, tto, preoptions, options, verbosity, servername, &handshake_cb, notif) ; + cbarg.notif = notif ; + sbearssl_client_init_and_run(fds, tto, preoptions, options, verbosity, servername, &handshake_cb, &cbarg) ; } #else diff --git a/src/tls/s6-tlsd-io.c b/src/tls/s6-tlsd-io.c index 01f0d74..060537a 100644 --- a/src/tls/s6-tlsd-io.c +++ b/src/tls/s6-tlsd-io.c @@ -41,11 +41,11 @@ static inline void doit (int *fds, tain_t const *tto, uint32_t preoptions, uint3 #include <s6-networking/sbearssl.h> -static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cb_context_t *cbarg) +static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cbarg *cbarg) { if (cbarg->notif) { - if (!sbearssl_send_environment(ctx, cbarg->notif)) return 0 ; + if (!sbearssl_send_environment(ctx, cbarg)) return 0 ; fd_close(cbarg->notif) ; } return 1 ; @@ -53,8 +53,10 @@ static int handshake_cb (br_ssl_engine_context *ctx, sbearssl_handshake_cb_conte static inline void doit (int *fds, tain_t const *tto, uint32_t preoptions, uint32_t options, unsigned int verbosity, unsigned int notif) { + sbearssl_handshake_cbarg cbarg = SBEARSSL_HANDSHAKE_CBARG_ZERO ; if (!random_init()) strerr_diefu1sys(111, "initialize random device") ; - sbearssl_server_init_and_run(fds, tto, preoptions, options, verbosity, &handshake_cb, notif) ; + cbarg.notif = notif ; + sbearssl_server_init_and_run(fds, tto, preoptions, options, verbosity, &handshake_cb, &cbarg) ; } #else |