1 // Copyright 2012 The Chromium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifdef UNSAFE_BUFFERS_BUILD
6 // TODO(crbug.com/40284755): Remove this and spanify to fix the errors.
7 #pragma allow_unsafe_buffers
8 #endif
9
10 #include "net/http/transport_security_state.h"
11
12 #include <stdint.h>
13
14 #include <algorithm>
15 #include <iterator>
16 #include <memory>
17 #include <string>
18 #include <vector>
19
20 #include "base/base64.h"
21 #include "base/files/file_path.h"
22 #include "base/functional/callback_helpers.h"
23 #include "base/json/json_reader.h"
24 #include "base/memory/raw_ptr.h"
25 #include "base/metrics/field_trial.h"
26 #include "base/metrics/field_trial_param_associator.h"
27 #include "base/rand_util.h"
28 #include "base/stl_util.h"
29 #include "base/strings/stringprintf.h"
30 #include "base/test/metrics/histogram_tester.h"
31 #include "base/test/mock_entropy_provider.h"
32 #include "base/test/scoped_feature_list.h"
33 #include "base/time/time.h"
34 #include "base/values.h"
35 #include "build/build_config.h"
36 #include "crypto/sha2.h"
37 #include "net/base/features.h"
38 #include "net/base/hash_value.h"
39 #include "net/base/host_port_pair.h"
40 #include "net/base/net_errors.h"
41 #include "net/base/schemeful_site.h"
42 #include "net/base/test_completion_callback.h"
43 #include "net/cert/asn1_util.h"
44 #include "net/cert/cert_verifier.h"
45 #include "net/cert/cert_verify_result.h"
46 #include "net/cert/ct_policy_status.h"
47 #include "net/cert/test_root_certs.h"
48 #include "net/cert/x509_certificate.h"
49 #include "net/extras/preload_data/decoder.h"
50 #include "net/http/http_status_code.h"
51 #include "net/http/http_util.h"
52 #include "net/http/transport_security_state_source.h"
53 #include "net/net_buildflags.h"
54 #include "net/ssl/ssl_info.h"
55 #include "net/test/cert_test_util.h"
56 #include "net/test/test_data_directory.h"
57 #include "net/test/test_with_task_environment.h"
58 #include "net/tools/huffman_trie/bit_writer.h"
59 #include "net/tools/huffman_trie/trie/trie_bit_buffer.h"
60 #include "testing/gmock/include/gmock/gmock.h"
61 #include "testing/gtest/include/gtest/gtest.h"
62 #include "url/origin.h"
63
64 namespace net {
65
66 namespace {
67
68 namespace test_default {
69 #include "net/http/transport_security_state_static_unittest_default.h"
70 }
71 namespace test1 {
72 #include "net/http/transport_security_state_static_unittest1.h"
73 }
74 namespace test2 {
75 #include "net/http/transport_security_state_static_unittest2.h"
76 }
77 namespace test3 {
78 #include "net/http/transport_security_state_static_unittest3.h"
79 }
80
81 const char kHost[] = "example.test";
82 const uint16_t kPort = 443;
83
84 const char* const kGoodPath[] = {
85 "sha256/AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
86 "sha256/fzP+pVAbH0hRoUphJKenIP8+2tD/d2QH9J+kQNieM6Q=",
87 "sha256/9vRUVdjloCa4wXUKfDWotV5eUXYD7vu0v0z9SRzQdzg=",
88 "sha256/Nn8jk5By4Vkq6BeOVZ7R7AC6XUUBZsWmUbJR1f1Y5FY=",
89 nullptr,
90 };
91
92 const char* const kBadPath[] = {
93 "sha256/1111111111111111111111111111111111111111111=",
94 "sha256/2222222222222222222222222222222222222222222=",
95 "sha256/3333333333333333333333333333333333333333333=",
96 nullptr,
97 };
98
99 class MockRequireCTDelegate : public TransportSecurityState::RequireCTDelegate {
100 public:
101 MOCK_METHOD3(IsCTRequiredForHost,
102 CTRequirementLevel(std::string_view hostname,
103 const X509Certificate* chain,
104 const HashValueVector& hashes));
105 };
106
operator ==(const TransportSecurityState::STSState & lhs,const TransportSecurityState::STSState & rhs)107 bool operator==(const TransportSecurityState::STSState& lhs,
108 const TransportSecurityState::STSState& rhs) {
109 return lhs.last_observed == rhs.last_observed && lhs.expiry == rhs.expiry &&
110 lhs.upgrade_mode == rhs.upgrade_mode &&
111 lhs.include_subdomains == rhs.include_subdomains &&
112 lhs.domain == rhs.domain;
113 }
114
operator ==(const TransportSecurityState::PKPState & lhs,const TransportSecurityState::PKPState & rhs)115 bool operator==(const TransportSecurityState::PKPState& lhs,
116 const TransportSecurityState::PKPState& rhs) {
117 return lhs.last_observed == rhs.last_observed && lhs.expiry == rhs.expiry &&
118 lhs.spki_hashes == rhs.spki_hashes &&
119 lhs.bad_spki_hashes == rhs.bad_spki_hashes &&
120 lhs.include_subdomains == rhs.include_subdomains &&
121 lhs.domain == rhs.domain;
122 }
123
124 } // namespace
125
126 class TransportSecurityStateTest : public ::testing::Test,
127 public WithTaskEnvironment {
128 public:
TransportSecurityStateTest()129 TransportSecurityStateTest()
130 : WithTaskEnvironment(
131 base::test::TaskEnvironment::TimeSource::MOCK_TIME) {
132 SetTransportSecurityStateSourceForTesting(&test_default::kHSTSSource);
133 // Need mocked out time for pruning tests. Don't start with a
134 // time of 0, as code doesn't generally expect it.
135 FastForwardBy(base::Days(1));
136 }
137
~TransportSecurityStateTest()138 ~TransportSecurityStateTest() override {
139 SetTransportSecurityStateSourceForTesting(nullptr);
140 }
141
DisableStaticPins(TransportSecurityState * state)142 static void DisableStaticPins(TransportSecurityState* state) {
143 state->enable_static_pins_ = false;
144 }
145
EnableStaticPins(TransportSecurityState * state)146 static void EnableStaticPins(TransportSecurityState* state) {
147 state->enable_static_pins_ = true;
148 state->SetPinningListAlwaysTimelyForTesting(true);
149 }
150
GetSampleSPKIHashes()151 static HashValueVector GetSampleSPKIHashes() {
152 HashValueVector spki_hashes;
153 HashValue hash(HASH_VALUE_SHA256);
154 memset(hash.data(), 0, hash.size());
155 spki_hashes.push_back(hash);
156 return spki_hashes;
157 }
158
GetSampleSPKIHash(uint8_t value)159 static HashValue GetSampleSPKIHash(uint8_t value) {
160 HashValue hash(HASH_VALUE_SHA256);
161 memset(hash.data(), value, hash.size());
162 return hash;
163 }
164
165 protected:
GetStaticDomainState(TransportSecurityState * state,const std::string & host,TransportSecurityState::STSState * sts_result,TransportSecurityState::PKPState * pkp_result)166 bool GetStaticDomainState(TransportSecurityState* state,
167 const std::string& host,
168 TransportSecurityState::STSState* sts_result,
169 TransportSecurityState::PKPState* pkp_result) {
170 bool ret = state->GetStaticSTSState(host, sts_result);
171 if (state->GetStaticPKPState(host, pkp_result))
172 ret = true;
173 return ret;
174 }
175
176 private:
177 base::test::ScopedFeatureList scoped_feature_list_;
178 };
179
TEST_F(TransportSecurityStateTest,DomainNameOddities)180 TEST_F(TransportSecurityStateTest, DomainNameOddities) {
181 TransportSecurityState state;
182 const base::Time current_time(base::Time::Now());
183 const base::Time expiry = current_time + base::Seconds(1000);
184
185 // DNS suffix search tests. Some DNS resolvers allow a terminal "." to
186 // indicate not perform DNS suffix searching. Ensure that regardless
187 // of how this is treated at the resolver layer, or at the URL/origin
188 // layer (that is, whether they are treated as equivalent or distinct),
189 // ensure that for policy matching, something lacking a terminal "."
190 // is equivalent to something with a terminal "."
191 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.com"));
192
193 state.AddHSTS("example.com", expiry, true /* include_subdomains */);
194 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
195 // Trailing '.' should be equivalent; it's just a resolver hint
196 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com."));
197 // Leading '.' should be invalid
198 EXPECT_FALSE(state.ShouldUpgradeToSSL(".example.com"));
199 // Subdomains should work regardless
200 EXPECT_TRUE(state.ShouldUpgradeToSSL("sub.example.com"));
201 EXPECT_TRUE(state.ShouldUpgradeToSSL("sub.example.com."));
202 // But invalid subdomains should be rejected
203 EXPECT_FALSE(state.ShouldUpgradeToSSL("sub..example.com"));
204 EXPECT_FALSE(state.ShouldUpgradeToSSL("sub..example.com."));
205
206 // Now try the inverse form
207 TransportSecurityState state2;
208 state2.AddHSTS("example.net.", expiry, true /* include_subdomains */);
209 EXPECT_TRUE(state2.ShouldUpgradeToSSL("example.net."));
210 EXPECT_TRUE(state2.ShouldUpgradeToSSL("example.net"));
211 EXPECT_TRUE(state2.ShouldUpgradeToSSL("sub.example.net."));
212 EXPECT_TRUE(state2.ShouldUpgradeToSSL("sub.example.net"));
213
214 // Finally, test weird things
215 TransportSecurityState state3;
216 state3.AddHSTS("", expiry, true /* include_subdomains */);
217 EXPECT_FALSE(state3.ShouldUpgradeToSSL(""));
218 EXPECT_FALSE(state3.ShouldUpgradeToSSL("."));
219 EXPECT_FALSE(state3.ShouldUpgradeToSSL("..."));
220 // Make sure it didn't somehow apply HSTS to the world
221 EXPECT_FALSE(state3.ShouldUpgradeToSSL("example.org"));
222
223 TransportSecurityState state4;
224 state4.AddHSTS(".", expiry, true /* include_subdomains */);
225 EXPECT_FALSE(state4.ShouldUpgradeToSSL(""));
226 EXPECT_FALSE(state4.ShouldUpgradeToSSL("."));
227 EXPECT_FALSE(state4.ShouldUpgradeToSSL("..."));
228 EXPECT_FALSE(state4.ShouldUpgradeToSSL("example.org"));
229
230 // Now do the same for preloaded entries
231 TransportSecurityState state5;
232 EXPECT_TRUE(state5.ShouldUpgradeToSSL("hsts-preloaded.test"));
233 EXPECT_TRUE(state5.ShouldUpgradeToSSL("hsts-preloaded.test."));
234 EXPECT_FALSE(state5.ShouldUpgradeToSSL("hsts-preloaded..test"));
235 EXPECT_FALSE(state5.ShouldUpgradeToSSL("hsts-preloaded..test."));
236 }
237
TEST_F(TransportSecurityStateTest,SimpleMatches)238 TEST_F(TransportSecurityStateTest, SimpleMatches) {
239 TransportSecurityState state;
240 const base::Time current_time(base::Time::Now());
241 const base::Time expiry = current_time + base::Seconds(1000);
242
243 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.com"));
244 bool include_subdomains = false;
245 state.AddHSTS("example.com", expiry, include_subdomains);
246 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
247 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example.com"));
248 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example.com"));
249 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("foo.example.com"));
250 }
251
TEST_F(TransportSecurityStateTest,MatchesCase1)252 TEST_F(TransportSecurityStateTest, MatchesCase1) {
253 TransportSecurityState state;
254 const base::Time current_time(base::Time::Now());
255 const base::Time expiry = current_time + base::Seconds(1000);
256
257 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.com"));
258 bool include_subdomains = false;
259 state.AddHSTS("EXample.coM", expiry, include_subdomains);
260 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
261 }
262
TEST_F(TransportSecurityStateTest,MatchesCase2)263 TEST_F(TransportSecurityStateTest, MatchesCase2) {
264 TransportSecurityState state;
265 const base::Time current_time(base::Time::Now());
266 const base::Time expiry = current_time + base::Seconds(1000);
267
268 // Check dynamic entries
269 EXPECT_FALSE(state.ShouldUpgradeToSSL("EXample.coM"));
270 bool include_subdomains = false;
271 state.AddHSTS("example.com", expiry, include_subdomains);
272 EXPECT_TRUE(state.ShouldUpgradeToSSL("EXample.coM"));
273
274 // Check static entries
275 EXPECT_TRUE(state.ShouldUpgradeToSSL("hStS-prelOAded.tEsT"));
276 EXPECT_TRUE(
277 state.ShouldUpgradeToSSL("inClude-subDOmaIns-hsts-prEloaDed.TesT"));
278 }
279
TEST_F(TransportSecurityStateTest,SubdomainMatches)280 TEST_F(TransportSecurityStateTest, SubdomainMatches) {
281 TransportSecurityState state;
282 const base::Time current_time(base::Time::Now());
283 const base::Time expiry = current_time + base::Seconds(1000);
284
285 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.test"));
286 bool include_subdomains = true;
287 state.AddHSTS("example.test", expiry, include_subdomains);
288 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.test"));
289 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example.test"));
290 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.example.test"));
291 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.baz.example.test"));
292 EXPECT_FALSE(state.ShouldUpgradeToSSL("test"));
293 EXPECT_FALSE(state.ShouldUpgradeToSSL("notexample.test"));
294 }
295
296 // Tests that a more-specific HSTS rule without the includeSubDomains bit does
297 // not override a less-specific rule with includeSubDomains. Applicability is
298 // checked before specificity. See https://crbug.com/821811.
TEST_F(TransportSecurityStateTest,STSSubdomainNoOverride)299 TEST_F(TransportSecurityStateTest, STSSubdomainNoOverride) {
300 TransportSecurityState state;
301 const base::Time current_time(base::Time::Now());
302 const base::Time expiry = current_time + base::Seconds(1000);
303 const base::Time older = current_time - base::Seconds(1000);
304
305 state.AddHSTS("example.test", expiry, true);
306 state.AddHSTS("foo.example.test", expiry, false);
307
308 // The example.test rule applies to the entire domain, including subdomains of
309 // foo.example.test.
310 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.test"));
311 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example.test"));
312 EXPECT_TRUE(state.ShouldUpgradeToSSL("bar.foo.example.test"));
313 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example.test"));
314
315 // Expire the foo.example.test rule.
316 state.AddHSTS("foo.example.test", older, false);
317
318 // The example.test rule still applies.
319 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.test"));
320 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example.test"));
321 EXPECT_TRUE(state.ShouldUpgradeToSSL("bar.foo.example.test"));
322 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example.test"));
323 }
324
325 // Tests that a more-specific HPKP rule overrides a less-specific rule
326 // with it, regardless of the includeSubDomains bit. Note this behavior does not
327 // match HSTS. See https://crbug.com/821811.
TEST_F(TransportSecurityStateTest,PKPSubdomainCarveout)328 TEST_F(TransportSecurityStateTest, PKPSubdomainCarveout) {
329 TransportSecurityState state;
330 const base::Time current_time(base::Time::Now());
331 const base::Time expiry = current_time + base::Seconds(1000);
332 const base::Time older = current_time - base::Seconds(1000);
333
334 state.AddHPKP("example.test", expiry, true, GetSampleSPKIHashes());
335 state.AddHPKP("foo.example.test", expiry, false, GetSampleSPKIHashes());
336 EXPECT_TRUE(state.HasPublicKeyPins("example.test"));
337 EXPECT_TRUE(state.HasPublicKeyPins("foo.example.test"));
338
339 // The foo.example.test rule overrides the example1.test rule, so
340 // bar.foo.example.test has no HPKP state.
341 EXPECT_FALSE(state.HasPublicKeyPins("bar.foo.example.test"));
342 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("bar.foo.example.test"));
343
344 // Expire the foo.example.test rule.
345 state.AddHPKP("foo.example.test", older, false, GetSampleSPKIHashes());
346
347 // Now the base example.test rule applies to bar.foo.example.test.
348 EXPECT_TRUE(state.HasPublicKeyPins("bar.foo.example.test"));
349 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example.test"));
350 }
351
TEST_F(TransportSecurityStateTest,FatalSSLErrors)352 TEST_F(TransportSecurityStateTest, FatalSSLErrors) {
353 TransportSecurityState state;
354 const base::Time current_time(base::Time::Now());
355 const base::Time expiry = current_time + base::Seconds(1000);
356
357 state.AddHSTS("example1.test", expiry, false);
358 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes());
359
360 // The presense of either HSTS or HPKP is enough to make SSL errors fatal.
361 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example1.test"));
362 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example2.test"));
363 }
364
365 // Tests that HPKP and HSTS state both expire. Also tests that expired entries
366 // are pruned.
TEST_F(TransportSecurityStateTest,Expiration)367 TEST_F(TransportSecurityStateTest, Expiration) {
368 TransportSecurityState state;
369 const base::Time current_time(base::Time::Now());
370 const base::Time expiry = current_time + base::Seconds(1000);
371 const base::Time older = current_time - base::Seconds(1000);
372
373 // Note: this test assumes that inserting an entry with an expiration time in
374 // the past works and is pruned on query.
375 state.AddHSTS("example1.test", older, false);
376 EXPECT_TRUE(TransportSecurityState::STSStateIterator(state).HasNext());
377 EXPECT_FALSE(state.ShouldUpgradeToSSL("example1.test"));
378 // Querying |state| for a domain should flush out expired entries.
379 EXPECT_FALSE(TransportSecurityState::STSStateIterator(state).HasNext());
380
381 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes());
382 EXPECT_TRUE(state.has_dynamic_pkp_state());
383 EXPECT_FALSE(state.HasPublicKeyPins("example1.test"));
384 // Querying |state| for a domain should flush out expired entries.
385 EXPECT_FALSE(state.has_dynamic_pkp_state());
386
387 state.AddHSTS("example1.test", older, false);
388 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes());
389 EXPECT_TRUE(TransportSecurityState::STSStateIterator(state).HasNext());
390 EXPECT_TRUE(state.has_dynamic_pkp_state());
391 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("example1.test"));
392 // Querying |state| for a domain should flush out expired entries.
393 EXPECT_FALSE(TransportSecurityState::STSStateIterator(state).HasNext());
394 EXPECT_FALSE(state.has_dynamic_pkp_state());
395
396 // Test that HSTS can outlive HPKP.
397 state.AddHSTS("example1.test", expiry, false);
398 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes());
399 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test"));
400 EXPECT_FALSE(state.HasPublicKeyPins("example1.test"));
401
402 // Test that HPKP can outlive HSTS.
403 state.AddHSTS("example2.test", older, false);
404 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes());
405 EXPECT_FALSE(state.ShouldUpgradeToSSL("example2.test"));
406 EXPECT_TRUE(state.HasPublicKeyPins("example2.test"));
407 }
408
409 // Tests that HPKP and HSTS state are queried independently for subdomain
410 // matches.
TEST_F(TransportSecurityStateTest,IndependentSubdomain)411 TEST_F(TransportSecurityStateTest, IndependentSubdomain) {
412 TransportSecurityState state;
413 const base::Time current_time(base::Time::Now());
414 const base::Time expiry = current_time + base::Seconds(1000);
415
416 state.AddHSTS("example1.test", expiry, true);
417 state.AddHPKP("example1.test", expiry, false, GetSampleSPKIHashes());
418
419 state.AddHSTS("example2.test", expiry, false);
420 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes());
421
422 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test"));
423 EXPECT_FALSE(state.HasPublicKeyPins("foo.example1.test"));
424 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example2.test"));
425 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test"));
426 }
427
428 // Tests that HPKP and HSTS state are inserted and overridden independently.
TEST_F(TransportSecurityStateTest,IndependentInsertion)429 TEST_F(TransportSecurityStateTest, IndependentInsertion) {
430 TransportSecurityState state;
431 const base::Time current_time(base::Time::Now());
432 const base::Time expiry = current_time + base::Seconds(1000);
433
434 // Place an includeSubdomains HSTS entry below a normal HPKP entry.
435 state.AddHSTS("example1.test", expiry, true);
436 state.AddHPKP("foo.example1.test", expiry, false, GetSampleSPKIHashes());
437
438 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test"));
439 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test"));
440 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test"));
441 EXPECT_FALSE(state.HasPublicKeyPins("example1.test"));
442
443 // Drop the includeSubdomains from the HSTS entry.
444 state.AddHSTS("example1.test", expiry, false);
445
446 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example1.test"));
447 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test"));
448
449 // Place an includeSubdomains HPKP entry below a normal HSTS entry.
450 state.AddHSTS("foo.example2.test", expiry, false);
451 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes());
452
453 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test"));
454 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test"));
455
456 // Drop the includeSubdomains from the HSTS entry.
457 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes());
458
459 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test"));
460 EXPECT_FALSE(state.HasPublicKeyPins("foo.example2.test"));
461 }
462
463 // Tests that GetDynamic[PKP|STS]State returns the correct data and that the
464 // states are not mixed together.
TEST_F(TransportSecurityStateTest,DynamicDomainState)465 TEST_F(TransportSecurityStateTest, DynamicDomainState) {
466 TransportSecurityState state;
467 const base::Time current_time(base::Time::Now());
468 const base::Time expiry1 = current_time + base::Seconds(1000);
469 const base::Time expiry2 = current_time + base::Seconds(2000);
470
471 state.AddHSTS("example.com", expiry1, true);
472 state.AddHPKP("foo.example.com", expiry2, false, GetSampleSPKIHashes());
473
474 TransportSecurityState::STSState sts_state;
475 TransportSecurityState::PKPState pkp_state;
476 ASSERT_TRUE(state.GetDynamicSTSState("foo.example.com", &sts_state));
477 ASSERT_TRUE(state.GetDynamicPKPState("foo.example.com", &pkp_state));
478 EXPECT_TRUE(sts_state.ShouldUpgradeToSSL());
479 EXPECT_TRUE(pkp_state.HasPublicKeyPins());
480 EXPECT_TRUE(sts_state.include_subdomains);
481 EXPECT_FALSE(pkp_state.include_subdomains);
482 EXPECT_EQ(expiry1, sts_state.expiry);
483 EXPECT_EQ(expiry2, pkp_state.expiry);
484 EXPECT_EQ("example.com", sts_state.domain);
485 EXPECT_EQ("foo.example.com", pkp_state.domain);
486 }
487
488 // Tests that GetSSLUpgradeDecision() matches the result of ShouldUpgradeToSSL()
489 // and correctly identifies the source of the decision.
TEST_F(TransportSecurityStateTest,StaticOrDynamicSource)490 TEST_F(TransportSecurityStateTest, StaticOrDynamicSource) {
491 TransportSecurityState state;
492 SetTransportSecurityStateSourceForTesting(&test1::kHSTSSource);
493
494 // Check preconditions of preloaded states.
495 TransportSecurityState::STSState sts_state;
496 ASSERT_TRUE(state.GetStaticSTSState("hsts.example.com", &sts_state));
497 ASSERT_EQ(sts_state.upgrade_mode,
498 TransportSecurityState::STSState::MODE_FORCE_HTTPS);
499 ASSERT_TRUE(sts_state.include_subdomains);
500 ASSERT_FALSE(state.GetStaticSTSState("dynamic.example.com", &sts_state));
501
502 const base::Time current_time(base::Time::Now());
503 const base::Time expiry = current_time + base::Seconds(1000);
504
505 EXPECT_EQ(state.GetSSLUpgradeDecision("dynamic.example.com"),
506 SSLUpgradeDecision::kNoUpgrade);
507 EXPECT_FALSE(state.ShouldUpgradeToSSL("dynamic.example.com"));
508
509 EXPECT_EQ(state.GetSSLUpgradeDecision("hsts.example.com"),
510 SSLUpgradeDecision::kStaticUpgrade);
511 EXPECT_TRUE(state.ShouldUpgradeToSSL("hsts.example.com"));
512
513 state.AddHSTS("dynamic.example.com", expiry, false);
514 EXPECT_EQ(state.GetSSLUpgradeDecision("dynamic.example.com"),
515 SSLUpgradeDecision::kDynamicUpgrade);
516 EXPECT_TRUE(state.ShouldUpgradeToSSL("dynamic.example.com"));
517
518 // Dynamic state for a host that already has static state doesn't change the
519 // decision.
520 state.AddHSTS("subdomain.hsts.example.com", expiry, false);
521 EXPECT_EQ(state.GetSSLUpgradeDecision("subdomain.hsts.example.com"),
522 SSLUpgradeDecision::kStaticUpgrade);
523 EXPECT_TRUE(state.ShouldUpgradeToSSL("subdomain.hsts.example.com"));
524 }
525
526 // Tests that new pins always override previous pins. This should be true for
527 // both pins at the same domain or includeSubdomains pins at a parent domain.
TEST_F(TransportSecurityStateTest,NewPinsOverride)528 TEST_F(TransportSecurityStateTest, NewPinsOverride) {
529 TransportSecurityState state;
530 TransportSecurityState::PKPState pkp_state;
531 const base::Time current_time(base::Time::Now());
532 const base::Time expiry = current_time + base::Seconds(1000);
533 HashValue hash1(HASH_VALUE_SHA256);
534 memset(hash1.data(), 0x01, hash1.size());
535 HashValue hash2(HASH_VALUE_SHA256);
536 memset(hash2.data(), 0x02, hash1.size());
537 HashValue hash3(HASH_VALUE_SHA256);
538 memset(hash3.data(), 0x03, hash1.size());
539
540 state.AddHPKP("example.com", expiry, true, HashValueVector(1, hash1));
541
542 ASSERT_TRUE(state.GetDynamicPKPState("foo.example.com", &pkp_state));
543 ASSERT_EQ(1u, pkp_state.spki_hashes.size());
544 EXPECT_EQ(pkp_state.spki_hashes[0], hash1);
545
546 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash2));
547
548 ASSERT_TRUE(state.GetDynamicPKPState("foo.example.com", &pkp_state));
549 ASSERT_EQ(1u, pkp_state.spki_hashes.size());
550 EXPECT_EQ(pkp_state.spki_hashes[0], hash2);
551
552 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash3));
553
554 ASSERT_TRUE(state.GetDynamicPKPState("foo.example.com", &pkp_state));
555 ASSERT_EQ(1u, pkp_state.spki_hashes.size());
556 EXPECT_EQ(pkp_state.spki_hashes[0], hash3);
557 }
558
TEST_F(TransportSecurityStateTest,DeleteAllDynamicDataBetween)559 TEST_F(TransportSecurityStateTest, DeleteAllDynamicDataBetween) {
560 TransportSecurityState state;
561 const base::Time current_time(base::Time::Now());
562 const base::Time expiry = current_time + base::Seconds(1000);
563 const base::Time older = current_time - base::Seconds(1000);
564
565 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.com"));
566 EXPECT_FALSE(state.HasPublicKeyPins("example.com"));
567 bool include_subdomains = false;
568 state.AddHSTS("example.com", expiry, include_subdomains);
569 state.AddHPKP("example.com", expiry, include_subdomains,
570 GetSampleSPKIHashes());
571
572 state.DeleteAllDynamicDataBetween(expiry, base::Time::Max(),
573 base::DoNothing());
574 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
575 EXPECT_TRUE(state.HasPublicKeyPins("example.com"));
576
577 state.DeleteAllDynamicDataBetween(older, current_time, base::DoNothing());
578 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
579 EXPECT_TRUE(state.HasPublicKeyPins("example.com"));
580
581 state.DeleteAllDynamicDataBetween(base::Time(), current_time,
582 base::DoNothing());
583 EXPECT_TRUE(state.ShouldUpgradeToSSL("example.com"));
584 EXPECT_TRUE(state.HasPublicKeyPins("example.com"));
585
586 state.DeleteAllDynamicDataBetween(older, base::Time::Max(),
587 base::DoNothing());
588 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.com"));
589 EXPECT_FALSE(state.HasPublicKeyPins("example.com"));
590
591 // Dynamic data in |state| should be empty now.
592 EXPECT_FALSE(TransportSecurityState::STSStateIterator(state).HasNext());
593 EXPECT_FALSE(state.has_dynamic_pkp_state());
594 }
595
TEST_F(TransportSecurityStateTest,DeleteDynamicDataForHost)596 TEST_F(TransportSecurityStateTest, DeleteDynamicDataForHost) {
597 TransportSecurityState state;
598 const base::Time current_time(base::Time::Now());
599 const base::Time expiry = current_time + base::Seconds(1000);
600 bool include_subdomains = false;
601
602 state.AddHSTS("example1.test", expiry, include_subdomains);
603 state.AddHPKP("example1.test", expiry, include_subdomains,
604 GetSampleSPKIHashes());
605
606 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test"));
607 EXPECT_FALSE(state.ShouldUpgradeToSSL("example2.test"));
608 EXPECT_TRUE(state.HasPublicKeyPins("example1.test"));
609 EXPECT_FALSE(state.HasPublicKeyPins("example2.test"));
610
611 EXPECT_TRUE(state.DeleteDynamicDataForHost("example1.test"));
612 EXPECT_FALSE(state.ShouldUpgradeToSSL("example1.test"));
613 EXPECT_FALSE(state.HasPublicKeyPins("example1.test"));
614 }
615
TEST_F(TransportSecurityStateTest,LongNames)616 TEST_F(TransportSecurityStateTest, LongNames) {
617 TransportSecurityState state;
618 state.SetPinningListAlwaysTimelyForTesting(true);
619 const char kLongName[] =
620 "lookupByWaveIdHashAndWaveIdIdAndWaveIdDomainAndWaveletIdIdAnd"
621 "WaveletIdDomainAndBlipBlipid";
622 TransportSecurityState::STSState sts_state;
623 TransportSecurityState::PKPState pkp_state;
624 // Just checks that we don't hit a NOTREACHED
625 EXPECT_FALSE(state.GetStaticSTSState(kLongName, &sts_state));
626 EXPECT_FALSE(state.GetStaticPKPState(kLongName, &pkp_state));
627 EXPECT_FALSE(state.GetDynamicSTSState(kLongName, &sts_state));
628 EXPECT_FALSE(state.GetDynamicPKPState(kLongName, &pkp_state));
629 }
630
AddHash(const std::string & type_and_base64,HashValueVector * out)631 static bool AddHash(const std::string& type_and_base64, HashValueVector* out) {
632 HashValue hash;
633 if (!hash.FromString(type_and_base64))
634 return false;
635
636 out->push_back(hash);
637 return true;
638 }
639
TEST_F(TransportSecurityStateTest,PinValidationWithoutRejectedCerts)640 TEST_F(TransportSecurityStateTest, PinValidationWithoutRejectedCerts) {
641 base::test::ScopedFeatureList scoped_feature_list_;
642 scoped_feature_list_.InitAndEnableFeature(
643 features::kStaticKeyPinningEnforcement);
644 HashValueVector good_hashes, bad_hashes;
645
646 for (size_t i = 0; kGoodPath[i]; i++) {
647 EXPECT_TRUE(AddHash(kGoodPath[i], &good_hashes));
648 }
649 for (size_t i = 0; kBadPath[i]; i++) {
650 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes));
651 }
652
653 TransportSecurityState state;
654 state.SetPinningListAlwaysTimelyForTesting(true);
655 EnableStaticPins(&state);
656
657 TransportSecurityState::PKPState pkp_state;
658 EXPECT_TRUE(state.GetStaticPKPState("no-rejected-pins-pkp.preloaded.test",
659 &pkp_state));
660 EXPECT_TRUE(pkp_state.HasPublicKeyPins());
661
662 EXPECT_TRUE(pkp_state.CheckPublicKeyPins(good_hashes));
663 EXPECT_FALSE(pkp_state.CheckPublicKeyPins(bad_hashes));
664 }
665
666 // Simple test for the HSTS preload process. The trie (generated from
667 // transport_security_state_static_unittest1.json) contains 1 entry. Test that
668 // the lookup methods can find the entry and correctly decode the different
669 // preloaded states (HSTS and HPKP).
TEST_F(TransportSecurityStateTest,DecodePreloadedSingle)670 TEST_F(TransportSecurityStateTest, DecodePreloadedSingle) {
671 base::test::ScopedFeatureList scoped_feature_list_;
672 scoped_feature_list_.InitAndEnableFeature(
673 features::kStaticKeyPinningEnforcement);
674 SetTransportSecurityStateSourceForTesting(&test1::kHSTSSource);
675
676 TransportSecurityState state;
677 TransportSecurityStateTest::EnableStaticPins(&state);
678
679 TransportSecurityState::STSState sts_state;
680 TransportSecurityState::PKPState pkp_state;
681 EXPECT_TRUE(
682 GetStaticDomainState(&state, "hsts.example.com", &sts_state, &pkp_state));
683 EXPECT_TRUE(sts_state.include_subdomains);
684 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
685 sts_state.upgrade_mode);
686 EXPECT_TRUE(pkp_state.include_subdomains);
687 ASSERT_EQ(1u, pkp_state.spki_hashes.size());
688 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x1));
689 ASSERT_EQ(1u, pkp_state.bad_spki_hashes.size());
690 EXPECT_EQ(pkp_state.bad_spki_hashes[0], GetSampleSPKIHash(0x2));
691 }
692
693 // More advanced test for the HSTS preload process where the trie (generated
694 // from transport_security_state_static_unittest2.json) contains multiple
695 // entries with a common prefix. Test that the lookup methods can find all
696 // entries and correctly decode the different preloaded states (HSTS and HPKP)
697 // for each entry.
TEST_F(TransportSecurityStateTest,DecodePreloadedMultiplePrefix)698 TEST_F(TransportSecurityStateTest, DecodePreloadedMultiplePrefix) {
699 base::test::ScopedFeatureList scoped_feature_list_;
700 scoped_feature_list_.InitAndEnableFeature(
701 features::kStaticKeyPinningEnforcement);
702 SetTransportSecurityStateSourceForTesting(&test2::kHSTSSource);
703
704 TransportSecurityState state;
705 TransportSecurityStateTest::EnableStaticPins(&state);
706
707 TransportSecurityState::STSState sts_state;
708 TransportSecurityState::PKPState pkp_state;
709
710 EXPECT_TRUE(
711 GetStaticDomainState(&state, "hsts.example.com", &sts_state, &pkp_state));
712 EXPECT_FALSE(sts_state.include_subdomains);
713 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
714 sts_state.upgrade_mode);
715 EXPECT_TRUE(pkp_state == TransportSecurityState::PKPState());
716
717 sts_state = TransportSecurityState::STSState();
718 pkp_state = TransportSecurityState::PKPState();
719 EXPECT_TRUE(
720 GetStaticDomainState(&state, "hpkp.example.com", &sts_state, &pkp_state));
721 EXPECT_TRUE(sts_state == TransportSecurityState::STSState());
722 EXPECT_TRUE(pkp_state.include_subdomains);
723 EXPECT_EQ(1U, pkp_state.spki_hashes.size());
724 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x1));
725 EXPECT_EQ(0U, pkp_state.bad_spki_hashes.size());
726
727 sts_state = TransportSecurityState::STSState();
728 pkp_state = TransportSecurityState::PKPState();
729 EXPECT_TRUE(
730 GetStaticDomainState(&state, "mix.example.com", &sts_state, &pkp_state));
731 EXPECT_FALSE(sts_state.include_subdomains);
732 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
733 sts_state.upgrade_mode);
734 EXPECT_TRUE(pkp_state.include_subdomains);
735 EXPECT_EQ(1U, pkp_state.spki_hashes.size());
736 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x2));
737 EXPECT_EQ(1U, pkp_state.bad_spki_hashes.size());
738 EXPECT_EQ(pkp_state.bad_spki_hashes[0], GetSampleSPKIHash(0x1));
739 }
740
741 // More advanced test for the HSTS preload process where the trie (generated
742 // from transport_security_state_static_unittest3.json) contains a mix of
743 // entries. Some entries share a prefix with the prefix also having its own
744 // preloaded state while others share no prefix. This results in a trie with
745 // several different internal structures. Test that the lookup methods can find
746 // all entries and correctly decode the different preloaded states (HSTS and
747 // HPKP) for each entry.
TEST_F(TransportSecurityStateTest,DecodePreloadedMultipleMix)748 TEST_F(TransportSecurityStateTest, DecodePreloadedMultipleMix) {
749 base::test::ScopedFeatureList scoped_feature_list_;
750 scoped_feature_list_.InitAndEnableFeature(
751 features::kStaticKeyPinningEnforcement);
752 SetTransportSecurityStateSourceForTesting(&test3::kHSTSSource);
753
754 TransportSecurityState state;
755 TransportSecurityStateTest::EnableStaticPins(&state);
756
757 TransportSecurityState::STSState sts_state;
758 TransportSecurityState::PKPState pkp_state;
759
760 EXPECT_TRUE(
761 GetStaticDomainState(&state, "example.com", &sts_state, &pkp_state));
762 EXPECT_TRUE(sts_state.include_subdomains);
763 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
764 sts_state.upgrade_mode);
765 EXPECT_TRUE(pkp_state == TransportSecurityState::PKPState());
766
767 sts_state = TransportSecurityState::STSState();
768 pkp_state = TransportSecurityState::PKPState();
769 EXPECT_TRUE(
770 GetStaticDomainState(&state, "hpkp.example.com", &sts_state, &pkp_state));
771 EXPECT_TRUE(sts_state == TransportSecurityState::STSState());
772 EXPECT_TRUE(pkp_state.include_subdomains);
773 EXPECT_EQ(1U, pkp_state.spki_hashes.size());
774 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x1));
775 EXPECT_EQ(0U, pkp_state.bad_spki_hashes.size());
776
777 sts_state = TransportSecurityState::STSState();
778 pkp_state = TransportSecurityState::PKPState();
779 EXPECT_TRUE(
780 GetStaticDomainState(&state, "example.org", &sts_state, &pkp_state));
781 EXPECT_FALSE(sts_state.include_subdomains);
782 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
783 sts_state.upgrade_mode);
784 EXPECT_TRUE(pkp_state == TransportSecurityState::PKPState());
785
786 sts_state = TransportSecurityState::STSState();
787 pkp_state = TransportSecurityState::PKPState();
788 EXPECT_TRUE(
789 GetStaticDomainState(&state, "badssl.com", &sts_state, &pkp_state));
790 EXPECT_TRUE(sts_state == TransportSecurityState::STSState());
791 EXPECT_TRUE(pkp_state.include_subdomains);
792 EXPECT_EQ(1U, pkp_state.spki_hashes.size());
793 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x1));
794 EXPECT_EQ(0U, pkp_state.bad_spki_hashes.size());
795
796 sts_state = TransportSecurityState::STSState();
797 pkp_state = TransportSecurityState::PKPState();
798 EXPECT_TRUE(
799 GetStaticDomainState(&state, "mix.badssl.com", &sts_state, &pkp_state));
800 EXPECT_FALSE(sts_state.include_subdomains);
801 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
802 sts_state.upgrade_mode);
803 EXPECT_TRUE(pkp_state.include_subdomains);
804 EXPECT_EQ(1U, pkp_state.spki_hashes.size());
805 EXPECT_EQ(pkp_state.spki_hashes[0], GetSampleSPKIHash(0x2));
806 EXPECT_EQ(1U, pkp_state.bad_spki_hashes.size());
807 EXPECT_EQ(pkp_state.bad_spki_hashes[0], GetSampleSPKIHash(0x1));
808
809 sts_state = TransportSecurityState::STSState();
810 pkp_state = TransportSecurityState::PKPState();
811
812 // This should be a simple entry in the context of
813 // TrieWriter::IsSimpleEntry().
814 EXPECT_TRUE(GetStaticDomainState(&state, "simple-entry.example.com",
815 &sts_state, &pkp_state));
816 EXPECT_TRUE(sts_state.include_subdomains);
817 EXPECT_EQ(TransportSecurityState::STSState::MODE_FORCE_HTTPS,
818 sts_state.upgrade_mode);
819 EXPECT_TRUE(pkp_state == TransportSecurityState::PKPState());
820 }
821
TEST_F(TransportSecurityStateTest,HstsHostBypassList)822 TEST_F(TransportSecurityStateTest, HstsHostBypassList) {
823 SetTransportSecurityStateSourceForTesting(&test_default::kHSTSSource);
824
825 TransportSecurityState::STSState sts_state;
826 TransportSecurityState::PKPState pkp_state;
827
828 std::string preloaded_tld = "example";
829 std::string subdomain = "sub.example";
830
831 {
832 TransportSecurityState state;
833 // Check that "example" is preloaded with subdomains.
834 EXPECT_TRUE(state.ShouldUpgradeToSSL(preloaded_tld));
835 EXPECT_TRUE(state.ShouldUpgradeToSSL(subdomain));
836 }
837
838 {
839 // Add "example" to the bypass list.
840 TransportSecurityState state({preloaded_tld});
841 EXPECT_FALSE(state.ShouldUpgradeToSSL(preloaded_tld));
842 // The preloaded entry should still apply to the subdomain.
843 EXPECT_TRUE(state.ShouldUpgradeToSSL(subdomain));
844 }
845 }
846
847 // Tests that TransportSecurityState always consults the RequireCTDelegate,
848 // if supplied.
TEST_F(TransportSecurityStateTest,RequireCTConsultsDelegate)849 TEST_F(TransportSecurityStateTest, RequireCTConsultsDelegate) {
850 using ::testing::_;
851 using ::testing::Return;
852 using CTRequirementLevel =
853 TransportSecurityState::RequireCTDelegate::CTRequirementLevel;
854
855 // Dummy cert to use as the validation chain. The contents do not matter.
856 scoped_refptr<X509Certificate> cert =
857 ImportCertFromFile(GetTestCertsDirectory(), "expired_cert.pem");
858 ASSERT_TRUE(cert);
859
860 HashValueVector hashes;
861 hashes.push_back(
862 HashValue(X509Certificate::CalculateFingerprint256(cert->cert_buffer())));
863
864 // If CT is required, then the requirements are not met if the CT policy
865 // wasn't met, but are met if the policy was met or the build was out of
866 // date.
867 {
868 TransportSecurityState state;
869 const TransportSecurityState::CTRequirementsStatus original_status =
870 state.CheckCTRequirements(
871 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
872 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS);
873
874 MockRequireCTDelegate always_require_delegate;
875 EXPECT_CALL(always_require_delegate, IsCTRequiredForHost(_, _, _))
876 .WillRepeatedly(Return(CTRequirementLevel::REQUIRED));
877 state.SetRequireCTDelegate(&always_require_delegate);
878 EXPECT_EQ(
879 TransportSecurityState::CT_REQUIREMENTS_NOT_MET,
880 state.CheckCTRequirements(
881 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
882 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
883 EXPECT_EQ(
884 TransportSecurityState::CT_REQUIREMENTS_NOT_MET,
885 state.CheckCTRequirements(
886 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
887 ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS));
888 EXPECT_EQ(
889 TransportSecurityState::CT_REQUIREMENTS_MET,
890 state.CheckCTRequirements(
891 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
892 ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS));
893 EXPECT_EQ(
894 TransportSecurityState::CT_REQUIREMENTS_MET,
895 state.CheckCTRequirements(
896 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
897 ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY));
898
899 state.SetRequireCTDelegate(nullptr);
900 EXPECT_EQ(
901 original_status,
902 state.CheckCTRequirements(
903 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
904 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
905 }
906
907 // If CT is not required, then regardless of the CT state for the host,
908 // it should indicate CT is not required.
909 {
910 TransportSecurityState state;
911 const TransportSecurityState::CTRequirementsStatus original_status =
912 state.CheckCTRequirements(
913 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
914 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS);
915
916 MockRequireCTDelegate never_require_delegate;
917 EXPECT_CALL(never_require_delegate, IsCTRequiredForHost(_, _, _))
918 .WillRepeatedly(Return(CTRequirementLevel::NOT_REQUIRED));
919 state.SetRequireCTDelegate(&never_require_delegate);
920 EXPECT_EQ(
921 TransportSecurityState::CT_NOT_REQUIRED,
922 state.CheckCTRequirements(
923 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
924 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
925 EXPECT_EQ(
926 TransportSecurityState::CT_NOT_REQUIRED,
927 state.CheckCTRequirements(
928 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
929 ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS));
930
931 state.SetRequireCTDelegate(nullptr);
932 EXPECT_EQ(
933 original_status,
934 state.CheckCTRequirements(
935 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
936 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
937 }
938 }
939
940 // Tests that the emergency disable flags cause CT to stop being required
941 // regardless of host or delegate status.
TEST(CTEmergencyDisableTest,CTEmergencyDisable)942 TEST(CTEmergencyDisableTest, CTEmergencyDisable) {
943 using ::testing::_;
944 using ::testing::Return;
945 using CTRequirementLevel =
946 TransportSecurityState::RequireCTDelegate::CTRequirementLevel;
947
948 // Dummy cert to use as the validation chain. The contents do not matter.
949 scoped_refptr<X509Certificate> cert =
950 ImportCertFromFile(GetTestCertsDirectory(), "expired_cert.pem");
951 ASSERT_TRUE(cert);
952
953 HashValueVector hashes;
954 hashes.push_back(
955 HashValue(X509Certificate::CalculateFingerprint256(cert->cert_buffer())));
956
957 TransportSecurityState state;
958 state.SetCTEmergencyDisabled(true);
959
960 MockRequireCTDelegate always_require_delegate;
961 EXPECT_CALL(always_require_delegate, IsCTRequiredForHost(_, _, _))
962 .WillRepeatedly(Return(CTRequirementLevel::REQUIRED));
963 state.SetRequireCTDelegate(&always_require_delegate);
964 EXPECT_EQ(TransportSecurityState::CT_NOT_REQUIRED,
965 state.CheckCTRequirements(
966 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
967 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
968 EXPECT_EQ(TransportSecurityState::CT_NOT_REQUIRED,
969 state.CheckCTRequirements(
970 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
971 ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS));
972 EXPECT_EQ(TransportSecurityState::CT_NOT_REQUIRED,
973 state.CheckCTRequirements(
974 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
975 ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS));
976 EXPECT_EQ(TransportSecurityState::CT_NOT_REQUIRED,
977 state.CheckCTRequirements(
978 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
979 ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY));
980
981 state.SetRequireCTDelegate(nullptr);
982 EXPECT_EQ(TransportSecurityState::CT_NOT_REQUIRED,
983 state.CheckCTRequirements(
984 HostPortPair("www.example.com", 443), true, hashes, cert.get(),
985 ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS));
986 }
987
988 #if BUILDFLAG(INCLUDE_TRANSPORT_SECURITY_STATE_PRELOAD_LIST)
989
990 class TransportSecurityStateStaticTest : public TransportSecurityStateTest {
991 public:
TransportSecurityStateStaticTest()992 TransportSecurityStateStaticTest() {
993 SetTransportSecurityStateSourceForTesting(nullptr);
994 }
995 };
996
StaticShouldRedirect(const char * hostname)997 static bool StaticShouldRedirect(const char* hostname) {
998 TransportSecurityState state;
999 TransportSecurityState::STSState sts_state;
1000 return state.GetStaticSTSState(hostname, &sts_state) &&
1001 sts_state.ShouldUpgradeToSSL();
1002 }
1003
HasStaticState(const char * hostname)1004 static bool HasStaticState(const char* hostname) {
1005 TransportSecurityState state;
1006 state.SetPinningListAlwaysTimelyForTesting(true);
1007 TransportSecurityState::STSState sts_state;
1008 TransportSecurityState::PKPState pkp_state;
1009 return state.GetStaticSTSState(hostname, &sts_state) ||
1010 state.GetStaticPKPState(hostname, &pkp_state);
1011 }
1012
HasStaticPublicKeyPins(const char * hostname)1013 static bool HasStaticPublicKeyPins(const char* hostname) {
1014 TransportSecurityState state;
1015 state.SetPinningListAlwaysTimelyForTesting(true);
1016 TransportSecurityStateTest::EnableStaticPins(&state);
1017 TransportSecurityState::PKPState pkp_state;
1018 if (!state.GetStaticPKPState(hostname, &pkp_state))
1019 return false;
1020
1021 return pkp_state.HasPublicKeyPins();
1022 }
1023
OnlyPinningInStaticState(const char * hostname)1024 static bool OnlyPinningInStaticState(const char* hostname) {
1025 TransportSecurityState state;
1026 TransportSecurityStateTest::EnableStaticPins(&state);
1027 TransportSecurityState::STSState sts_state;
1028 TransportSecurityState::PKPState pkp_state;
1029 return HasStaticPublicKeyPins(hostname) && !StaticShouldRedirect(hostname);
1030 }
1031
TEST_F(TransportSecurityStateStaticTest,EnableStaticPins)1032 TEST_F(TransportSecurityStateStaticTest, EnableStaticPins) {
1033 base::test::ScopedFeatureList scoped_feature_list_;
1034 scoped_feature_list_.InitAndEnableFeature(
1035 features::kStaticKeyPinningEnforcement);
1036 TransportSecurityState state;
1037 state.SetPinningListAlwaysTimelyForTesting(true);
1038 TransportSecurityState::PKPState pkp_state;
1039
1040 EnableStaticPins(&state);
1041
1042 EXPECT_TRUE(state.GetStaticPKPState("chrome.google.com", &pkp_state));
1043 EXPECT_FALSE(pkp_state.spki_hashes.empty());
1044 }
1045
TEST_F(TransportSecurityStateStaticTest,DisableStaticPins)1046 TEST_F(TransportSecurityStateStaticTest, DisableStaticPins) {
1047 TransportSecurityState state;
1048 state.SetPinningListAlwaysTimelyForTesting(true);
1049 TransportSecurityState::PKPState pkp_state;
1050
1051 DisableStaticPins(&state);
1052 EXPECT_FALSE(state.GetStaticPKPState("chrome.google.com", &pkp_state));
1053 EXPECT_TRUE(pkp_state.spki_hashes.empty());
1054 }
1055
TEST_F(TransportSecurityStateStaticTest,IsPreloaded)1056 TEST_F(TransportSecurityStateStaticTest, IsPreloaded) {
1057 const std::string paypal = "paypal.com";
1058 const std::string www_paypal = "www.paypal.com";
1059 const std::string foo_paypal = "foo.paypal.com";
1060 const std::string a_www_paypal = "a.www.paypal.com";
1061 const std::string abc_paypal = "a.b.c.paypal.com";
1062 const std::string example = "example.com";
1063 const std::string aypal = "aypal.com";
1064 const std::string google = "google";
1065 const std::string www_google = "www.google";
1066 const std::string foo = "foo";
1067 const std::string bank = "example.bank";
1068 const std::string insurance = "sub.example.insurance";
1069
1070 TransportSecurityState state;
1071 TransportSecurityState::STSState sts_state;
1072 TransportSecurityState::PKPState pkp_state;
1073
1074 EXPECT_TRUE(GetStaticDomainState(&state, paypal, &sts_state, &pkp_state));
1075 EXPECT_TRUE(GetStaticDomainState(&state, www_paypal, &sts_state, &pkp_state));
1076 EXPECT_FALSE(sts_state.include_subdomains);
1077 EXPECT_TRUE(GetStaticDomainState(&state, google, &sts_state, &pkp_state));
1078 EXPECT_TRUE(GetStaticDomainState(&state, www_google, &sts_state, &pkp_state));
1079 EXPECT_TRUE(GetStaticDomainState(&state, foo, &sts_state, &pkp_state));
1080 EXPECT_TRUE(GetStaticDomainState(&state, bank, &sts_state, &pkp_state));
1081 EXPECT_TRUE(sts_state.include_subdomains);
1082 EXPECT_TRUE(GetStaticDomainState(&state, insurance, &sts_state, &pkp_state));
1083 EXPECT_TRUE(sts_state.include_subdomains);
1084 EXPECT_FALSE(
1085 GetStaticDomainState(&state, a_www_paypal, &sts_state, &pkp_state));
1086 EXPECT_FALSE(
1087 GetStaticDomainState(&state, abc_paypal, &sts_state, &pkp_state));
1088 EXPECT_FALSE(GetStaticDomainState(&state, example, &sts_state, &pkp_state));
1089 EXPECT_FALSE(GetStaticDomainState(&state, aypal, &sts_state, &pkp_state));
1090 }
1091
TEST_F(TransportSecurityStateStaticTest,PreloadedDomainSet)1092 TEST_F(TransportSecurityStateStaticTest, PreloadedDomainSet) {
1093 base::test::ScopedFeatureList scoped_feature_list_;
1094 scoped_feature_list_.InitAndEnableFeature(
1095 features::kStaticKeyPinningEnforcement);
1096 TransportSecurityState state;
1097 EnableStaticPins(&state);
1098 TransportSecurityState::STSState sts_state;
1099 TransportSecurityState::PKPState pkp_state;
1100
1101 // The domain wasn't being set, leading to a blank string in the
1102 // chrome://net-internals/#hsts UI. So test that.
1103 EXPECT_TRUE(state.GetStaticPKPState("market.android.com", &pkp_state));
1104 EXPECT_TRUE(state.GetStaticSTSState("market.android.com", &sts_state));
1105 EXPECT_EQ(sts_state.domain, "market.android.com");
1106 EXPECT_EQ(pkp_state.domain, "market.android.com");
1107 EXPECT_TRUE(state.GetStaticPKPState("sub.market.android.com", &pkp_state));
1108 EXPECT_TRUE(state.GetStaticSTSState("sub.market.android.com", &sts_state));
1109 EXPECT_EQ(sts_state.domain, "market.android.com");
1110 EXPECT_EQ(pkp_state.domain, "market.android.com");
1111 }
1112
TEST_F(TransportSecurityStateStaticTest,Preloaded)1113 TEST_F(TransportSecurityStateStaticTest, Preloaded) {
1114 base::test::ScopedFeatureList scoped_feature_list_;
1115 scoped_feature_list_.InitAndEnableFeature(
1116 features::kStaticKeyPinningEnforcement);
1117 TransportSecurityState state;
1118 EnableStaticPins(&state);
1119 TransportSecurityState::STSState sts_state;
1120 TransportSecurityState::PKPState pkp_state;
1121
1122 // We do more extensive checks for the first domain.
1123 EXPECT_TRUE(state.GetStaticSTSState("www.paypal.com", &sts_state));
1124 EXPECT_FALSE(state.GetStaticPKPState("www.paypal.com", &pkp_state));
1125 EXPECT_EQ(sts_state.upgrade_mode,
1126 TransportSecurityState::STSState::MODE_FORCE_HTTPS);
1127 EXPECT_FALSE(sts_state.include_subdomains);
1128 EXPECT_FALSE(pkp_state.include_subdomains);
1129
1130 EXPECT_TRUE(HasStaticState("paypal.com"));
1131 EXPECT_FALSE(HasStaticState("www2.paypal.com"));
1132
1133 // Google hosts:
1134
1135 EXPECT_TRUE(StaticShouldRedirect("chrome.google.com"));
1136 EXPECT_TRUE(StaticShouldRedirect("checkout.google.com"));
1137 EXPECT_TRUE(StaticShouldRedirect("wallet.google.com"));
1138 EXPECT_TRUE(StaticShouldRedirect("docs.google.com"));
1139 EXPECT_TRUE(StaticShouldRedirect("sites.google.com"));
1140 EXPECT_TRUE(StaticShouldRedirect("drive.google.com"));
1141 EXPECT_TRUE(StaticShouldRedirect("spreadsheets.google.com"));
1142 EXPECT_TRUE(StaticShouldRedirect("appengine.google.com"));
1143 EXPECT_TRUE(StaticShouldRedirect("market.android.com"));
1144 EXPECT_TRUE(StaticShouldRedirect("encrypted.google.com"));
1145 EXPECT_TRUE(StaticShouldRedirect("accounts.google.com"));
1146 EXPECT_TRUE(StaticShouldRedirect("profiles.google.com"));
1147 EXPECT_TRUE(StaticShouldRedirect("mail.google.com"));
1148 EXPECT_TRUE(StaticShouldRedirect("chatenabled.mail.google.com"));
1149 EXPECT_TRUE(StaticShouldRedirect("talkgadget.google.com"));
1150 EXPECT_TRUE(StaticShouldRedirect("hostedtalkgadget.google.com"));
1151 EXPECT_TRUE(StaticShouldRedirect("talk.google.com"));
1152 EXPECT_TRUE(StaticShouldRedirect("plus.google.com"));
1153 EXPECT_TRUE(StaticShouldRedirect("groups.google.com"));
1154 EXPECT_TRUE(StaticShouldRedirect("apis.google.com"));
1155 EXPECT_TRUE(StaticShouldRedirect("oauthaccountmanager.googleapis.com"));
1156 EXPECT_TRUE(StaticShouldRedirect("passwordsleakcheck-pa.googleapis.com"));
1157 EXPECT_TRUE(StaticShouldRedirect("ssl.google-analytics.com"));
1158 EXPECT_TRUE(StaticShouldRedirect("google"));
1159 EXPECT_TRUE(StaticShouldRedirect("foo.google"));
1160 EXPECT_TRUE(StaticShouldRedirect("foo"));
1161 EXPECT_TRUE(StaticShouldRedirect("domaintest.foo"));
1162 EXPECT_TRUE(StaticShouldRedirect("gmail.com"));
1163 EXPECT_TRUE(StaticShouldRedirect("www.gmail.com"));
1164 EXPECT_TRUE(StaticShouldRedirect("googlemail.com"));
1165 EXPECT_TRUE(StaticShouldRedirect("www.googlemail.com"));
1166 EXPECT_TRUE(StaticShouldRedirect("googleplex.com"));
1167 EXPECT_TRUE(StaticShouldRedirect("www.googleplex.com"));
1168 EXPECT_TRUE(StaticShouldRedirect("www.google-analytics.com"));
1169 EXPECT_TRUE(StaticShouldRedirect("www.youtube.com"));
1170 EXPECT_TRUE(StaticShouldRedirect("youtube.com"));
1171
1172 // These domains used to be only HSTS when SNI was available.
1173 EXPECT_TRUE(state.GetStaticSTSState("gmail.com", &sts_state));
1174 EXPECT_TRUE(state.GetStaticPKPState("gmail.com", &pkp_state));
1175 EXPECT_TRUE(state.GetStaticSTSState("www.gmail.com", &sts_state));
1176 EXPECT_TRUE(state.GetStaticPKPState("www.gmail.com", &pkp_state));
1177 EXPECT_TRUE(state.GetStaticSTSState("googlemail.com", &sts_state));
1178 EXPECT_TRUE(state.GetStaticPKPState("googlemail.com", &pkp_state));
1179 EXPECT_TRUE(state.GetStaticSTSState("www.googlemail.com", &sts_state));
1180 EXPECT_TRUE(state.GetStaticPKPState("www.googlemail.com", &pkp_state));
1181
1182 // fi.g.co should not force HTTPS because there are still HTTP-only services
1183 // on it.
1184 EXPECT_FALSE(StaticShouldRedirect("fi.g.co"));
1185
1186 // Other hosts:
1187
1188 EXPECT_TRUE(StaticShouldRedirect("aladdinschools.appspot.com"));
1189
1190 EXPECT_TRUE(StaticShouldRedirect("ottospora.nl"));
1191 EXPECT_TRUE(StaticShouldRedirect("www.ottospora.nl"));
1192
1193 EXPECT_TRUE(StaticShouldRedirect("www.paycheckrecords.com"));
1194
1195 EXPECT_TRUE(StaticShouldRedirect("lastpass.com"));
1196 EXPECT_TRUE(StaticShouldRedirect("www.lastpass.com"));
1197 EXPECT_FALSE(HasStaticState("blog.lastpass.com"));
1198
1199 EXPECT_TRUE(StaticShouldRedirect("keyerror.com"));
1200 EXPECT_TRUE(StaticShouldRedirect("www.keyerror.com"));
1201
1202 EXPECT_TRUE(StaticShouldRedirect("entropia.de"));
1203 EXPECT_TRUE(StaticShouldRedirect("www.entropia.de"));
1204 EXPECT_FALSE(HasStaticState("foo.entropia.de"));
1205
1206 EXPECT_TRUE(StaticShouldRedirect("www.elanex.biz"));
1207 EXPECT_FALSE(HasStaticState("elanex.biz"));
1208 EXPECT_FALSE(HasStaticState("foo.elanex.biz"));
1209
1210 EXPECT_TRUE(StaticShouldRedirect("sunshinepress.org"));
1211 EXPECT_TRUE(StaticShouldRedirect("www.sunshinepress.org"));
1212 EXPECT_TRUE(StaticShouldRedirect("a.b.sunshinepress.org"));
1213
1214 EXPECT_TRUE(StaticShouldRedirect("www.noisebridge.net"));
1215 EXPECT_FALSE(HasStaticState("noisebridge.net"));
1216 EXPECT_FALSE(HasStaticState("foo.noisebridge.net"));
1217
1218 EXPECT_TRUE(StaticShouldRedirect("neg9.org"));
1219 EXPECT_FALSE(HasStaticState("www.neg9.org"));
1220
1221 EXPECT_TRUE(StaticShouldRedirect("riseup.net"));
1222 EXPECT_TRUE(StaticShouldRedirect("foo.riseup.net"));
1223
1224 EXPECT_TRUE(StaticShouldRedirect("factor.cc"));
1225 EXPECT_FALSE(HasStaticState("www.factor.cc"));
1226
1227 EXPECT_TRUE(StaticShouldRedirect("members.mayfirst.org"));
1228 EXPECT_TRUE(StaticShouldRedirect("support.mayfirst.org"));
1229 EXPECT_TRUE(StaticShouldRedirect("id.mayfirst.org"));
1230 EXPECT_TRUE(StaticShouldRedirect("lists.mayfirst.org"));
1231 EXPECT_FALSE(HasStaticState("www.mayfirst.org"));
1232
1233 EXPECT_TRUE(StaticShouldRedirect("romab.com"));
1234 EXPECT_TRUE(StaticShouldRedirect("www.romab.com"));
1235 EXPECT_TRUE(StaticShouldRedirect("foo.romab.com"));
1236
1237 EXPECT_TRUE(StaticShouldRedirect("logentries.com"));
1238 EXPECT_TRUE(StaticShouldRedirect("www.logentries.com"));
1239 EXPECT_FALSE(HasStaticState("foo.logentries.com"));
1240
1241 EXPECT_TRUE(StaticShouldRedirect("stripe.com"));
1242 EXPECT_TRUE(StaticShouldRedirect("foo.stripe.com"));
1243
1244 EXPECT_TRUE(StaticShouldRedirect("cloudsecurityalliance.org"));
1245 EXPECT_TRUE(StaticShouldRedirect("foo.cloudsecurityalliance.org"));
1246
1247 EXPECT_TRUE(StaticShouldRedirect("login.sapo.pt"));
1248 EXPECT_TRUE(StaticShouldRedirect("foo.login.sapo.pt"));
1249
1250 EXPECT_TRUE(StaticShouldRedirect("mattmccutchen.net"));
1251 EXPECT_TRUE(StaticShouldRedirect("foo.mattmccutchen.net"));
1252
1253 EXPECT_TRUE(StaticShouldRedirect("betnet.fr"));
1254 EXPECT_TRUE(StaticShouldRedirect("foo.betnet.fr"));
1255
1256 EXPECT_TRUE(StaticShouldRedirect("uprotect.it"));
1257 EXPECT_TRUE(StaticShouldRedirect("foo.uprotect.it"));
1258
1259 EXPECT_TRUE(StaticShouldRedirect("cert.se"));
1260 EXPECT_TRUE(StaticShouldRedirect("foo.cert.se"));
1261
1262 EXPECT_TRUE(StaticShouldRedirect("crypto.is"));
1263 EXPECT_TRUE(StaticShouldRedirect("foo.crypto.is"));
1264
1265 EXPECT_TRUE(StaticShouldRedirect("simon.butcher.name"));
1266 EXPECT_TRUE(StaticShouldRedirect("foo.simon.butcher.name"));
1267
1268 EXPECT_TRUE(StaticShouldRedirect("linx.net"));
1269 EXPECT_TRUE(StaticShouldRedirect("foo.linx.net"));
1270
1271 EXPECT_TRUE(StaticShouldRedirect("dropcam.com"));
1272 EXPECT_TRUE(StaticShouldRedirect("www.dropcam.com"));
1273 EXPECT_FALSE(HasStaticState("foo.dropcam.com"));
1274
1275 EXPECT_TRUE(StaticShouldRedirect("ebanking.indovinabank.com.vn"));
1276 EXPECT_TRUE(StaticShouldRedirect("foo.ebanking.indovinabank.com.vn"));
1277
1278 EXPECT_TRUE(StaticShouldRedirect("epoxate.com"));
1279 EXPECT_FALSE(HasStaticState("foo.epoxate.com"));
1280
1281 EXPECT_TRUE(StaticShouldRedirect("www.moneybookers.com"));
1282 EXPECT_FALSE(HasStaticState("moneybookers.com"));
1283
1284 EXPECT_TRUE(StaticShouldRedirect("ledgerscope.net"));
1285 EXPECT_TRUE(StaticShouldRedirect("www.ledgerscope.net"));
1286 EXPECT_FALSE(HasStaticState("status.ledgerscope.net"));
1287
1288 EXPECT_TRUE(StaticShouldRedirect("foo.app.recurly.com"));
1289 EXPECT_TRUE(StaticShouldRedirect("foo.api.recurly.com"));
1290
1291 EXPECT_TRUE(StaticShouldRedirect("greplin.com"));
1292 EXPECT_TRUE(StaticShouldRedirect("www.greplin.com"));
1293 EXPECT_FALSE(HasStaticState("foo.greplin.com"));
1294
1295 EXPECT_TRUE(StaticShouldRedirect("luneta.nearbuysystems.com"));
1296 EXPECT_TRUE(StaticShouldRedirect("foo.luneta.nearbuysystems.com"));
1297
1298 EXPECT_TRUE(StaticShouldRedirect("ubertt.org"));
1299 EXPECT_TRUE(StaticShouldRedirect("foo.ubertt.org"));
1300
1301 EXPECT_TRUE(StaticShouldRedirect("pixi.me"));
1302 EXPECT_TRUE(StaticShouldRedirect("www.pixi.me"));
1303
1304 EXPECT_TRUE(StaticShouldRedirect("grepular.com"));
1305 EXPECT_TRUE(StaticShouldRedirect("www.grepular.com"));
1306
1307 EXPECT_TRUE(StaticShouldRedirect("mydigipass.com"));
1308 EXPECT_FALSE(StaticShouldRedirect("foo.mydigipass.com"));
1309 EXPECT_TRUE(StaticShouldRedirect("www.mydigipass.com"));
1310 EXPECT_FALSE(StaticShouldRedirect("foo.www.mydigipass.com"));
1311 EXPECT_TRUE(StaticShouldRedirect("developer.mydigipass.com"));
1312 EXPECT_FALSE(StaticShouldRedirect("foo.developer.mydigipass.com"));
1313 EXPECT_TRUE(StaticShouldRedirect("www.developer.mydigipass.com"));
1314 EXPECT_FALSE(StaticShouldRedirect("foo.www.developer.mydigipass.com"));
1315 EXPECT_TRUE(StaticShouldRedirect("sandbox.mydigipass.com"));
1316 EXPECT_FALSE(StaticShouldRedirect("foo.sandbox.mydigipass.com"));
1317 EXPECT_TRUE(StaticShouldRedirect("www.sandbox.mydigipass.com"));
1318 EXPECT_FALSE(StaticShouldRedirect("foo.www.sandbox.mydigipass.com"));
1319
1320 EXPECT_TRUE(StaticShouldRedirect("bigshinylock.minazo.net"));
1321 EXPECT_TRUE(StaticShouldRedirect("foo.bigshinylock.minazo.net"));
1322
1323 EXPECT_TRUE(StaticShouldRedirect("crate.io"));
1324 EXPECT_TRUE(StaticShouldRedirect("foo.crate.io"));
1325
1326 EXPECT_TRUE(StaticShouldRedirect("sub.bank"));
1327 EXPECT_TRUE(StaticShouldRedirect("sub.insurance"));
1328 }
1329
TEST_F(TransportSecurityStateStaticTest,PreloadedPins)1330 TEST_F(TransportSecurityStateStaticTest, PreloadedPins) {
1331 base::test::ScopedFeatureList scoped_feature_list_;
1332 scoped_feature_list_.InitAndEnableFeature(
1333 features::kStaticKeyPinningEnforcement);
1334 TransportSecurityState state;
1335 EnableStaticPins(&state);
1336 TransportSecurityState::STSState sts_state;
1337 TransportSecurityState::PKPState pkp_state;
1338
1339 // We do more extensive checks for the first domain.
1340 EXPECT_TRUE(state.GetStaticSTSState("www.paypal.com", &sts_state));
1341 EXPECT_FALSE(state.GetStaticPKPState("www.paypal.com", &pkp_state));
1342 EXPECT_EQ(sts_state.upgrade_mode,
1343 TransportSecurityState::STSState::MODE_FORCE_HTTPS);
1344 EXPECT_FALSE(sts_state.include_subdomains);
1345 EXPECT_FALSE(pkp_state.include_subdomains);
1346
1347 EXPECT_TRUE(OnlyPinningInStaticState("www.google.com"));
1348 EXPECT_TRUE(OnlyPinningInStaticState("foo.google.com"));
1349 EXPECT_TRUE(OnlyPinningInStaticState("google.com"));
1350 EXPECT_TRUE(OnlyPinningInStaticState("i.ytimg.com"));
1351 EXPECT_TRUE(OnlyPinningInStaticState("ytimg.com"));
1352 EXPECT_TRUE(OnlyPinningInStaticState("googleusercontent.com"));
1353 EXPECT_TRUE(OnlyPinningInStaticState("www.googleusercontent.com"));
1354 EXPECT_TRUE(OnlyPinningInStaticState("googleapis.com"));
1355 EXPECT_TRUE(OnlyPinningInStaticState("googleadservices.com"));
1356 EXPECT_TRUE(OnlyPinningInStaticState("googlecode.com"));
1357 EXPECT_TRUE(OnlyPinningInStaticState("appspot.com"));
1358 EXPECT_TRUE(OnlyPinningInStaticState("googlesyndication.com"));
1359 EXPECT_TRUE(OnlyPinningInStaticState("doubleclick.net"));
1360 EXPECT_TRUE(OnlyPinningInStaticState("googlegroups.com"));
1361
1362 // Facebook has pinning and hsts on facebook.com, but only pinning on
1363 // subdomains.
1364 EXPECT_TRUE(state.GetStaticPKPState("facebook.com", &pkp_state));
1365 EXPECT_FALSE(pkp_state.spki_hashes.empty());
1366 EXPECT_TRUE(StaticShouldRedirect("facebook.com"));
1367
1368 EXPECT_TRUE(state.GetStaticPKPState("foo.facebook.com", &pkp_state));
1369 EXPECT_FALSE(pkp_state.spki_hashes.empty());
1370 EXPECT_FALSE(StaticShouldRedirect("foo.facebook.com"));
1371
1372 // www.facebook.com and subdomains have both pinning and hsts.
1373 EXPECT_TRUE(state.GetStaticPKPState("www.facebook.com", &pkp_state));
1374 EXPECT_FALSE(pkp_state.spki_hashes.empty());
1375 EXPECT_TRUE(StaticShouldRedirect("www.facebook.com"));
1376
1377 EXPECT_TRUE(state.GetStaticPKPState("foo.www.facebook.com", &pkp_state));
1378 EXPECT_FALSE(pkp_state.spki_hashes.empty());
1379 EXPECT_TRUE(StaticShouldRedirect("foo.www.facebook.com"));
1380 }
1381
TEST_F(TransportSecurityStateStaticTest,BuiltinCertPins)1382 TEST_F(TransportSecurityStateStaticTest, BuiltinCertPins) {
1383 base::test::ScopedFeatureList scoped_feature_list_;
1384 scoped_feature_list_.InitAndEnableFeature(
1385 features::kStaticKeyPinningEnforcement);
1386 TransportSecurityState state;
1387 EnableStaticPins(&state);
1388 TransportSecurityState::PKPState pkp_state;
1389
1390 EXPECT_TRUE(state.GetStaticPKPState("chrome.google.com", &pkp_state));
1391 EXPECT_TRUE(HasStaticPublicKeyPins("chrome.google.com"));
1392
1393 HashValueVector hashes;
1394 // Checks that a built-in list does exist.
1395 EXPECT_FALSE(pkp_state.CheckPublicKeyPins(hashes));
1396 EXPECT_FALSE(HasStaticPublicKeyPins("www.paypal.com"));
1397
1398 EXPECT_TRUE(HasStaticPublicKeyPins("docs.google.com"));
1399 EXPECT_TRUE(HasStaticPublicKeyPins("1.docs.google.com"));
1400 EXPECT_TRUE(HasStaticPublicKeyPins("sites.google.com"));
1401 EXPECT_TRUE(HasStaticPublicKeyPins("drive.google.com"));
1402 EXPECT_TRUE(HasStaticPublicKeyPins("spreadsheets.google.com"));
1403 EXPECT_TRUE(HasStaticPublicKeyPins("wallet.google.com"));
1404 EXPECT_TRUE(HasStaticPublicKeyPins("checkout.google.com"));
1405 EXPECT_TRUE(HasStaticPublicKeyPins("appengine.google.com"));
1406 EXPECT_TRUE(HasStaticPublicKeyPins("market.android.com"));
1407 EXPECT_TRUE(HasStaticPublicKeyPins("encrypted.google.com"));
1408 EXPECT_TRUE(HasStaticPublicKeyPins("accounts.google.com"));
1409 EXPECT_TRUE(HasStaticPublicKeyPins("profiles.google.com"));
1410 EXPECT_TRUE(HasStaticPublicKeyPins("mail.google.com"));
1411 EXPECT_TRUE(HasStaticPublicKeyPins("chatenabled.mail.google.com"));
1412 EXPECT_TRUE(HasStaticPublicKeyPins("talkgadget.google.com"));
1413 EXPECT_TRUE(HasStaticPublicKeyPins("hostedtalkgadget.google.com"));
1414 EXPECT_TRUE(HasStaticPublicKeyPins("talk.google.com"));
1415 EXPECT_TRUE(HasStaticPublicKeyPins("plus.google.com"));
1416 EXPECT_TRUE(HasStaticPublicKeyPins("groups.google.com"));
1417 EXPECT_TRUE(HasStaticPublicKeyPins("apis.google.com"));
1418 EXPECT_TRUE(HasStaticPublicKeyPins("www.google-analytics.com"));
1419 EXPECT_TRUE(HasStaticPublicKeyPins("www.youtube.com"));
1420 EXPECT_TRUE(HasStaticPublicKeyPins("youtube.com"));
1421
1422 EXPECT_TRUE(HasStaticPublicKeyPins("ssl.gstatic.com"));
1423 EXPECT_TRUE(HasStaticPublicKeyPins("gstatic.com"));
1424 EXPECT_TRUE(HasStaticPublicKeyPins("www.gstatic.com"));
1425 EXPECT_TRUE(HasStaticPublicKeyPins("ssl.google-analytics.com"));
1426 EXPECT_TRUE(HasStaticPublicKeyPins("www.googleplex.com"));
1427 }
1428
TEST_F(TransportSecurityStateStaticTest,OptionalHSTSCertPins)1429 TEST_F(TransportSecurityStateStaticTest, OptionalHSTSCertPins) {
1430 base::test::ScopedFeatureList scoped_feature_list_;
1431 scoped_feature_list_.InitAndEnableFeature(
1432 features::kStaticKeyPinningEnforcement);
1433 TransportSecurityState state;
1434 EnableStaticPins(&state);
1435
1436 EXPECT_TRUE(HasStaticPublicKeyPins("google.com"));
1437 EXPECT_TRUE(HasStaticPublicKeyPins("www.google.com"));
1438 EXPECT_TRUE(HasStaticPublicKeyPins("mail-attachment.googleusercontent.com"));
1439 EXPECT_TRUE(HasStaticPublicKeyPins("www.youtube.com"));
1440 EXPECT_TRUE(HasStaticPublicKeyPins("i.ytimg.com"));
1441 EXPECT_TRUE(HasStaticPublicKeyPins("googleapis.com"));
1442 EXPECT_TRUE(HasStaticPublicKeyPins("ajax.googleapis.com"));
1443 EXPECT_TRUE(HasStaticPublicKeyPins("googleadservices.com"));
1444 EXPECT_TRUE(HasStaticPublicKeyPins("pagead2.googleadservices.com"));
1445 EXPECT_TRUE(HasStaticPublicKeyPins("googlecode.com"));
1446 EXPECT_TRUE(HasStaticPublicKeyPins("kibbles.googlecode.com"));
1447 EXPECT_TRUE(HasStaticPublicKeyPins("appspot.com"));
1448 EXPECT_TRUE(HasStaticPublicKeyPins("googlesyndication.com"));
1449 EXPECT_TRUE(HasStaticPublicKeyPins("doubleclick.net"));
1450 EXPECT_TRUE(HasStaticPublicKeyPins("ad.doubleclick.net"));
1451 EXPECT_TRUE(HasStaticPublicKeyPins("redirector.gvt1.com"));
1452 EXPECT_TRUE(HasStaticPublicKeyPins("a.googlegroups.com"));
1453 }
1454
TEST_F(TransportSecurityStateStaticTest,OverrideBuiltins)1455 TEST_F(TransportSecurityStateStaticTest, OverrideBuiltins) {
1456 base::test::ScopedFeatureList scoped_feature_list_;
1457 scoped_feature_list_.InitAndEnableFeature(
1458 features::kStaticKeyPinningEnforcement);
1459 EXPECT_TRUE(HasStaticPublicKeyPins("google.com"));
1460 EXPECT_FALSE(StaticShouldRedirect("google.com"));
1461 EXPECT_FALSE(StaticShouldRedirect("www.google.com"));
1462
1463 TransportSecurityState state;
1464 state.SetPinningListAlwaysTimelyForTesting(true);
1465
1466 const base::Time current_time(base::Time::Now());
1467 const base::Time expiry = current_time + base::Seconds(1000);
1468 state.AddHSTS("www.google.com", expiry, true);
1469
1470 EXPECT_TRUE(state.ShouldUpgradeToSSL("www.google.com"));
1471 }
1472
TEST_F(TransportSecurityStateTest,WriteSizeDecodeSize)1473 TEST_F(TransportSecurityStateTest, WriteSizeDecodeSize) {
1474 for (size_t i = 0; i < 300; ++i) {
1475 SCOPED_TRACE(i);
1476 huffman_trie::TrieBitBuffer buffer;
1477 buffer.WriteSize(i);
1478 huffman_trie::BitWriter writer;
1479 buffer.WriteToBitWriter(&writer);
1480 size_t position = writer.position();
1481 writer.Flush();
1482 ASSERT_NE(writer.bytes().data(), nullptr);
1483 extras::PreloadDecoder::BitReader reader(writer.bytes().data(), position);
1484 size_t decoded_size;
1485 EXPECT_TRUE(reader.DecodeSize(&decoded_size));
1486 EXPECT_EQ(i, decoded_size);
1487 }
1488 }
1489
TEST_F(TransportSecurityStateTest,DecodeSizeFour)1490 TEST_F(TransportSecurityStateTest, DecodeSizeFour) {
1491 // Test that BitReader::DecodeSize properly handles the number 4, including
1492 // not over-reading input bytes. BitReader::Next only fails if there's not
1493 // another byte to read from; if it reads past the number of bits in the
1494 // buffer but is still in the last byte it will still succeed. For this
1495 // reason, this test puts the encoding of 4 at the end of the byte to check
1496 // that DecodeSize doesn't over-read.
1497 //
1498 // 4 is encoded as 0b010. Shifted right to fill one byte, it is 0x02, with 5
1499 // bits of padding.
1500 uint8_t encoded = 0x02;
1501 extras::PreloadDecoder::BitReader reader(&encoded, 8);
1502 for (size_t i = 0; i < 5; ++i) {
1503 bool unused;
1504 ASSERT_TRUE(reader.Next(&unused));
1505 }
1506 size_t decoded_size;
1507 EXPECT_TRUE(reader.DecodeSize(&decoded_size));
1508 EXPECT_EQ(4u, decoded_size);
1509 }
1510
1511 #endif // BUILDFLAG(INCLUDE_TRANSPORT_SECURITY_STATE_PRELOAD_LIST)
1512
TEST_F(TransportSecurityStateTest,UpdateKeyPinsListValidPin)1513 TEST_F(TransportSecurityStateTest, UpdateKeyPinsListValidPin) {
1514 base::test::ScopedFeatureList scoped_feature_list_;
1515 scoped_feature_list_.InitAndEnableFeature(
1516 features::kStaticKeyPinningEnforcement);
1517 HostPortPair host_port_pair(kHost, kPort);
1518
1519 HashValueVector bad_hashes;
1520 for (size_t i = 0; kBadPath[i]; i++)
1521 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes));
1522
1523 TransportSecurityState state;
1524 EnableStaticPins(&state);
1525
1526 // Prior to updating the list, bad_hashes should be rejected.
1527 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1528 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1529
1530 // Update the pins list, adding bad_hashes to the accepted hashes for this
1531 // host.
1532 std::vector<std::vector<uint8_t>> accepted_hashes;
1533 for (size_t i = 0; kBadPath[i]; i++) {
1534 HashValue hash;
1535 ASSERT_TRUE(hash.FromString(kBadPath[i]));
1536 accepted_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1537 }
1538 TransportSecurityState::PinSet test_pinset(
1539 /*name=*/"test",
1540 /*static_spki_hashes=*/accepted_hashes,
1541 /*bad_static_spki_hashes=*/{});
1542 TransportSecurityState::PinSetInfo test_pinsetinfo(
1543 /*hostname=*/kHost, /*pinset_name=*/"test",
1544 /*include_subdomains=*/false);
1545 state.UpdatePinList({test_pinset}, {test_pinsetinfo}, base::Time::Now());
1546
1547 // Hashes should now be accepted.
1548 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1549 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1550 }
1551
TEST_F(TransportSecurityStateTest,UpdateKeyPinsListNotValidPin)1552 TEST_F(TransportSecurityStateTest, UpdateKeyPinsListNotValidPin) {
1553 base::test::ScopedFeatureList scoped_feature_list_;
1554 scoped_feature_list_.InitAndEnableFeature(
1555 features::kStaticKeyPinningEnforcement);
1556 HostPortPair host_port_pair(kHost, kPort);
1557
1558 HashValueVector good_hashes;
1559 for (size_t i = 0; kGoodPath[i]; i++)
1560 EXPECT_TRUE(AddHash(kGoodPath[i], &good_hashes));
1561
1562 TransportSecurityState state;
1563 EnableStaticPins(&state);
1564
1565 // Prior to updating the list, good_hashes should be accepted
1566 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1567 state.CheckPublicKeyPins(host_port_pair, true, good_hashes));
1568
1569 // Update the pins list, adding good_hashes to the rejected hashes for this
1570 // host.
1571 std::vector<std::vector<uint8_t>> rejected_hashes;
1572 for (size_t i = 0; kGoodPath[i]; i++) {
1573 HashValue hash;
1574 ASSERT_TRUE(hash.FromString(kGoodPath[i]));
1575 rejected_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1576 }
1577 TransportSecurityState::PinSet test_pinset(
1578 /*name=*/"test",
1579 /*static_spki_hashes=*/{},
1580 /*bad_static_spki_hashes=*/rejected_hashes);
1581 TransportSecurityState::PinSetInfo test_pinsetinfo(
1582 /*hostname=*/kHost, /* pinset_name=*/"test",
1583 /*include_subdomains=*/false);
1584 state.UpdatePinList({test_pinset}, {test_pinsetinfo}, base::Time::Now());
1585
1586 // Hashes should now be rejected.
1587 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1588 state.CheckPublicKeyPins(host_port_pair, true, good_hashes));
1589
1590 // Hashes should also be rejected if the hostname has a trailing dot.
1591 host_port_pair = HostPortPair("example.test.", kPort);
1592 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1593 state.CheckPublicKeyPins(host_port_pair, true, good_hashes));
1594
1595 // Hashes should also be rejected if the hostname has different
1596 // capitalization.
1597 host_port_pair = HostPortPair("ExAmpLe.tEsT", kPort);
1598 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1599 state.CheckPublicKeyPins(host_port_pair, true, good_hashes));
1600 }
1601
TEST_F(TransportSecurityStateTest,UpdateKeyPinsEmptyList)1602 TEST_F(TransportSecurityStateTest, UpdateKeyPinsEmptyList) {
1603 base::test::ScopedFeatureList scoped_feature_list_;
1604 scoped_feature_list_.InitAndEnableFeature(
1605 features::kStaticKeyPinningEnforcement);
1606 HostPortPair host_port_pair(kHost, kPort);
1607
1608 HashValueVector bad_hashes;
1609 for (size_t i = 0; kBadPath[i]; i++)
1610 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes));
1611
1612 TransportSecurityState state;
1613 EnableStaticPins(&state);
1614
1615 // Prior to updating the list, bad_hashes should be rejected.
1616 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1617 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1618
1619 // Update the pins list with an empty list.
1620 state.UpdatePinList({}, {}, base::Time::Now());
1621
1622 // Hashes should now be accepted.
1623 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1624 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1625 }
1626
TEST_F(TransportSecurityStateTest,UpdateKeyPinsIncludeSubdomains)1627 TEST_F(TransportSecurityStateTest, UpdateKeyPinsIncludeSubdomains) {
1628 base::test::ScopedFeatureList scoped_feature_list_;
1629 scoped_feature_list_.InitAndEnableFeature(
1630 features::kStaticKeyPinningEnforcement);
1631 HostPortPair host_port_pair("example.sub.test", kPort);
1632
1633 // unpinned_hashes is a set of hashes that (after the update) won't match the
1634 // expected hashes for the tld of this domain. kGoodPath is used here because
1635 // it's a path that is accepted prior to any updates, and this test will
1636 // validate it is rejected afterwards.
1637 HashValueVector unpinned_hashes;
1638 for (size_t i = 0; kGoodPath[i]; i++) {
1639 EXPECT_TRUE(AddHash(kGoodPath[i], &unpinned_hashes));
1640 }
1641
1642 TransportSecurityState state;
1643 EnableStaticPins(&state);
1644
1645 // Prior to updating the list, unpinned_hashes should be accepted
1646 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1647 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1648
1649 // Update the pins list, adding kBadPath to the accepted hashes for this
1650 // host, relying on include_subdomains for enforcement. The contents of the
1651 // hashes don't matter as long as they are different from unpinned_hashes,
1652 // kBadPath is used for convenience.
1653 std::vector<std::vector<uint8_t>> accepted_hashes;
1654 for (size_t i = 0; kBadPath[i]; i++) {
1655 HashValue hash;
1656 ASSERT_TRUE(hash.FromString(kBadPath[i]));
1657 accepted_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1658 }
1659 TransportSecurityState::PinSet test_pinset(
1660 /*name=*/"test",
1661 /*static_spki_hashes=*/{accepted_hashes},
1662 /*bad_static_spki_hashes=*/{});
1663 // The host used in the test is "example.sub.test", so this pinset will only
1664 // match due to include subdomains.
1665 TransportSecurityState::PinSetInfo test_pinsetinfo(
1666 /*hostname=*/"sub.test", /* pinset_name=*/"test",
1667 /*include_subdomains=*/true);
1668 state.UpdatePinList({test_pinset}, {test_pinsetinfo}, base::Time::Now());
1669
1670 // The path that was accepted before updating the pins should now be rejected.
1671 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1672 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1673 }
1674
TEST_F(TransportSecurityStateTest,UpdateKeyPinsIncludeSubdomainsTLD)1675 TEST_F(TransportSecurityStateTest, UpdateKeyPinsIncludeSubdomainsTLD) {
1676 base::test::ScopedFeatureList scoped_feature_list_;
1677 scoped_feature_list_.InitAndEnableFeature(
1678 features::kStaticKeyPinningEnforcement);
1679 HostPortPair host_port_pair(kHost, kPort);
1680
1681 // unpinned_hashes is a set of hashes that (after the update) won't match the
1682 // expected hashes for the tld of this domain. kGoodPath is used here because
1683 // it's a path that is accepted prior to any updates, and this test will
1684 // validate it is rejected afterwards.
1685 HashValueVector unpinned_hashes;
1686 for (size_t i = 0; kGoodPath[i]; i++) {
1687 EXPECT_TRUE(AddHash(kGoodPath[i], &unpinned_hashes));
1688 }
1689
1690 TransportSecurityState state;
1691 EnableStaticPins(&state);
1692
1693 // Prior to updating the list, unpinned_hashes should be accepted
1694 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1695 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1696
1697 // Update the pins list, adding kBadPath to the accepted hashes for this
1698 // host, relying on include_subdomains for enforcement. The contents of the
1699 // hashes don't matter as long as they are different from unpinned_hashes,
1700 // kBadPath is used for convenience.
1701 std::vector<std::vector<uint8_t>> accepted_hashes;
1702 for (size_t i = 0; kBadPath[i]; i++) {
1703 HashValue hash;
1704 ASSERT_TRUE(hash.FromString(kBadPath[i]));
1705 accepted_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1706 }
1707 TransportSecurityState::PinSet test_pinset(
1708 /*name=*/"test",
1709 /*static_spki_hashes=*/{accepted_hashes},
1710 /*bad_static_spki_hashes=*/{});
1711 // The host used in the test is "example.test", so this pinset will only match
1712 // due to include subdomains.
1713 TransportSecurityState::PinSetInfo test_pinsetinfo(
1714 /*hostname=*/"test", /* pinset_name=*/"test",
1715 /*include_subdomains=*/true);
1716 state.UpdatePinList({test_pinset}, {test_pinsetinfo}, base::Time::Now());
1717
1718 // The path that was accepted before updating the pins should now be rejected.
1719 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1720 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1721 }
1722
TEST_F(TransportSecurityStateTest,UpdateKeyPinsDontIncludeSubdomains)1723 TEST_F(TransportSecurityStateTest, UpdateKeyPinsDontIncludeSubdomains) {
1724 base::test::ScopedFeatureList scoped_feature_list_;
1725 scoped_feature_list_.InitAndEnableFeature(
1726 features::kStaticKeyPinningEnforcement);
1727 HostPortPair host_port_pair(kHost, kPort);
1728
1729 // unpinned_hashes is a set of hashes that (after the update) won't match the
1730 // expected hashes for the tld of this domain. kGoodPath is used here because
1731 // it's a path that is accepted prior to any updates, and this test will
1732 // validate it is accepted or rejected afterwards depending on whether the
1733 // domain is an exact match.
1734 HashValueVector unpinned_hashes;
1735 for (size_t i = 0; kGoodPath[i]; i++) {
1736 EXPECT_TRUE(AddHash(kGoodPath[i], &unpinned_hashes));
1737 }
1738
1739 TransportSecurityState state;
1740 EnableStaticPins(&state);
1741
1742 // Prior to updating the list, unpinned_hashes should be accepted
1743 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1744 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1745
1746 // Update the pins list, adding kBadPath to the accepted hashes for the
1747 // tld of this host, but without include_subdomains set. The contents of the
1748 // hashes don't matter as long as they are different from unpinned_hashes,
1749 // kBadPath is used for convenience.
1750 std::vector<std::vector<uint8_t>> accepted_hashes;
1751 for (size_t i = 0; kBadPath[i]; i++) {
1752 HashValue hash;
1753 ASSERT_TRUE(hash.FromString(kBadPath[i]));
1754 accepted_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1755 }
1756 TransportSecurityState::PinSet test_pinset(
1757 /*name=*/"test",
1758 /*static_spki_hashes=*/{accepted_hashes},
1759 /*bad_static_spki_hashes=*/{});
1760 // The host used in the test is "example.test", so this pinset will not match
1761 // due to include subdomains not being set.
1762 TransportSecurityState::PinSetInfo test_pinsetinfo(
1763 /*hostname=*/"test", /* pinset_name=*/"test",
1764 /*include_subdomains=*/false);
1765 state.UpdatePinList({test_pinset}, {test_pinsetinfo}, base::Time::Now());
1766
1767 // Hashes that were accepted before the update should still be accepted since
1768 // include subdomains is not set for the pinset, and this is not an exact
1769 // match.
1770 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1771 state.CheckPublicKeyPins(host_port_pair, true, unpinned_hashes));
1772
1773 // Hashes should be rejected for an exact match of the hostname.
1774 HostPortPair exact_match_host("test", kPort);
1775 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1776 state.CheckPublicKeyPins(exact_match_host, true, unpinned_hashes));
1777 }
1778
TEST_F(TransportSecurityStateTest,UpdateKeyPinsListTimestamp)1779 TEST_F(TransportSecurityStateTest, UpdateKeyPinsListTimestamp) {
1780 base::test::ScopedFeatureList scoped_feature_list_;
1781 scoped_feature_list_.InitAndEnableFeature(
1782 features::kStaticKeyPinningEnforcement);
1783 HostPortPair host_port_pair(kHost, kPort);
1784
1785 HashValueVector bad_hashes;
1786 for (size_t i = 0; kBadPath[i]; i++)
1787 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes));
1788
1789 TransportSecurityState state;
1790 EnableStaticPins(&state);
1791
1792 // Prior to updating the list, bad_hashes should be rejected.
1793 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1794 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1795
1796 // TransportSecurityStateTest sets a flag when EnableStaticPins is called that
1797 // results in TransportSecurityState considering the pins list as always
1798 // timely. We need to disable it so we can test that the timestamp has the
1799 // required effect.
1800 state.SetPinningListAlwaysTimelyForTesting(false);
1801
1802 // Update the pins list, with bad hashes as rejected, but a timestamp >70 days
1803 // old.
1804 std::vector<std::vector<uint8_t>> rejected_hashes;
1805 for (size_t i = 0; kBadPath[i]; i++) {
1806 HashValue hash;
1807 ASSERT_TRUE(hash.FromString(kBadPath[i]));
1808 rejected_hashes.emplace_back(hash.data(), hash.data() + hash.size());
1809 }
1810 TransportSecurityState::PinSet test_pinset(
1811 /*name=*/"test",
1812 /*static_spki_hashes=*/{},
1813 /*bad_static_spki_hashes=*/rejected_hashes);
1814 TransportSecurityState::PinSetInfo test_pinsetinfo(
1815 /*hostname=*/kHost, /* pinset_name=*/"test",
1816 /*include_subdomains=*/false);
1817 state.UpdatePinList({test_pinset}, {test_pinsetinfo},
1818 base::Time::Now() - base::Days(70));
1819
1820 // Hashes should now be accepted.
1821 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1822 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1823
1824 // Update the pins list again, with a timestamp <70 days old.
1825 state.UpdatePinList({test_pinset}, {test_pinsetinfo},
1826 base::Time::Now() - base::Days(69));
1827
1828 // Hashes should now be rejected.
1829 EXPECT_EQ(TransportSecurityState::PKPStatus::VIOLATED,
1830 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1831 }
1832
1833 class TransportSecurityStatePinningKillswitchTest
1834 : public TransportSecurityStateTest {
1835 public:
TransportSecurityStatePinningKillswitchTest()1836 TransportSecurityStatePinningKillswitchTest() {
1837 scoped_feature_list_.InitAndDisableFeature(
1838 features::kStaticKeyPinningEnforcement);
1839 }
1840
1841 protected:
1842 base::test::ScopedFeatureList scoped_feature_list_;
1843 };
1844
TEST_F(TransportSecurityStatePinningKillswitchTest,PinningKillswitchSet)1845 TEST_F(TransportSecurityStatePinningKillswitchTest, PinningKillswitchSet) {
1846 HostPortPair host_port_pair(kHost, kPort);
1847
1848 HashValueVector bad_hashes;
1849 for (size_t i = 0; kBadPath[i]; i++)
1850 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes));
1851
1852 TransportSecurityState state;
1853 EnableStaticPins(&state);
1854
1855 // Hashes should be accepted since pinning enforcement is disabled.
1856 EXPECT_EQ(TransportSecurityState::PKPStatus::OK,
1857 state.CheckPublicKeyPins(host_port_pair, true, bad_hashes));
1858 }
1859
1860 } // namespace net
1861