Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1451)

Unified Diff: net/socket/ssl_client_socket_openssl.cc

Issue 416683002: This CL corrects a bug in which the OnHandshakeComplete callback for an ssl session was never called (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@r2
Patch Set: Changed the names of several confusingly named methods. Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: net/socket/ssl_client_socket_openssl.cc
diff --git a/net/socket/ssl_client_socket_openssl.cc b/net/socket/ssl_client_socket_openssl.cc
index a6f5caf188d96dac7c1a339e732990cb05ebd6f3..4d108fc92782f156390dcded83b4be3eaaba2ad9 100644
--- a/net/socket/ssl_client_socket_openssl.cc
+++ b/net/socket/ssl_client_socket_openssl.cc
@@ -363,6 +363,8 @@ SSLClientSocketOpenSSL::SSLClientSocketOpenSSL(
next_handshake_state_(STATE_NONE),
npn_status_(kNextProtoUnsupported),
channel_id_xtn_negotiated_(false),
+ ran_handshake_finished_callback_(false),
+ marked_session_as_good_(false),
net_log_(transport_->socket()->NetLog()) {
}
@@ -435,14 +437,6 @@ int SSLClientSocketOpenSSL::Connect(const CompletionCallback& callback) {
return rv;
}
- if (!handshake_completion_callback_.is_null()) {
- SSLContext* context = SSLContext::GetInstance();
- context->session_cache()->SetSessionAddedCallback(
- ssl_,
- base::Bind(&SSLClientSocketOpenSSL::OnHandshakeCompletion,
- base::Unretained(this)));
- }
-
// Set SSL to client mode. Handshake happens in the loop below.
SSL_set_connect_state(ssl_);
@@ -465,8 +459,6 @@ void SSLClientSocketOpenSSL::Disconnect() {
// completed, this is a no-op.
OnHandshakeCompletion();
if (ssl_) {
- SSLContext* context = SSLContext::GetInstance();
- context->session_cache()->RemoveSessionAddedCallback(ssl_);
// Calling SSL_shutdown prevents the session from being marked as
// unresumable.
SSL_shutdown(ssl_);
@@ -687,6 +679,18 @@ int SSLClientSocketOpenSSL::SetSendBufferSize(int32 size) {
return transport_->socket()->SetSendBufferSize(size);
}
+// static
+void SSLClientSocketOpenSSL::InfoCallback(const SSL* ssl,
+ int result,
+ int /*unused*/) {
wtc 2014/08/07 20:04:04 The second parameter should be named "type". The t
+ SSLClientSocketOpenSSL* ssl_socket =
+ SSLContext::GetInstance()->GetClientSocketFromSSL(ssl);
wtc 2014/08/07 20:04:03 Move this into the if block because it is only use
+ if (result == SSL_CB_HANDSHAKE_DONE) {
+ ssl_socket->ran_handshake_finished_callback_ = true;
+ ssl_socket->CheckIfHandshakeFinished();
+ }
+}
+
int SSLClientSocketOpenSSL::Init() {
DCHECK(!ssl_);
DCHECK(!transport_bio_);
@@ -701,6 +705,9 @@ int SSLClientSocketOpenSSL::Init() {
if (!SSL_set_tlsext_host_name(ssl_, host_and_port_.host().c_str()))
return ERR_UNEXPECTED;
+ // Set an OpenSSL callback to monitor this SSL*'s connection.
+ SSL_set_info_callback(ssl_, &InfoCallback);
+
trying_cached_session_ = context->session_cache()->SetSSLSessionWithKey(
ssl_, GetSessionCacheKey());
@@ -1032,6 +1039,8 @@ int SSLClientSocketOpenSSL::DoVerifyCertComplete(int result) {
// TODO(joth): Work out if we need to remember the intermediate CA certs
// when the server sends them to us, and do so here.
SSLContext::GetInstance()->session_cache()->MarkSSLSessionAsGood(ssl_);
+ marked_session_as_good_ = true;
+ CheckIfHandshakeFinished();
} else {
DVLOG(1) << "DoVerifyCertComplete error " << ErrorToString(result)
<< " (" << result << ")";
@@ -1577,6 +1586,19 @@ long SSLClientSocketOpenSSL::MaybeReplayTransportError(
return retvalue;
}
+// Determines if the session for |ssl_| is in the cache, and calls the
wtc 2014/08/07 20:04:03 "the session for |ssl_| is in the cache" is not tr
+// handshake completion callback if that is the case.
+//
+// CheckIfHandshakeFinished is called twice per connection: once after
+// MarkSSLSessionAsGood, when the certificate has been verified, and
+// once via an OpenSSL callback when the handshake has completed. On the
+// second call, when the certificate has been verified and the handshake
+// has completed, the connection's handshake completion callback is run.
+void SSLClientSocketOpenSSL::CheckIfHandshakeFinished() {
wtc 2014/08/07 20:04:03 Nit: to match the declaration order in the .h file
+ if (ran_handshake_finished_callback_ && marked_session_as_good_)
+ OnHandshakeCompletion();
+}
+
// static
long SSLClientSocketOpenSSL::BIOCallback(
BIO *bio,

Powered by Google App Engine
This is Rietveld 408576698