| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/http/transport_security_state.h" | 5 #include "net/http/transport_security_state.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <vector> | 9 #include <vector> |
| 10 | 10 |
| 11 #include "base/base64.h" | 11 #include "base/base64.h" |
| 12 #include "base/files/file_path.h" | 12 #include "base/files/file_path.h" |
| 13 #include "base/json/json_reader.h" |
| 13 #include "base/rand_util.h" | 14 #include "base/rand_util.h" |
| 14 #include "base/sha1.h" | 15 #include "base/sha1.h" |
| 15 #include "base/strings/string_piece.h" | 16 #include "base/strings/string_piece.h" |
| 17 #include "base/values.h" |
| 16 #include "crypto/sha2.h" | 18 #include "crypto/sha2.h" |
| 17 #include "net/base/net_errors.h" | 19 #include "net/base/net_errors.h" |
| 18 #include "net/base/test_completion_callback.h" | 20 #include "net/base/test_completion_callback.h" |
| 19 #include "net/base/test_data_directory.h" | 21 #include "net/base/test_data_directory.h" |
| 20 #include "net/cert/asn1_util.h" | 22 #include "net/cert/asn1_util.h" |
| 21 #include "net/cert/cert_verifier.h" | 23 #include "net/cert/cert_verifier.h" |
| 22 #include "net/cert/cert_verify_result.h" | 24 #include "net/cert/cert_verify_result.h" |
| 23 #include "net/cert/test_root_certs.h" | 25 #include "net/cert/test_root_certs.h" |
| 24 #include "net/cert/x509_cert_types.h" | 26 #include "net/cert/x509_cert_types.h" |
| 25 #include "net/cert/x509_certificate.h" | 27 #include "net/cert/x509_certificate.h" |
| 28 #include "net/http/certificate_report_sender.h" |
| 26 #include "net/http/http_util.h" | 29 #include "net/http/http_util.h" |
| 30 #include "net/http/transport_security_reporter.h" |
| 27 #include "net/log/net_log.h" | 31 #include "net/log/net_log.h" |
| 28 #include "net/ssl/ssl_info.h" | 32 #include "net/ssl/ssl_info.h" |
| 29 #include "net/test/cert_test_util.h" | 33 #include "net/test/cert_test_util.h" |
| 30 #include "testing/gtest/include/gtest/gtest.h" | 34 #include "testing/gtest/include/gtest/gtest.h" |
| 31 | 35 |
| 32 #if defined(USE_OPENSSL) | 36 #if defined(USE_OPENSSL) |
| 33 #include "crypto/openssl_util.h" | 37 #include "crypto/openssl_util.h" |
| 34 #else | 38 #else |
| 35 #include "crypto/nss_util.h" | 39 #include "crypto/nss_util.h" |
| 36 #endif | 40 #endif |
| 37 | 41 |
| 42 namespace { |
| 43 |
| 44 // A mock CertificateReportSender that just remembers the latest report |
| 45 // URI and report to be sent. |
| 46 class MockCertificateReportSender : public net::CertificateReportSender { |
| 47 public: |
| 48 MockCertificateReportSender() {} |
| 49 ~MockCertificateReportSender() override {} |
| 50 |
| 51 void Send(const GURL& report_uri, const std::string& report) override { |
| 52 latest_report_uri_ = report_uri; |
| 53 latest_report_ = report; |
| 54 } |
| 55 |
| 56 const GURL& latest_report_uri() { return latest_report_uri_; } |
| 57 const std::string& latest_report() { return latest_report_; } |
| 58 |
| 59 private: |
| 60 GURL latest_report_uri_; |
| 61 std::string latest_report_; |
| 62 }; |
| 63 |
| 64 void CompareCertificateChainWithList( |
| 65 const scoped_refptr<net::X509Certificate>& cert_chain, |
| 66 const base::ListValue* cert_list) { |
| 67 ASSERT_TRUE(cert_chain); |
| 68 std::vector<std::string> pem_encoded_chain; |
| 69 cert_chain->GetPEMEncodedChain(&pem_encoded_chain); |
| 70 EXPECT_EQ(pem_encoded_chain.size(), cert_list->GetSize()); |
| 71 |
| 72 for (size_t i = 0; i < pem_encoded_chain.size(); i++) { |
| 73 std::string list_cert; |
| 74 ASSERT_TRUE(cert_list->GetString(i, &list_cert)); |
| 75 EXPECT_EQ(pem_encoded_chain[i], list_cert); |
| 76 } |
| 77 } |
| 78 |
| 79 void CheckHPKPReport( |
| 80 const std::string& report, |
| 81 const std::string& hostname, |
| 82 uint16_t port, |
| 83 const base::Time& expiry, |
| 84 bool include_subdomains, |
| 85 const std::string& noted_hostname, |
| 86 const scoped_refptr<net::X509Certificate>& served_certificate_chain, |
| 87 const scoped_refptr<net::X509Certificate>& validated_certificate_chain, |
| 88 const net::HashValueVector& known_pins) { |
| 89 // TODO(estark): check time in RFC3339 format. |
| 90 |
| 91 scoped_ptr<base::Value> value(base::JSONReader::Read(report)); |
| 92 ASSERT_TRUE(value); |
| 93 ASSERT_TRUE(value->IsType(base::Value::TYPE_DICTIONARY)); |
| 94 |
| 95 scoped_ptr<base::DictionaryValue> report_dict( |
| 96 static_cast<base::DictionaryValue*>(value.release())); |
| 97 |
| 98 std::string report_hostname; |
| 99 EXPECT_TRUE(report_dict->GetString("hostname", &report_hostname)); |
| 100 EXPECT_EQ(hostname, report_hostname); |
| 101 |
| 102 int report_port; |
| 103 EXPECT_TRUE(report_dict->GetInteger("port", &report_port)); |
| 104 EXPECT_EQ(port, report_port); |
| 105 |
| 106 bool report_include_subdomains; |
| 107 EXPECT_TRUE(report_dict->GetBoolean("include-subdomains", |
| 108 &report_include_subdomains)); |
| 109 EXPECT_EQ(include_subdomains, report_include_subdomains); |
| 110 |
| 111 std::string report_noted_hostname; |
| 112 EXPECT_TRUE(report_dict->GetString("hostname", &report_noted_hostname)); |
| 113 EXPECT_EQ(hostname, report_noted_hostname); |
| 114 |
| 115 base::ListValue* report_served_certificate_chain; |
| 116 EXPECT_TRUE(report_dict->GetList("served-certificate-chain", |
| 117 &report_served_certificate_chain)); |
| 118 CompareCertificateChainWithList(served_certificate_chain, |
| 119 report_served_certificate_chain); |
| 120 |
| 121 base::ListValue* report_validated_certificate_chain; |
| 122 EXPECT_TRUE(report_dict->GetList("validated-certificate-chain", |
| 123 &report_validated_certificate_chain)); |
| 124 CompareCertificateChainWithList(validated_certificate_chain, |
| 125 report_validated_certificate_chain); |
| 126 } |
| 127 |
| 128 } // namespace |
| 129 |
| 38 namespace net { | 130 namespace net { |
| 39 | 131 |
| 40 class TransportSecurityStateTest : public testing::Test { | 132 class TransportSecurityStateTest : public testing::Test { |
| 41 public: | 133 public: |
| 42 void SetUp() override { | 134 void SetUp() override { |
| 43 #if defined(USE_OPENSSL) | 135 #if defined(USE_OPENSSL) |
| 44 crypto::EnsureOpenSSLInit(); | 136 crypto::EnsureOpenSSLInit(); |
| 45 #else | 137 #else |
| 46 crypto::EnsureNSSInit(); | 138 crypto::EnsureNSSInit(); |
| 47 #endif | 139 #endif |
| (...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 205 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.example.test")); | 297 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.example.test")); |
| 206 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.baz.example.test")); | 298 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.bar.baz.example.test")); |
| 207 EXPECT_FALSE(state.ShouldUpgradeToSSL("test")); | 299 EXPECT_FALSE(state.ShouldUpgradeToSSL("test")); |
| 208 EXPECT_FALSE(state.ShouldUpgradeToSSL("notexample.test")); | 300 EXPECT_FALSE(state.ShouldUpgradeToSSL("notexample.test")); |
| 209 } | 301 } |
| 210 | 302 |
| 211 // Tests that a more-specific HSTS or HPKP rule overrides a less-specific rule | 303 // Tests that a more-specific HSTS or HPKP rule overrides a less-specific rule |
| 212 // with it, regardless of the includeSubDomains bit. This is a regression test | 304 // with it, regardless of the includeSubDomains bit. This is a regression test |
| 213 // for https://crbug.com/469957. | 305 // for https://crbug.com/469957. |
| 214 TEST_F(TransportSecurityStateTest, SubdomainCarveout) { | 306 TEST_F(TransportSecurityStateTest, SubdomainCarveout) { |
| 307 static const char kReportUri[] = "http://example.com/test"; |
| 308 std::string report_uri(kReportUri); |
| 309 |
| 215 TransportSecurityState state; | 310 TransportSecurityState state; |
| 216 const base::Time current_time(base::Time::Now()); | 311 const base::Time current_time(base::Time::Now()); |
| 217 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 312 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 218 const base::Time older = current_time - base::TimeDelta::FromSeconds(1000); | 313 const base::Time older = current_time - base::TimeDelta::FromSeconds(1000); |
| 219 | 314 |
| 220 state.AddHSTS("example1.test", expiry, true); | 315 state.AddHSTS("example1.test", expiry, true); |
| 221 state.AddHSTS("foo.example1.test", expiry, false); | 316 state.AddHSTS("foo.example1.test", expiry, false); |
| 222 | 317 |
| 223 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes()); | 318 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes(), |
| 224 state.AddHPKP("foo.example2.test", expiry, false, GetSampleSPKIHashes()); | 319 report_uri); |
| 320 state.AddHPKP("foo.example2.test", expiry, false, GetSampleSPKIHashes(), |
| 321 report_uri); |
| 225 | 322 |
| 226 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); | 323 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); |
| 227 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); | 324 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); |
| 228 | 325 |
| 229 // The foo.example1.test rule overrides the example1.test rule, so | 326 // The foo.example1.test rule overrides the example1.test rule, so |
| 230 // bar.foo.example1.test has no HSTS state. | 327 // bar.foo.example1.test has no HSTS state. |
| 231 EXPECT_FALSE(state.ShouldUpgradeToSSL("bar.foo.example1.test")); | 328 EXPECT_FALSE(state.ShouldUpgradeToSSL("bar.foo.example1.test")); |
| 232 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("bar.foo.example1.test")); | 329 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("bar.foo.example1.test")); |
| 233 | 330 |
| 234 EXPECT_TRUE(state.HasPublicKeyPins("example2.test")); | 331 EXPECT_TRUE(state.HasPublicKeyPins("example2.test")); |
| 235 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); | 332 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); |
| 236 | 333 |
| 237 // The foo.example2.test rule overrides the example1.test rule, so | 334 // The foo.example2.test rule overrides the example1.test rule, so |
| 238 // bar.foo.example2.test has no HPKP state. | 335 // bar.foo.example2.test has no HPKP state. |
| 239 EXPECT_FALSE(state.HasPublicKeyPins("bar.foo.example2.test")); | 336 EXPECT_FALSE(state.HasPublicKeyPins("bar.foo.example2.test")); |
| 240 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("bar.foo.example2.test")); | 337 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("bar.foo.example2.test")); |
| 241 | 338 |
| 242 // Expire the foo.example*.test rules. | 339 // Expire the foo.example*.test rules. |
| 243 state.AddHSTS("foo.example1.test", older, false); | 340 state.AddHSTS("foo.example1.test", older, false); |
| 244 state.AddHPKP("foo.example2.test", older, false, GetSampleSPKIHashes()); | 341 state.AddHPKP("foo.example2.test", older, false, GetSampleSPKIHashes(), |
| 342 report_uri); |
| 245 | 343 |
| 246 // Now the base example*.test rules apply to bar.foo.example*.test. | 344 // Now the base example*.test rules apply to bar.foo.example*.test. |
| 247 EXPECT_TRUE(state.ShouldUpgradeToSSL("bar.foo.example1.test")); | 345 EXPECT_TRUE(state.ShouldUpgradeToSSL("bar.foo.example1.test")); |
| 248 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example1.test")); | 346 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example1.test")); |
| 249 EXPECT_TRUE(state.HasPublicKeyPins("bar.foo.example2.test")); | 347 EXPECT_TRUE(state.HasPublicKeyPins("bar.foo.example2.test")); |
| 250 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example2.test")); | 348 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("bar.foo.example2.test")); |
| 251 } | 349 } |
| 252 | 350 |
| 253 TEST_F(TransportSecurityStateTest, FatalSSLErrors) { | 351 TEST_F(TransportSecurityStateTest, FatalSSLErrors) { |
| 352 static const char kReportUri[] = "http://example.com/test"; |
| 353 std::string report_uri(kReportUri); |
| 354 |
| 254 TransportSecurityState state; | 355 TransportSecurityState state; |
| 255 const base::Time current_time(base::Time::Now()); | 356 const base::Time current_time(base::Time::Now()); |
| 256 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 357 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 257 | 358 |
| 258 state.AddHSTS("example1.test", expiry, false); | 359 state.AddHSTS("example1.test", expiry, false); |
| 259 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes()); | 360 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes(), |
| 361 report_uri); |
| 260 | 362 |
| 261 // The presense of either HSTS or HPKP is enough to make SSL errors fatal. | 363 // The presense of either HSTS or HPKP is enough to make SSL errors fatal. |
| 262 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example1.test")); | 364 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example1.test")); |
| 263 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example2.test")); | 365 EXPECT_TRUE(state.ShouldSSLErrorsBeFatal("example2.test")); |
| 264 } | 366 } |
| 265 | 367 |
| 266 // Tests that HPKP and HSTS state both expire. Also tests that expired entries | 368 // Tests that HPKP and HSTS state both expire. Also tests that expired entries |
| 267 // are pruned. | 369 // are pruned. |
| 268 TEST_F(TransportSecurityStateTest, Expiration) { | 370 TEST_F(TransportSecurityStateTest, Expiration) { |
| 371 static const char kReportUri[] = "http://example.com/test"; |
| 372 std::string report_uri(kReportUri); |
| 373 |
| 269 TransportSecurityState state; | 374 TransportSecurityState state; |
| 270 const base::Time current_time(base::Time::Now()); | 375 const base::Time current_time(base::Time::Now()); |
| 271 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 376 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 272 const base::Time older = current_time - base::TimeDelta::FromSeconds(1000); | 377 const base::Time older = current_time - base::TimeDelta::FromSeconds(1000); |
| 273 | 378 |
| 274 // Note: this test assumes that inserting an entry with an expiration time in | 379 // Note: this test assumes that inserting an entry with an expiration time in |
| 275 // the past works and is pruned on query. | 380 // the past works and is pruned on query. |
| 276 state.AddHSTS("example1.test", older, false); | 381 state.AddHSTS("example1.test", older, false); |
| 277 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); | 382 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); |
| 278 EXPECT_FALSE(state.ShouldUpgradeToSSL("example1.test")); | 383 EXPECT_FALSE(state.ShouldUpgradeToSSL("example1.test")); |
| 279 // Querying |state| for a domain should flush out expired entries. | 384 // Querying |state| for a domain should flush out expired entries. |
| 280 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); | 385 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); |
| 281 | 386 |
| 282 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes()); | 387 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes(), |
| 388 report_uri); |
| 283 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); | 389 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); |
| 284 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); | 390 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); |
| 285 // Querying |state| for a domain should flush out expired entries. | 391 // Querying |state| for a domain should flush out expired entries. |
| 286 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); | 392 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); |
| 287 | 393 |
| 288 state.AddHSTS("example1.test", older, false); | 394 state.AddHSTS("example1.test", older, false); |
| 289 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes()); | 395 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes(), |
| 396 report_uri); |
| 290 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); | 397 EXPECT_TRUE(TransportSecurityState::Iterator(state).HasNext()); |
| 291 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("example1.test")); | 398 EXPECT_FALSE(state.ShouldSSLErrorsBeFatal("example1.test")); |
| 292 // Querying |state| for a domain should flush out expired entries. | 399 // Querying |state| for a domain should flush out expired entries. |
| 293 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); | 400 EXPECT_FALSE(TransportSecurityState::Iterator(state).HasNext()); |
| 294 | 401 |
| 295 // Test that HSTS can outlive HPKP. | 402 // Test that HSTS can outlive HPKP. |
| 296 state.AddHSTS("example1.test", expiry, false); | 403 state.AddHSTS("example1.test", expiry, false); |
| 297 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes()); | 404 state.AddHPKP("example1.test", older, false, GetSampleSPKIHashes(), |
| 405 report_uri); |
| 298 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); | 406 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); |
| 299 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); | 407 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); |
| 300 | 408 |
| 301 // Test that HPKP can outlive HSTS. | 409 // Test that HPKP can outlive HSTS. |
| 302 state.AddHSTS("example2.test", older, false); | 410 state.AddHSTS("example2.test", older, false); |
| 303 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes()); | 411 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes(), |
| 412 report_uri); |
| 304 EXPECT_FALSE(state.ShouldUpgradeToSSL("example2.test")); | 413 EXPECT_FALSE(state.ShouldUpgradeToSSL("example2.test")); |
| 305 EXPECT_TRUE(state.HasPublicKeyPins("example2.test")); | 414 EXPECT_TRUE(state.HasPublicKeyPins("example2.test")); |
| 306 } | 415 } |
| 307 | 416 |
| 308 TEST_F(TransportSecurityStateTest, InvalidDomains) { | 417 TEST_F(TransportSecurityStateTest, InvalidDomains) { |
| 309 TransportSecurityState state; | 418 TransportSecurityState state; |
| 310 const base::Time current_time(base::Time::Now()); | 419 const base::Time current_time(base::Time::Now()); |
| 311 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 420 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 312 | 421 |
| 313 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.test")); | 422 EXPECT_FALSE(state.ShouldUpgradeToSSL("example.test")); |
| 314 bool include_subdomains = true; | 423 bool include_subdomains = true; |
| 315 state.AddHSTS("example.test", expiry, include_subdomains); | 424 state.AddHSTS("example.test", expiry, include_subdomains); |
| 316 EXPECT_TRUE(state.ShouldUpgradeToSSL("www-.foo.example.test")); | 425 EXPECT_TRUE(state.ShouldUpgradeToSSL("www-.foo.example.test")); |
| 317 EXPECT_TRUE(state.ShouldUpgradeToSSL("2\x01.foo.example.test")); | 426 EXPECT_TRUE(state.ShouldUpgradeToSSL("2\x01.foo.example.test")); |
| 318 } | 427 } |
| 319 | 428 |
| 320 // Tests that HPKP and HSTS state are queried independently for subdomain | 429 // Tests that HPKP and HSTS state are queried independently for subdomain |
| 321 // matches. | 430 // matches. |
| 322 TEST_F(TransportSecurityStateTest, IndependentSubdomain) { | 431 TEST_F(TransportSecurityStateTest, IndependentSubdomain) { |
| 432 static const char kReportUri[] = "http://example.com/test"; |
| 433 std::string report_uri(kReportUri); |
| 434 |
| 323 TransportSecurityState state; | 435 TransportSecurityState state; |
| 324 const base::Time current_time(base::Time::Now()); | 436 const base::Time current_time(base::Time::Now()); |
| 325 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 437 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 326 | 438 |
| 327 state.AddHSTS("example1.test", expiry, true); | 439 state.AddHSTS("example1.test", expiry, true); |
| 328 state.AddHPKP("example1.test", expiry, false, GetSampleSPKIHashes()); | 440 state.AddHPKP("example1.test", expiry, false, GetSampleSPKIHashes(), |
| 441 report_uri); |
| 329 | 442 |
| 330 state.AddHSTS("example2.test", expiry, false); | 443 state.AddHSTS("example2.test", expiry, false); |
| 331 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes()); | 444 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes(), |
| 445 report_uri); |
| 332 | 446 |
| 333 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); | 447 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); |
| 334 EXPECT_FALSE(state.HasPublicKeyPins("foo.example1.test")); | 448 EXPECT_FALSE(state.HasPublicKeyPins("foo.example1.test")); |
| 335 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example2.test")); | 449 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example2.test")); |
| 336 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); | 450 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); |
| 337 } | 451 } |
| 338 | 452 |
| 339 // Tests that HPKP and HSTS state are inserted and overridden independently. | 453 // Tests that HPKP and HSTS state are inserted and overridden independently. |
| 340 TEST_F(TransportSecurityStateTest, IndependentInsertion) { | 454 TEST_F(TransportSecurityStateTest, IndependentInsertion) { |
| 455 static const char kReportUri[] = "http://example.com/test"; |
| 456 std::string report_uri(kReportUri); |
| 457 |
| 341 TransportSecurityState state; | 458 TransportSecurityState state; |
| 342 const base::Time current_time(base::Time::Now()); | 459 const base::Time current_time(base::Time::Now()); |
| 343 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 460 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 344 | 461 |
| 345 // Place an includeSubdomains HSTS entry below a normal HPKP entry. | 462 // Place an includeSubdomains HSTS entry below a normal HPKP entry. |
| 346 state.AddHSTS("example1.test", expiry, true); | 463 state.AddHSTS("example1.test", expiry, true); |
| 347 state.AddHPKP("foo.example1.test", expiry, false, GetSampleSPKIHashes()); | 464 state.AddHPKP("foo.example1.test", expiry, false, GetSampleSPKIHashes(), |
| 465 report_uri); |
| 348 | 466 |
| 349 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); | 467 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example1.test")); |
| 350 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test")); | 468 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test")); |
| 351 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); | 469 EXPECT_TRUE(state.ShouldUpgradeToSSL("example1.test")); |
| 352 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); | 470 EXPECT_FALSE(state.HasPublicKeyPins("example1.test")); |
| 353 | 471 |
| 354 // Drop the includeSubdomains from the HSTS entry. | 472 // Drop the includeSubdomains from the HSTS entry. |
| 355 state.AddHSTS("example1.test", expiry, false); | 473 state.AddHSTS("example1.test", expiry, false); |
| 356 | 474 |
| 357 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example1.test")); | 475 EXPECT_FALSE(state.ShouldUpgradeToSSL("foo.example1.test")); |
| 358 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test")); | 476 EXPECT_TRUE(state.HasPublicKeyPins("foo.example1.test")); |
| 359 | 477 |
| 360 // Place an includeSubdomains HPKP entry below a normal HSTS entry. | 478 // Place an includeSubdomains HPKP entry below a normal HSTS entry. |
| 361 state.AddHSTS("foo.example2.test", expiry, false); | 479 state.AddHSTS("foo.example2.test", expiry, false); |
| 362 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes()); | 480 state.AddHPKP("example2.test", expiry, true, GetSampleSPKIHashes(), |
| 481 report_uri); |
| 363 | 482 |
| 364 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test")); | 483 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test")); |
| 365 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); | 484 EXPECT_TRUE(state.HasPublicKeyPins("foo.example2.test")); |
| 366 | 485 |
| 367 // Drop the includeSubdomains from the HSTS entry. | 486 // Drop the includeSubdomains from the HSTS entry. |
| 368 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes()); | 487 state.AddHPKP("example2.test", expiry, false, GetSampleSPKIHashes(), |
| 488 report_uri); |
| 369 | 489 |
| 370 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test")); | 490 EXPECT_TRUE(state.ShouldUpgradeToSSL("foo.example2.test")); |
| 371 EXPECT_FALSE(state.HasPublicKeyPins("foo.example2.test")); | 491 EXPECT_FALSE(state.HasPublicKeyPins("foo.example2.test")); |
| 372 } | 492 } |
| 373 | 493 |
| 374 // Tests that GetDynamicDomainState appropriately stitches together the results | 494 // Tests that GetDynamicDomainState appropriately stitches together the results |
| 375 // of HSTS and HPKP. | 495 // of HSTS and HPKP. |
| 376 TEST_F(TransportSecurityStateTest, DynamicDomainState) { | 496 TEST_F(TransportSecurityStateTest, DynamicDomainState) { |
| 497 static const char kReportUri[] = "http://example.com/test"; |
| 498 std::string report_uri(kReportUri); |
| 499 |
| 377 TransportSecurityState state; | 500 TransportSecurityState state; |
| 378 const base::Time current_time(base::Time::Now()); | 501 const base::Time current_time(base::Time::Now()); |
| 379 const base::Time expiry1 = current_time + base::TimeDelta::FromSeconds(1000); | 502 const base::Time expiry1 = current_time + base::TimeDelta::FromSeconds(1000); |
| 380 const base::Time expiry2 = current_time + base::TimeDelta::FromSeconds(2000); | 503 const base::Time expiry2 = current_time + base::TimeDelta::FromSeconds(2000); |
| 381 | 504 |
| 382 state.AddHSTS("example.com", expiry1, true); | 505 state.AddHSTS("example.com", expiry1, true); |
| 383 state.AddHPKP("foo.example.com", expiry2, false, GetSampleSPKIHashes()); | 506 state.AddHPKP("foo.example.com", expiry2, false, GetSampleSPKIHashes(), |
| 507 report_uri); |
| 384 | 508 |
| 385 TransportSecurityState::DomainState domain_state; | 509 TransportSecurityState::DomainState domain_state; |
| 386 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); | 510 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); |
| 387 EXPECT_TRUE(domain_state.ShouldUpgradeToSSL()); | 511 EXPECT_TRUE(domain_state.ShouldUpgradeToSSL()); |
| 388 EXPECT_TRUE(domain_state.HasPublicKeyPins()); | 512 EXPECT_TRUE(domain_state.HasPublicKeyPins()); |
| 389 EXPECT_TRUE(domain_state.sts.include_subdomains); | 513 EXPECT_TRUE(domain_state.sts.include_subdomains); |
| 390 EXPECT_FALSE(domain_state.pkp.include_subdomains); | 514 EXPECT_FALSE(domain_state.pkp.include_subdomains); |
| 391 EXPECT_EQ(expiry1, domain_state.sts.expiry); | 515 EXPECT_EQ(expiry1, domain_state.sts.expiry); |
| 392 EXPECT_EQ(expiry2, domain_state.pkp.expiry); | 516 EXPECT_EQ(expiry2, domain_state.pkp.expiry); |
| 393 EXPECT_EQ("example.com", domain_state.sts.domain); | 517 EXPECT_EQ("example.com", domain_state.sts.domain); |
| 394 EXPECT_EQ("foo.example.com", domain_state.pkp.domain); | 518 EXPECT_EQ("foo.example.com", domain_state.pkp.domain); |
| 395 } | 519 } |
| 396 | 520 |
| 397 // Tests that new pins always override previous pins. This should be true for | 521 // Tests that new pins always override previous pins. This should be true for |
| 398 // both pins at the same domain or includeSubdomains pins at a parent domain. | 522 // both pins at the same domain or includeSubdomains pins at a parent domain. |
| 399 TEST_F(TransportSecurityStateTest, NewPinsOverride) { | 523 TEST_F(TransportSecurityStateTest, NewPinsOverride) { |
| 524 static const char kReportUri[] = "http://example.com/test"; |
| 525 std::string report_uri(kReportUri); |
| 526 |
| 400 TransportSecurityState state; | 527 TransportSecurityState state; |
| 401 TransportSecurityState::DomainState domain_state; | 528 TransportSecurityState::DomainState domain_state; |
| 402 const base::Time current_time(base::Time::Now()); | 529 const base::Time current_time(base::Time::Now()); |
| 403 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 530 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 404 HashValue hash1(HASH_VALUE_SHA1); | 531 HashValue hash1(HASH_VALUE_SHA1); |
| 405 memset(hash1.data(), 0x01, hash1.size()); | 532 memset(hash1.data(), 0x01, hash1.size()); |
| 406 HashValue hash2(HASH_VALUE_SHA1); | 533 HashValue hash2(HASH_VALUE_SHA1); |
| 407 memset(hash2.data(), 0x02, hash1.size()); | 534 memset(hash2.data(), 0x02, hash1.size()); |
| 408 HashValue hash3(HASH_VALUE_SHA1); | 535 HashValue hash3(HASH_VALUE_SHA1); |
| 409 memset(hash3.data(), 0x03, hash1.size()); | 536 memset(hash3.data(), 0x03, hash1.size()); |
| 410 | 537 |
| 411 state.AddHPKP("example.com", expiry, true, HashValueVector(1, hash1)); | 538 state.AddHPKP("example.com", expiry, true, HashValueVector(1, hash1), |
| 539 report_uri); |
| 412 | 540 |
| 413 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); | 541 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); |
| 414 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); | 542 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); |
| 415 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash1)); | 543 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash1)); |
| 416 | 544 |
| 417 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash2)); | 545 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash2), |
| 546 report_uri); |
| 418 | 547 |
| 419 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); | 548 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); |
| 420 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); | 549 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); |
| 421 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash2)); | 550 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash2)); |
| 422 | 551 |
| 423 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash3)); | 552 state.AddHPKP("foo.example.com", expiry, false, HashValueVector(1, hash3), |
| 553 report_uri); |
| 424 | 554 |
| 425 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); | 555 ASSERT_TRUE(state.GetDynamicDomainState("foo.example.com", &domain_state)); |
| 426 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); | 556 ASSERT_EQ(1u, domain_state.pkp.spki_hashes.size()); |
| 427 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash3)); | 557 EXPECT_TRUE(domain_state.pkp.spki_hashes[0].Equals(hash3)); |
| 428 } | 558 } |
| 429 | 559 |
| 430 TEST_F(TransportSecurityStateTest, DeleteAllDynamicDataSince) { | 560 TEST_F(TransportSecurityStateTest, DeleteAllDynamicDataSince) { |
| 431 TransportSecurityState state; | 561 TransportSecurityState state; |
| 432 const base::Time current_time(base::Time::Now()); | 562 const base::Time current_time(base::Time::Now()); |
| 433 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); | 563 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| (...skipping 594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1028 | 1158 |
| 1029 // These hosts used to only be HSTS when SNI was available. | 1159 // These hosts used to only be HSTS when SNI was available. |
| 1030 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( | 1160 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( |
| 1031 "gmail.com")); | 1161 "gmail.com")); |
| 1032 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( | 1162 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( |
| 1033 "googlegroups.com")); | 1163 "googlegroups.com")); |
| 1034 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( | 1164 EXPECT_TRUE(TransportSecurityState::IsGooglePinnedProperty( |
| 1035 "www.googlegroups.com")); | 1165 "www.googlegroups.com")); |
| 1036 } | 1166 } |
| 1037 | 1167 |
| 1168 TEST_F(TransportSecurityStateTest, HPKPReporting) { |
| 1169 const char kHost[] = "example.com"; |
| 1170 const char kSubdomain[] = "foo.example.com"; |
| 1171 const uint16_t kPort = 443; |
| 1172 GURL report_uri("http://www.example.com/report"); |
| 1173 // Two dummy certs to use as the server-sent and validated chains. The |
| 1174 // contents don't matter. |
| 1175 scoped_refptr<X509Certificate> cert1 = |
| 1176 ImportCertFromFile(GetTestCertsDirectory(), "test_mail_google_com.pem"); |
| 1177 scoped_refptr<X509Certificate> cert2 = |
| 1178 ImportCertFromFile(GetTestCertsDirectory(), "expired_cert.pem"); |
| 1179 ASSERT_TRUE(cert1); |
| 1180 ASSERT_TRUE(cert2); |
| 1181 |
| 1182 // kGoodPath is blog.torproject.org. |
| 1183 static const char* const kGoodPath[] = { |
| 1184 "sha1/m9lHYJYke9k0GtVZ+bXSQYE8nDI=", |
| 1185 "sha1/o5OZxATDsgmwgcIfIWIneMJ0jkw=", |
| 1186 "sha1/wHqYaI2J+6sFZAwRfap9ZbjKzE4=", |
| 1187 NULL, |
| 1188 }; |
| 1189 |
| 1190 // kBadPath is plus.google.com via Trustcenter, which is utterly wrong for |
| 1191 // torproject.org. |
| 1192 static const char* const kBadPath[] = { |
| 1193 "sha1/4BjDjn8v2lWeUFQnqSs0BgbIcrU=", |
| 1194 "sha1/gzuEEAB/bkqdQS3EIjk2by7lW+k=", |
| 1195 "sha1/SOZo+SvSspXXR9gjIBBPM5iQn9Q=", |
| 1196 NULL, |
| 1197 }; |
| 1198 |
| 1199 HashValueVector good_hashes, bad_hashes; |
| 1200 |
| 1201 for (size_t i = 0; kGoodPath[i]; i++) { |
| 1202 EXPECT_TRUE(AddHash(kGoodPath[i], &good_hashes)); |
| 1203 } |
| 1204 for (size_t i = 0; kBadPath[i]; i++) { |
| 1205 EXPECT_TRUE(AddHash(kBadPath[i], &bad_hashes)); |
| 1206 } |
| 1207 |
| 1208 TransportSecurityState state; |
| 1209 MockCertificateReportSender* mock_report_sender = |
| 1210 new MockCertificateReportSender(); |
| 1211 TransportSecurityReporter reporter( |
| 1212 &state, scoped_ptr<CertificateReportSender>(mock_report_sender)); |
| 1213 |
| 1214 const base::Time current_time(base::Time::Now()); |
| 1215 const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); |
| 1216 state.AddHPKP(kHost, expiry, true, good_hashes, report_uri.spec()); |
| 1217 |
| 1218 EXPECT_EQ(GURL(), mock_report_sender->latest_report_uri()); |
| 1219 EXPECT_EQ(std::string(), mock_report_sender->latest_report()); |
| 1220 |
| 1221 std::string failure_log; |
| 1222 EXPECT_FALSE(state.CheckPublicKeyPins( |
| 1223 kHost, true, bad_hashes, kPort, cert1, cert2, |
| 1224 TransportSecurityState::DO_NOT_SEND_PUBLIC_KEY_PIN_REPORT, &failure_log)); |
| 1225 |
| 1226 // No report should have been sent because of the DO_NOT_SEND_REPORT |
| 1227 // argument. |
| 1228 EXPECT_EQ(GURL(), mock_report_sender->latest_report_uri()); |
| 1229 EXPECT_EQ(std::string(), mock_report_sender->latest_report()); |
| 1230 |
| 1231 EXPECT_TRUE(state.CheckPublicKeyPins( |
| 1232 kHost, true, good_hashes, kPort, cert1, cert2, |
| 1233 TransportSecurityState::SEND_PUBLIC_KEY_PIN_REPORT, &failure_log)); |
| 1234 |
| 1235 // No report should have been sent because there was no violation. |
| 1236 EXPECT_EQ(GURL(), mock_report_sender->latest_report_uri()); |
| 1237 EXPECT_EQ(std::string(), mock_report_sender->latest_report()); |
| 1238 |
| 1239 EXPECT_FALSE(state.CheckPublicKeyPins( |
| 1240 kHost, true, bad_hashes, kPort, cert1, cert2, |
| 1241 TransportSecurityState::SEND_PUBLIC_KEY_PIN_REPORT, &failure_log)); |
| 1242 |
| 1243 // Now a report should have been sent. Check that it contains the |
| 1244 // right information. |
| 1245 EXPECT_EQ(report_uri, mock_report_sender->latest_report_uri()); |
| 1246 std::string report = mock_report_sender->latest_report(); |
| 1247 ASSERT_FALSE(report.empty()); |
| 1248 CheckHPKPReport(report, kHost, kPort, expiry, true, kHost, cert1, cert2, |
| 1249 good_hashes); |
| 1250 |
| 1251 EXPECT_FALSE(state.CheckPublicKeyPins( |
| 1252 kSubdomain, true, bad_hashes, kPort, cert1, cert2, |
| 1253 TransportSecurityState::SEND_PUBLIC_KEY_PIN_REPORT, &failure_log)); |
| 1254 |
| 1255 // Now a report should have been sent for the subdomain. Check that it |
| 1256 // contains the |
| 1257 // right information. |
| 1258 EXPECT_EQ(report_uri, mock_report_sender->latest_report_uri()); |
| 1259 report = mock_report_sender->latest_report(); |
| 1260 ASSERT_FALSE(report.empty()); |
| 1261 CheckHPKPReport(report, kSubdomain, kPort, expiry, true, kHost, cert1, cert2, |
| 1262 good_hashes); |
| 1263 } |
| 1264 |
| 1038 } // namespace net | 1265 } // namespace net |
| OLD | NEW |