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 <memory> | 8 #include <memory> |
9 #include <utility> | 9 #include <utility> |
10 #include <vector> | 10 #include <vector> |
(...skipping 619 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
630 bool found; | 630 bool found; |
631 if (!DecodeHSTSPreloadRaw(hostname, &found, out)) { | 631 if (!DecodeHSTSPreloadRaw(hostname, &found, out)) { |
632 DCHECK(false) << "Internal error in DecodeHSTSPreloadRaw for hostname " | 632 DCHECK(false) << "Internal error in DecodeHSTSPreloadRaw for hostname " |
633 << hostname; | 633 << hostname; |
634 return false; | 634 return false; |
635 } | 635 } |
636 | 636 |
637 return found; | 637 return found; |
638 } | 638 } |
639 | 639 |
| 640 // Serializes an OCSPVerifyResult::ResponseStatus to a string enum, suitable for |
| 641 // the |response-status| field in an Expect-Staple report. |
| 642 std::string SerializeExpectStapleResponseStatus( |
| 643 OCSPVerifyResult::ResponseStatus status) { |
| 644 switch (status) { |
| 645 case OCSPVerifyResult::MISSING: |
| 646 return "MISSING"; |
| 647 case OCSPVerifyResult::PROVIDED: |
| 648 return "PROVIDED"; |
| 649 case OCSPVerifyResult::ERROR_RESPONSE: |
| 650 return "ERROR_RESPONSE"; |
| 651 case OCSPVerifyResult::BAD_PRODUCED_AT: |
| 652 return "BAD_PRODUCED_AT"; |
| 653 case OCSPVerifyResult::NO_MATCHING_RESPONSE: |
| 654 return "NO_MATCHING_RESPONSE"; |
| 655 case OCSPVerifyResult::INVALID_DATE: |
| 656 return "INVALID_DATE"; |
| 657 case OCSPVerifyResult::PARSE_RESPONSE_ERROR: |
| 658 return "PARSE_RESPONSE_ERROR"; |
| 659 case OCSPVerifyResult::PARSE_RESPONSE_DATA_ERROR: |
| 660 return "PARSE_RESPONSE_DATA_ERROR"; |
| 661 } |
| 662 return std::string(); |
| 663 } |
| 664 |
| 665 // Serializes an OCSPRevocationStatus to a string enum, suitable for the |
| 666 // |cert-status| field in an Expect-Staple report. |
| 667 std::string SerializeExpectStapleRevocationStatus( |
| 668 const OCSPRevocationStatus& status) { |
| 669 switch (status) { |
| 670 case OCSPRevocationStatus::GOOD: |
| 671 return "GOOD"; |
| 672 case OCSPRevocationStatus::REVOKED: |
| 673 return "REVOKED"; |
| 674 case OCSPRevocationStatus::UNKNOWN: |
| 675 return "UNKNOWN"; |
| 676 } |
| 677 return std::string(); |
| 678 } |
| 679 |
| 680 bool SerializeExpectStapleReport(const HostPortPair& host_port_pair, |
| 681 const SSLInfo& ssl_info, |
| 682 const std::string& ocsp_response, |
| 683 std::string* out_serialized_report) { |
| 684 base::DictionaryValue report; |
| 685 report.SetString("date-time", TimeToISO8601(base::Time::Now())); |
| 686 report.SetString("hostname", host_port_pair.host()); |
| 687 report.SetInteger("port", host_port_pair.port()); |
| 688 report.SetString("response-status", |
| 689 SerializeExpectStapleResponseStatus( |
| 690 ssl_info.ocsp_result.response_status)); |
| 691 |
| 692 if (!ocsp_response.empty()) { |
| 693 std::string encoded_ocsp_response; |
| 694 base::Base64Encode(ocsp_response, &encoded_ocsp_response); |
| 695 report.SetString("ocsp-response", encoded_ocsp_response); |
| 696 } |
| 697 if (ssl_info.ocsp_result.response_status == OCSPVerifyResult::PROVIDED) { |
| 698 report.SetString("cert-status", |
| 699 SerializeExpectStapleRevocationStatus( |
| 700 ssl_info.ocsp_result.revocation_status)); |
| 701 } |
| 702 if (ssl_info.is_issued_by_known_root) { |
| 703 report.Set("served-certificate-chain", |
| 704 GetPEMEncodedChainAsList(ssl_info.unverified_cert.get())); |
| 705 report.Set("validated-certificate-chain", |
| 706 GetPEMEncodedChainAsList(ssl_info.cert.get())); |
| 707 } |
| 708 |
| 709 if (!base::JSONWriter::Write(report, out_serialized_report)) |
| 710 return false; |
| 711 return true; |
| 712 } |
| 713 |
640 } // namespace | 714 } // namespace |
641 | 715 |
642 TransportSecurityState::TransportSecurityState() | 716 TransportSecurityState::TransportSecurityState() |
643 : enable_static_pins_(true), | 717 : enable_static_pins_(true), |
644 enable_static_expect_ct_(true), | 718 enable_static_expect_ct_(true), |
645 enable_static_expect_staple_(false), | 719 enable_static_expect_staple_(false), |
646 enable_pkp_bypass_for_local_trust_anchors_(true), | 720 enable_pkp_bypass_for_local_trust_anchors_(true), |
647 sent_reports_cache_(kMaxHPKPReportCacheEntries) { | 721 sent_reports_cache_(kMaxHPKPReportCacheEntries) { |
648 // Static pinning is only enabled for official builds to make sure that | 722 // Static pinning is only enabled for official builds to make sure that |
649 // others don't end up with pins that cannot be easily updated. | 723 // others don't end up with pins that cannot be easily updated. |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
706 | 780 |
707 if (pin_validity == PKPStatus::VIOLATED) { | 781 if (pin_validity == PKPStatus::VIOLATED) { |
708 LOG(ERROR) << *pinning_failure_log; | 782 LOG(ERROR) << *pinning_failure_log; |
709 ReportUMAOnPinFailure(host_port_pair.host()); | 783 ReportUMAOnPinFailure(host_port_pair.host()); |
710 } | 784 } |
711 UMA_HISTOGRAM_BOOLEAN("Net.PublicKeyPinSuccess", | 785 UMA_HISTOGRAM_BOOLEAN("Net.PublicKeyPinSuccess", |
712 pin_validity == PKPStatus::OK); | 786 pin_validity == PKPStatus::OK); |
713 return pin_validity; | 787 return pin_validity; |
714 } | 788 } |
715 | 789 |
| 790 void TransportSecurityState::CheckExpectStaple( |
| 791 const HostPortPair& host_port_pair, |
| 792 const SSLInfo& ssl_info, |
| 793 const std::string& ocsp_response) { |
| 794 DCHECK(CalledOnValidThread()); |
| 795 if (!enable_static_expect_staple_ || !report_sender_) |
| 796 return; |
| 797 |
| 798 // Determine if the host is on the Expect-Staple preload list. If the build is |
| 799 // not timely (i.e. the preload list is not fresh), this will fail and return |
| 800 // false. |
| 801 ExpectStapleState expect_staple_state; |
| 802 if (!GetStaticExpectStapleState(host_port_pair.host(), &expect_staple_state)) |
| 803 return; |
| 804 |
| 805 // No report needed if a stapled OCSP response was provided. |
| 806 if (ssl_info.ocsp_result.response_status == OCSPVerifyResult::PROVIDED && |
| 807 ssl_info.ocsp_result.revocation_status == OCSPRevocationStatus::GOOD) { |
| 808 return; |
| 809 } |
| 810 |
| 811 std::string serialized_report; |
| 812 if (!SerializeExpectStapleReport(host_port_pair, ssl_info, ocsp_response, |
| 813 &serialized_report)) { |
| 814 return; |
| 815 } |
| 816 report_sender_->Send(expect_staple_state.report_uri, serialized_report); |
| 817 } |
| 818 |
716 bool TransportSecurityState::HasPublicKeyPins(const std::string& host) { | 819 bool TransportSecurityState::HasPublicKeyPins(const std::string& host) { |
717 PKPState dynamic_state; | 820 PKPState dynamic_state; |
718 if (GetDynamicPKPState(host, &dynamic_state)) | 821 if (GetDynamicPKPState(host, &dynamic_state)) |
719 return dynamic_state.HasPublicKeyPins(); | 822 return dynamic_state.HasPublicKeyPins(); |
720 | 823 |
721 STSState unused; | 824 STSState unused; |
722 PKPState static_pkp_state; | 825 PKPState static_pkp_state; |
723 if (GetStaticDomainState(host, &unused, &static_pkp_state)) { | 826 if (GetStaticDomainState(host, &unused, &static_pkp_state)) { |
724 if (static_pkp_state.HasPublicKeyPins()) | 827 if (static_pkp_state.HasPublicKeyPins()) |
725 return true; | 828 return true; |
(...skipping 795 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1521 TransportSecurityState::PKPStateIterator::PKPStateIterator( | 1624 TransportSecurityState::PKPStateIterator::PKPStateIterator( |
1522 const TransportSecurityState& state) | 1625 const TransportSecurityState& state) |
1523 : iterator_(state.enabled_pkp_hosts_.begin()), | 1626 : iterator_(state.enabled_pkp_hosts_.begin()), |
1524 end_(state.enabled_pkp_hosts_.end()) { | 1627 end_(state.enabled_pkp_hosts_.end()) { |
1525 } | 1628 } |
1526 | 1629 |
1527 TransportSecurityState::PKPStateIterator::~PKPStateIterator() { | 1630 TransportSecurityState::PKPStateIterator::~PKPStateIterator() { |
1528 } | 1631 } |
1529 | 1632 |
1530 } // namespace | 1633 } // namespace |
OLD | NEW |