From 98647e059d9dd54d6c814a67a8b8bcdf0b2c3c90 Mon Sep 17 00:00:00 2001 From: yhirose Date: Wed, 21 Oct 2026 16:41:12 -0400 Subject: [PATCH] Require client certificates once update_certs_pem() loads a client CA SSLServer::update_certs_pem() loaded the client CA it was given but left client certificate verification as it was, so on a server built without a client CA it returned true while clients without a certificate still got in. Turn verification on, as the constructors do when they are given a client CA. A client CA passed to update_certs_pem() now always makes client certificates required. --- httplib.h | 4 +++- test/test.cc | 25 +++++++++++++++++-------- 2 files changed, 20 insertions(+), 9 deletions(-) diff --git a/httplib.h b/httplib.h index 3cefcfde..40902e2e 100644 --- a/httplib.h +++ b/httplib.h @@ -18955,7 +18955,9 @@ inline bool SSLServer::update_certs_pem(const char *cert_pem, return false; } if (client_ca_pem) { - return tls::update_server_client_ca(ctx_, client_ca_pem); + if (!tls::update_server_client_ca(ctx_, client_ca_pem)) { return false; } + // As in the constructors, a client CA makes client certificates required + tls::set_verify_client(ctx_, true); } return true; } diff --git a/test/test.cc b/test/test.cc index d32001a8..639f0fd3 100644 --- a/test/test.cc +++ b/test/test.cc @@ -16221,15 +16221,24 @@ TEST(SSLClientServerTest, ClientCertStillRequiredAfterVerifyCallbackCleared) { }); } +void UpdateCertsPemWithClientCA(SSLServer &svr) { + std::string cert_pem, key_pem, ca_pem; + read_file(SERVER_CERT_FILE, cert_pem); + read_file(SERVER_PRIVATE_KEY_FILE, key_pem); + read_file(CLIENT_CA_CERT_FILE, ca_pem); + ASSERT_TRUE( + svr.update_certs_pem(cert_pem.c_str(), key_pem.c_str(), ca_pem.c_str())); +} + +TEST(SSLClientServerTest, UpdateCertsPemWithClientCARequiresClientCert) { + SSLServer svr(SERVER_CERT_FILE, SERVER_PRIVATE_KEY_FILE); + ASSERT_TRUE(svr.is_valid()); + UpdateCertsPemWithClientCA(svr); + RejectsClientWithoutCert(svr); +} + TEST(SSLClientServerTest, ClientCertStillRequiredAfterUpdateCertsPem) { - ClientCertStillRequired([](SSLServer &svr) { - std::string cert_pem, key_pem, ca_pem; - read_file(SERVER_CERT_FILE, cert_pem); - read_file(SERVER_PRIVATE_KEY_FILE, key_pem); - read_file(CLIENT_CA_CERT_FILE, ca_pem); - ASSERT_TRUE(svr.update_certs_pem(cert_pem.c_str(), key_pem.c_str(), - ca_pem.c_str())); - }); + ClientCertStillRequired(UpdateCertsPemWithClientCA); } // A TLS error from one request must not show up in a later request's Result