Switch libssl to the new SPKI parsing APIs Bug: 42290364 Change-Id: I91bc1950e5759c5267131fc0bc301104aeca7d7b Reviewed-on: https://boringssl-review.googlesource.com/c/boringssl/+/81654 Reviewed-by: Adam Langley <agl@google.com> Commit-Queue: David Benjamin <davidben@google.com>
diff --git a/ssl/internal.h b/ssl/internal.h index 4a442e4..18e2494 100644 --- a/ssl/internal.h +++ b/ssl/internal.h
@@ -878,6 +878,12 @@ size_t max_out, Span<const uint8_t> in); +// ssl_parse_peer_subject_public_key_info decodes a SubjectPublicKeyInfo +// representing the peer TLS key. It returns a newly-allocated |EVP_PKEY| or +// nullptr on error. +bssl::UniquePtr<EVP_PKEY> ssl_parse_peer_subject_public_key_info( + Span<const uint8_t> spki); + // ssl_pkey_supports_algorithm returns whether |pkey| may be used to sign // |sigalg|. bool ssl_pkey_supports_algorithm(const SSL *ssl, EVP_PKEY *pkey,
diff --git a/ssl/ssl_cert.cc b/ssl/ssl_cert.cc index c0d510b..3be7d14 100644 --- a/ssl/ssl_cert.cc +++ b/ssl/ssl_cert.cc
@@ -262,13 +262,14 @@ } UniquePtr<EVP_PKEY> ssl_cert_parse_pubkey(const CBS *in) { - CBS buf = *in, tbs_cert; - if (!ssl_cert_skip_to_spki(&buf, &tbs_cert)) { + CBS buf = *in, tbs_cert, spki; + if (!ssl_cert_skip_to_spki(&buf, &tbs_cert) || + !CBS_get_asn1_element(&tbs_cert, &spki, CBS_ASN1_SEQUENCE)) { OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT); return nullptr; } - return UniquePtr<EVP_PKEY>(EVP_parse_public_key(&tbs_cert)); + return ssl_parse_peer_subject_public_key_info(spki); } bool ssl_compare_public_and_private_key(const EVP_PKEY *pubkey,
diff --git a/ssl/ssl_credential.cc b/ssl/ssl_credential.cc index 95c1a76..bbbd767 100644 --- a/ssl/ssl_credential.cc +++ b/ssl/ssl_credential.cc
@@ -428,9 +428,8 @@ return 0; } - UniquePtr<EVP_PKEY> pubkey(EVP_parse_public_key(&spki)); - if (pubkey == nullptr || CBS_len(&spki) != 0) { - OPENSSL_PUT_ERROR(SSL, SSL_R_DECODE_ERROR); + UniquePtr<EVP_PKEY> pubkey = ssl_parse_peer_subject_public_key_info(spki); + if (pubkey == nullptr) { return 0; }
diff --git a/ssl/ssl_privkey.cc b/ssl/ssl_privkey.cc index 8e54853..5db3dc6 100644 --- a/ssl/ssl_privkey.cc +++ b/ssl/ssl_privkey.cc
@@ -109,6 +109,19 @@ return NULL; } +bssl::UniquePtr<EVP_PKEY> ssl_parse_peer_subject_public_key_info( + Span<const uint8_t> spki) { + // Ideally the set of reachable algorithms would flow from |SSL_CTX| for dead + // code elimination, but for now we just specify every algorithm that might be + // reachable from libssl. + const EVP_PKEY_ALG *const algs[] = { + EVP_pkey_rsa(), EVP_pkey_ec_p256(), EVP_pkey_ec_p384(), + EVP_pkey_ec_p521(), EVP_pkey_ed25519(), + }; + return bssl::UniquePtr<EVP_PKEY>(EVP_PKEY_from_subject_public_key_info( + spki.data(), spki.size(), algs, std::size(algs))); +} + bool ssl_pkey_supports_algorithm(const SSL *ssl, EVP_PKEY *pkey, uint16_t sigalg, bool is_verify) { const SSL_SIGNATURE_ALGORITHM *alg = get_signature_algorithm(sigalg);