diff options
author | lloyd <[email protected]> | 2012-09-07 19:40:54 +0000 |
---|---|---|
committer | lloyd <[email protected]> | 2012-09-07 19:40:54 +0000 |
commit | 4f1d7f4a08201b6495dae63af5f96d36687bff6e (patch) | |
tree | a382819aca1284106768678c1297d1ebf4508f3d | |
parent | 3a05ab962a7bb4fe4ecb19ac2972f76ac6756b09 (diff) |
Save the peer public key in the handshake state instead of pulling it
out of the cert repeatedly.
-rw-r--r-- | src/tls/msg_cert_verify.cpp | 4 | ||||
-rw-r--r-- | src/tls/msg_server_kex.cpp | 10 | ||||
-rw-r--r-- | src/tls/tls_client.cpp | 17 | ||||
-rw-r--r-- | src/tls/tls_handshake_state.cpp | 8 | ||||
-rw-r--r-- | src/tls/tls_handshake_state.h | 4 | ||||
-rw-r--r-- | src/tls/tls_messages.h | 2 |
6 files changed, 29 insertions, 16 deletions
diff --git a/src/tls/msg_cert_verify.cpp b/src/tls/msg_cert_verify.cpp index 18d851e53..8cdadfe7d 100644 --- a/src/tls/msg_cert_verify.cpp +++ b/src/tls/msg_cert_verify.cpp @@ -28,7 +28,7 @@ Certificate_Verify::Certificate_Verify(Handshake_IO& io, BOTAN_ASSERT_NONNULL(priv_key); std::pair<std::string, Signature_Format> format = - state.choose_sig_format(priv_key, m_hash_algo, m_sig_algo, true, policy); + state.choose_sig_format(*priv_key, m_hash_algo, m_sig_algo, true, policy); PK_Signer signer(*priv_key, format.first, format.second); @@ -97,7 +97,7 @@ bool Certificate_Verify::verify(const X509_Certificate& cert, std::unique_ptr<Public_Key> key(cert.subject_public_key()); std::pair<std::string, Signature_Format> format = - state.understand_sig_format(key.get(), m_hash_algo, m_sig_algo, true); + state.understand_sig_format(*key.get(), m_hash_algo, m_sig_algo, true); PK_Verifier verifier(*key, format.first, format.second); diff --git a/src/tls/msg_server_kex.cpp b/src/tls/msg_server_kex.cpp index 250a8c126..de50080ec 100644 --- a/src/tls/msg_server_kex.cpp +++ b/src/tls/msg_server_kex.cpp @@ -125,7 +125,7 @@ Server_Key_Exchange::Server_Key_Exchange(Handshake_IO& io, BOTAN_ASSERT(signing_key, "Signing key was set"); std::pair<std::string, Signature_Format> format = - state.choose_sig_format(signing_key, m_hash_algo, m_sig_algo, false, policy); + state.choose_sig_format(*signing_key, m_hash_algo, m_sig_algo, false, policy); PK_Signer signer(*signing_key, format.first, format.second); @@ -254,15 +254,13 @@ std::vector<byte> Server_Key_Exchange::serialize() const /** * Verify a Server Key Exchange message */ -bool Server_Key_Exchange::verify(const X509_Certificate& cert, +bool Server_Key_Exchange::verify(const Public_Key& server_key, const Handshake_State& state) const { - std::unique_ptr<Public_Key> key(cert.subject_public_key()); - std::pair<std::string, Signature_Format> format = - state.understand_sig_format(key.get(), m_hash_algo, m_sig_algo, false); + state.understand_sig_format(server_key, m_hash_algo, m_sig_algo, false); - PK_Verifier verifier(*key, format.first, format.second); + PK_Verifier verifier(server_key, format.first, format.second); verifier.update(state.client_hello()->random()); verifier.update(state.server_hello()->random()); diff --git a/src/tls/tls_client.cpp b/src/tls/tls_client.cpp index eac8e263b..ec1c40549 100644 --- a/src/tls/tls_client.cpp +++ b/src/tls/tls_client.cpp @@ -9,6 +9,7 @@ #include <botan/internal/tls_handshake_state.h> #include <botan/internal/tls_messages.h> #include <botan/internal/stl_util.h> +#include <botan/internal/assert.h> #include <memory> namespace Botan { @@ -27,9 +28,17 @@ class Client_Handshake_State : public Handshake_State std::function<void (const Handshake_Message&)>()) : Handshake_State(io, msg_callback) {} + const Public_Key& get_server_public_Key() const + { + BOTAN_ASSERT(server_public_key, "Server sent us a certificate"); + return *server_public_key.get(); + } + // Used during session resumption secure_vector<byte> resume_master_secret; + std::unique_ptr<Public_Key> server_public_key; + // Used by client using NPN std::function<std::string (std::vector<std::string>)> client_npn_cb; }; @@ -328,6 +337,9 @@ void Client::process_handshake_msg(const Handshake_State* /*active_state*/, if(peer_key->algo_name() != state.ciphersuite().sig_algo()) throw TLS_Exception(Alert::ILLEGAL_PARAMETER, "Certificate key type did not match ciphersuite"); + + dynamic_cast<Client_Handshake_State&>(state). + server_public_key.reset(peer_key.release()); } else if(type == SERVER_KEX) { @@ -343,7 +355,10 @@ void Client::process_handshake_msg(const Handshake_State* /*active_state*/, if(state.ciphersuite().sig_algo() != "") { - if(!state.server_kex()->verify(m_peer_certs[0], state)) + const Public_Key& server_key = + dynamic_cast<Client_Handshake_State&>(state).get_server_public_Key(); + + if(!state.server_kex()->verify(server_key, state)) { throw TLS_Exception(Alert::DECRYPT_ERROR, "Bad signature on server key exchange"); diff --git a/src/tls/tls_handshake_state.cpp b/src/tls/tls_handshake_state.cpp index 24e00772d..ff03ca6dd 100644 --- a/src/tls/tls_handshake_state.cpp +++ b/src/tls/tls_handshake_state.cpp @@ -326,13 +326,13 @@ std::string choose_hash(const std::string& sig_algo, } std::pair<std::string, Signature_Format> -Handshake_State::choose_sig_format(const Private_Key* key, +Handshake_State::choose_sig_format(const Private_Key& key, std::string& hash_algo_out, std::string& sig_algo_out, bool for_client_auth, const Policy& policy) const { - const std::string sig_algo = key->algo_name(); + const std::string sig_algo = key.algo_name(); const std::string hash_algo = choose_hash(sig_algo, @@ -365,12 +365,12 @@ Handshake_State::choose_sig_format(const Private_Key* key, } std::pair<std::string, Signature_Format> -Handshake_State::understand_sig_format(const Public_Key* key, +Handshake_State::understand_sig_format(const Public_Key& key, std::string hash_algo, std::string sig_algo, bool for_client_auth) const { - const std::string algo_name = key->algo_name(); + const std::string algo_name = key.algo_name(); /* FIXME: This should check what was sent against the client hello diff --git a/src/tls/tls_handshake_state.h b/src/tls/tls_handshake_state.h index 486e6bfb8..0ada6cfd7 100644 --- a/src/tls/tls_handshake_state.h +++ b/src/tls/tls_handshake_state.h @@ -80,13 +80,13 @@ class Handshake_State const std::vector<byte>& session_ticket() const; std::pair<std::string, Signature_Format> - understand_sig_format(const Public_Key* key, + understand_sig_format(const Public_Key& key, std::string hash_algo, std::string sig_algo, bool for_client_auth) const; std::pair<std::string, Signature_Format> - choose_sig_format(const Private_Key* key, + choose_sig_format(const Private_Key& key, std::string& hash_algo, std::string& sig_algo, bool for_client_auth, diff --git a/src/tls/tls_messages.h b/src/tls/tls_messages.h index 6fd7f675c..5a9363669 100644 --- a/src/tls/tls_messages.h +++ b/src/tls/tls_messages.h @@ -397,7 +397,7 @@ class Server_Key_Exchange : public Handshake_Message const std::vector<byte>& params() const { return m_params; } - bool verify(const X509_Certificate& cert, + bool verify(const Public_Key& server_key, const Handshake_State& state) const; // Only valid for certain kex types |