diff --git a/google/cloud/internal/openssl/ssl_ec_curves.cc b/google/cloud/internal/openssl/ssl_ec_curves.cc index 5ffcd6a50c694..de2220a067b1d 100644 --- a/google/cloud/internal/openssl/ssl_ec_curves.cc +++ b/google/cloud/internal/openssl/ssl_ec_curves.cc @@ -17,7 +17,6 @@ #include #include #include -#include #include #include #include @@ -27,14 +26,12 @@ namespace cloud { namespace rest_internal { GOOGLE_CLOUD_CPP_INLINE_NAMESPACE_BEGIN -#if OPENSSL_VERSION_NUMBER >= 0x30500000L || defined(OPENSSL_IS_BORINGSSL) +#if OPENSSL_VERSION_NUMBER >= 0x30500000L namespace { struct OpenSslDeleter { -#if OPENSSL_VERSION_NUMBER >= 0x30500000L void operator()(STACK_OF(OPENSSL_CSTRING) * ptr) { sk_OPENSSL_CSTRING_free(ptr); } -#endif void operator()(SSL_CTX* ptr) { SSL_CTX_free(ptr); } }; } // namespace @@ -56,44 +53,27 @@ std::vector AvailableCryptoGroups() { if (name != nullptr) groups.emplace_back(name); } } -#else // OPENSSL_VERSION_NUMBER < 0x30500000L - std::vector builtin_groups; +#elif defined(OPENSSL_IS_BORINGSSL) && defined(SSL_GROUP_SECP256R1) + // BoringSSL reports the names of all the TLS groups it supports. It added + // `SSL_get_all_group_names()` in the same change as the `SSL_GROUP_*` + // macros, so we use the latter to detect the former. + std::vector names(SSL_get_all_group_names(nullptr, 0)); + SSL_get_all_group_names(names.data(), names.size()); + for (char const* name : names) { + if (name != nullptr) groups.emplace_back(name); + } +#elif defined(OPENSSL_IS_BORINGSSL) + // Versions of BoringSSL without `SSL_get_all_group_names()` predate support + // for X25519MLKEM768. Returning an empty list leaves the library's default + // groups unchanged. +#else // OpenSSL < 3.5 size_t const num_curves = EC_get_builtin_curves(nullptr, 0); std::vector builtin(num_curves); EC_get_builtin_curves(builtin.data(), num_curves); for (auto const& c : builtin) { char const* name = OBJ_nid2sn(c.nid); - if (name != nullptr) builtin_groups.emplace_back(name); - } -#ifdef OPENSSL_IS_BORINGSSL - // "secp224r1" can be included in the builtin curves, but it results in a - // "CURL error [59]=Couldn't use specified SSL cipher" error. - for (auto const& curve : builtin_groups) { - if (curve == "secp224r1") continue; - groups.emplace_back(curve); - } - - // Unlike OpenSSL, BoringSSL does not provide a way to query the available - // curves, so we have to probe the library using a temporary SSL_CTX. - std::array constexpr kCandidates{ - "X25519", - "X25519MLKEM768", - "X25519Kyber768Draft00", - }; - - auto ctx = - std::unique_ptr(SSL_CTX_new(TLS_method())); - if (!ctx) return groups; - for (auto const& curve : kCandidates) { - // SSL_CTX_set1_curves_list returns 1 if the curve(s) are - // recognized/supported - if (SSL_CTX_set1_curves_list(ctx.get(), curve.data()) == 1) { - groups.emplace_back(curve); - } + if (name != nullptr) groups.emplace_back(name); } -#else - groups = std::move(builtin_groups); -#endif // OPENSSL_IS_BORINGSSL #endif // OPENSSL_VERSION_NUMBER >= 0x30500000L return groups; }