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

Side by Side Diff: net/socket/ssl_host_info.cc

Issue 135373002: Added SSLHostInfo. Storing of server host info to our standard disk cache. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: fixed wtc's comments Created 6 years, 11 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 unified diff | Download patch | Annotate | Revision Log
« net/http/http_transaction.h ('K') | « net/socket/ssl_host_info.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "net/socket/ssl_host_info.h"
6
7 #include "base/bind.h"
8 #include "base/metrics/histogram.h"
9 #include "base/pickle.h"
10 #include "base/strings/string_piece.h"
11 #include "net/cert/cert_verifier.h"
12 #include "net/cert/crl_set.h"
13 #include "net/cert/x509_certificate.h"
14 #include "net/socket/ssl_client_socket.h"
15 #include "net/ssl/ssl_config_service.h"
16
17 namespace net {
18
19 SSLHostInfo::State::State() {}
20
21 SSLHostInfo::State::~State() {}
22
23 void SSLHostInfo::State::Clear() {
24 certs.clear();
25 }
26
27 SSLHostInfo::SSLHostInfo(
28 const std::string& hostname,
29 const SSLConfig& ssl_config,
30 CertVerifier* cert_verifier)
31 : cert_verification_complete_(false),
32 cert_verification_error_(ERR_CERT_INVALID),
33 hostname_(hostname),
34 cert_parsing_failed_(false),
35 rev_checking_enabled_(ssl_config.rev_checking_enabled),
36 verify_ev_cert_(ssl_config.verify_ev_cert),
37 verifier_(cert_verifier),
38 weak_factory_(this) {
39 }
40
41 SSLHostInfo::~SSLHostInfo() {
42 }
43
44 const SSLHostInfo::State& SSLHostInfo::state() const {
45 return state_;
46 }
47
48 SSLHostInfo::State* SSLHostInfo::mutable_state() {
49 return &state_;
50 }
51
52 bool SSLHostInfo::Parse(const std::string& data) {
53 State* state = mutable_state();
54
55 state->Clear();
56 cert_verification_complete_ = false;
57
58 bool r = ParseInner(data);
59 if (!r)
60 state->Clear();
61 return r;
62 }
63
64 bool SSLHostInfo::ParseInner(const std::string& data) {
65 State* state = mutable_state();
66
67 Pickle p(data.data(), data.size());
68 PickleIterator iter(p);
69
70 int num_der_certs;
71 if (!p.ReadInt(&iter, &num_der_certs) ||
72 num_der_certs < 0) {
73 return false;
74 }
75
76 for (int i = 0; i < num_der_certs; i++) {
77 std::string der_cert;
78 if (!p.ReadString(&iter, &der_cert))
79 return false;
80 state->certs.push_back(der_cert);
81 }
82
83 // Ignore obsolete members of the State structure.
84 std::string throwaway_string;
85 bool throwaway_bool;
86 // This was state->server_hello.
87 if (!p.ReadString(&iter, &throwaway_string))
88 return false;
89
90 // This was state->npn_valid.
91 if (!p.ReadBool(&iter, &throwaway_bool))
92 return false;
93
94 if (throwaway_bool) {
95 int throwaway_int;
96 // These were state->npn_status and state->npn_protocol.
97 if (!p.ReadInt(&iter, &throwaway_int) ||
98 !p.ReadString(&iter, &throwaway_string)) {
99 return false;
100 }
101 }
102
103 if (!state->certs.empty()) {
104 std::vector<base::StringPiece> der_certs(state->certs.size());
105 for (size_t i = 0; i < state->certs.size(); i++)
106 der_certs[i] = state->certs[i];
107 cert_ = X509Certificate::CreateFromDERCertChain(der_certs);
108 if (cert_.get()) {
109 int flags = 0;
110 if (verify_ev_cert_)
111 flags |= CertVerifier::VERIFY_EV_CERT;
112 if (rev_checking_enabled_)
113 flags |= CertVerifier::VERIFY_REV_CHECKING_ENABLED;
114 VLOG(1) << "Kicking off verification for " << hostname_;
115 verification_start_time_ = base::TimeTicks::Now();
116 verification_end_time_ = base::TimeTicks();
117 scoped_refptr<CRLSet> crl_set(SSLConfigService::GetCRLSet());
118 int rv = verifier_.Verify(
119 cert_.get(), hostname_, flags, crl_set, &cert_verify_result_,
120 base::Bind(&SSLHostInfo::VerifyCallback, weak_factory_.GetWeakPtr()),
121 // TODO(willchan): Figure out how to use NetLog here.
122 BoundNetLog());
123 if (rv != ERR_IO_PENDING)
124 VerifyCallback(rv);
125 } else {
126 cert_parsing_failed_ = true;
127 DCHECK(cert_verification_callback_.is_null());
128 }
129 }
130
131 return true;
132 }
133
134 std::string SSLHostInfo::Serialize() const {
135 Pickle p(sizeof(Pickle::Header));
136
137 static const unsigned kMaxCertificatesSize = 32 * 1024;
138 unsigned der_certs_size = 0;
139
140 for (std::vector<std::string>::const_iterator
141 i = state_.certs.begin(); i != state_.certs.end(); i++) {
142 der_certs_size += i->size();
143 }
144
145 // We don't care to save the certificates over a certain size.
146 if (der_certs_size > kMaxCertificatesSize)
147 return "";
148
149 if (!p.WriteInt(state_.certs.size()))
150 return "";
151
152 for (std::vector<std::string>::const_iterator
153 i = state_.certs.begin(); i != state_.certs.end(); i++) {
154 if (!p.WriteString(*i))
155 return "";
156 }
157
158 // Write dummy values for obsolete members of the State structure:
159 // state->server_hello and state->npn_valid.
160 if (!p.WriteString("") ||
161 !p.WriteBool(false)) {
162 return "";
163 }
164
165 return std::string(reinterpret_cast<const char *>(p.data()), p.size());
166 }
167
168 const CertVerifyResult& SSLHostInfo::cert_verify_result() const {
169 return cert_verify_result_;
170 }
171
172 int SSLHostInfo::WaitForCertVerification(const CompletionCallback& callback) {
173 if (cert_verification_complete_)
174 return cert_verification_error_;
175
176 DCHECK(!cert_parsing_failed_);
177 DCHECK(cert_verification_callback_.is_null());
178 DCHECK(!state_.certs.empty());
179 cert_verification_callback_ = callback;
180 return ERR_IO_PENDING;
181 }
182
183 void SSLHostInfo::VerifyCallback(int rv) {
184 DCHECK(!verification_start_time_.is_null());
185 base::TimeTicks now = base::TimeTicks::Now();
186 const base::TimeDelta duration = now - verification_start_time();
187 bool is_google = hostname_ == "google.com" ||
188 (hostname_.size() > 11 &&
189 hostname_.rfind(".google.com") == hostname_.size() - 11);
190 if (is_google) {
191 UMA_HISTOGRAM_TIMES("Net.SSLHostInfoVerificationTimeMs_Google", duration);
192 }
193 UMA_HISTOGRAM_TIMES("Net.SSLHostInfoVerificationTimeMs", duration);
194 VLOG(1) << "Verification took " << duration.InMilliseconds() << "ms";
195 verification_end_time_ = now;
196 cert_verification_complete_ = true;
197 cert_verification_error_ = rv;
198 if (!cert_verification_callback_.is_null()) {
199 CompletionCallback callback = cert_verification_callback_;
200 cert_verification_callback_.Reset();
201 callback.Run(rv);
202 }
203 }
204
205 SSLHostInfoFactory::~SSLHostInfoFactory() {}
206
207 } // namespace net
OLDNEW
« net/http/http_transaction.h ('K') | « net/socket/ssl_host_info.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698