summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTheo Buehler <tb@cvs.openbsd.org>2023-06-18 17:50:29 +0000
committerTheo Buehler <tb@cvs.openbsd.org>2023-06-18 17:50:29 +0000
commitf892509cf2ef4cc6388534aedf0d4af347cef342 (patch)
tree3f96cbc04c2af56e19d5a43cc0d139f2ae309c41
parent03e605e28e8b3cc62fecf4eec05e7f7ee4e42baa (diff)
tls_signer: reinstate the default EC_KEY methods
Previously, we would set the ECDSA_METHOD on the EC_KEY, which, by way of lovely indirection in our three crypto/ec* directories ended up having no effect on the default methods. Now that we set a new EC_KEY_METHOD, we need to make sure we still have the other handlers that we might need. Like so many things that were made opaque in the 1.1 re"design", the accessors were written without actual application code in mind. In particular, EC_KEY_METHOD lacks a dup(). This means we get to fetch the default methods with getters and then set them again on the new method. This is particularly awesome because once someone adds a new method to the opaque struct, all applications will have to adapt and do a get/set dance. So far this is very reminiscent of PostgreSQL with BIO_meth_* https://github.com/postgres/postgres/blob/a14e75eb0b6a73821e0d66c0d407372ec8376105/src/interfaces/libpq/fe-secure-openssl.c#L1921-L1928 Only it's worse here because someone wanted to be smart and save a few public functions, so we have to use getters that get several functions at once. Which in turn means we need to have function pointers with the precise signatures which are part of the struct that was made opaque. We will add a EC_KEY_METHOD_dup() in the next bump, but for now this is the best fix we can have. Whenever you think you've seen the worst turds in this code base, you find another one that could serve as an exemplar. ok jsing op
-rw-r--r--lib/libtls/tls_signer.c31
1 files changed, 29 insertions, 2 deletions
diff --git a/lib/libtls/tls_signer.c b/lib/libtls/tls_signer.c
index c1b60bfcc44..78206d1223b 100644
--- a/lib/libtls/tls_signer.c
+++ b/lib/libtls/tls_signer.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: tls_signer.c,v 1.7 2023/06/18 17:24:09 tb Exp $ */
+/* $OpenBSD: tls_signer.c,v 1.8 2023/06/18 17:50:28 tb Exp $ */
/*
* Copyright (c) 2021 Eric Faurot <eric@openbsd.org>
*
@@ -423,6 +423,20 @@ EC_KEY_METHOD *
tls_signer_ecdsa_method(void)
{
static EC_KEY_METHOD *ecdsa_method = NULL;
+ const EC_KEY_METHOD *default_method;
+ int (*keygen)(EC_KEY *key);
+ int (*compute_key)(void *out, size_t outlen, const EC_POINT *pub_key,
+ EC_KEY *ecdh, void *(*KDF) (const void *in, size_t inlen, void *out,
+ size_t *outlen));
+ int (*sign)(int type, const unsigned char *dgst, int dlen,
+ unsigned char *sig, unsigned int *siglen,
+ const BIGNUM *kinv, const BIGNUM *r, EC_KEY *eckey);
+ int (*sign_setup)(EC_KEY *eckey, BN_CTX *ctx_in,
+ BIGNUM **kinvp, BIGNUM **rp);
+ int (*verify)(int type, const unsigned char *dgst, int dgst_len,
+ const unsigned char *sigbuf, int sig_len, EC_KEY *eckey);
+ int (*verify_sig)(const unsigned char *dgst, int dgst_len,
+ const ECDSA_SIG *sig, EC_KEY *eckey);
pthread_mutex_lock(&signer_method_lock);
@@ -433,7 +447,20 @@ tls_signer_ecdsa_method(void)
if (ecdsa_method == NULL)
goto out;
- EC_KEY_METHOD_set_sign(ecdsa_method, NULL, NULL, tls_ecdsa_do_sign);
+ default_method = EC_KEY_get_default_method();
+
+ EC_KEY_METHOD_get_keygen(default_method, &keygen);
+ EC_KEY_METHOD_set_keygen(ecdsa_method, keygen);
+
+ EC_KEY_METHOD_get_compute_key(default_method, &compute_key);
+ EC_KEY_METHOD_set_compute_key(ecdsa_method, compute_key);
+
+ EC_KEY_METHOD_get_sign(default_method, &sign, &sign_setup, NULL);
+ EC_KEY_METHOD_set_sign(ecdsa_method, sign, sign_setup,
+ tls_ecdsa_do_sign);
+
+ EC_KEY_METHOD_get_verify(default_method, &verify, &verify_sig);
+ EC_KEY_METHOD_set_verify(ecdsa_method, verify, verify_sig);
out:
pthread_mutex_unlock(&signer_method_lock);