| // Copyright 2020 The Chromium Authors | 
 | // Use of this source code is governed by a BSD-style license that can be | 
 | // found in the LICENSE file. | 
 |  | 
 | #include <memory> | 
 |  | 
 | #include "base/task/current_thread.h" | 
 | #include "build/build_config.h" | 
 | #include "chrome/browser/browser_process.h" | 
 | #include "chrome/browser/net/system_network_context_manager.h" | 
 | #include "chrome/browser/policy/chrome_browser_policy_connector.h" | 
 | #include "chrome/browser/ssl/ssl_browsertest_util.h" | 
 | #include "chrome/browser/ui/browser.h" | 
 | #include "chrome/common/pref_names.h" | 
 | #include "chrome/test/base/chrome_test_utils.h" | 
 | #include "chrome/test/base/in_process_browser_test.h" | 
 | #include "chrome/test/base/ui_test_utils.h" | 
 | #include "components/policy/core/common/mock_configuration_policy_provider.h" | 
 | #include "components/policy/policy_constants.h" | 
 | #include "components/prefs/pref_service.h" | 
 | #include "components/security_interstitials/content/ssl_error_handler.h" | 
 | #include "content/public/browser/navigation_entry.h" | 
 | #include "content/public/browser/network_service_instance.h" | 
 | #include "content/public/browser/ssl_status.h" | 
 | #include "content/public/common/network_service_util.h" | 
 | #include "content/public/test/browser_test.h" | 
 | #include "net/cert/ev_root_ca_metadata.h" | 
 | #include "net/test/cert_test_util.h" | 
 | #include "net/test/embedded_test_server/embedded_test_server.h" | 
 | #include "net/test/test_data_directory.h" | 
 | #include "services/network/public/cpp/features.h" | 
 | #include "services/network/public/mojom/ssl_config.mojom.h" | 
 | #include "third_party/blink/public/common/features.h" | 
 |  | 
 | namespace AuthState = ssl_test_util::AuthState; | 
 |  | 
 | namespace { | 
 |  | 
 | // The test EV policy OID used for generated certs. | 
 | static const char kOCSPTestCertPolicy[] = "1.3.6.1.4.1.11129.2.4.1"; | 
 |  | 
 | }  // namespace | 
 |  | 
 | class OCSPBrowserTest : public PlatformBrowserTest, | 
 |                         public network::mojom::SSLConfigClient { | 
 |  public: | 
 |   OCSPBrowserTest() = default; | 
 |  | 
 |   void SetUp() override { | 
 |     SystemNetworkContextManager::SetEnableCertificateTransparencyForTesting( | 
 |         false); | 
 |  | 
 |     policy_provider_.SetDefaultReturns( | 
 |         /*is_initialization_complete_return=*/true, | 
 |         /*is_first_policy_load_complete_return=*/true); | 
 |     policy::BrowserPolicyConnector::SetPolicyProviderForTesting( | 
 |         &policy_provider_); | 
 |  | 
 |     InProcessBrowserTest::SetUp(); | 
 |     SSLErrorHandler::ResetConfigForTesting(); | 
 |   } | 
 |  | 
 |   void TearDown() override { | 
 |     InProcessBrowserTest::TearDown(); | 
 |  | 
 |     SystemNetworkContextManager::SetEnableCertificateTransparencyForTesting( | 
 |         absl::nullopt); | 
 |   } | 
 |  | 
 |   void SetUpOnMainThread() override { | 
 |     network::mojom::NetworkContextParamsPtr context_params = | 
 |         g_browser_process->system_network_context_manager() | 
 |             ->CreateDefaultNetworkContextParams(); | 
 |     last_ssl_config_ = *context_params->initial_ssl_config; | 
 |     receiver_.Bind(std::move(context_params->ssl_config_client_receiver)); | 
 |   } | 
 |  | 
 |   // Sets the policy identified by |policy_name| to be true, ensuring | 
 |   // that the corresponding boolean pref |pref_name| is updated to match. | 
 |   void EnablePolicy(PrefService* pref_service, | 
 |                     const char* policy_name, | 
 |                     const char* pref_name) { | 
 |     policy::PolicyMap policy_map; | 
 |     policy_map.Set(policy_name, policy::POLICY_LEVEL_MANDATORY, | 
 |                    policy::POLICY_SCOPE_MACHINE, policy::POLICY_SOURCE_CLOUD, | 
 |                    base::Value(true), nullptr); | 
 |  | 
 |     EXPECT_NO_FATAL_FAILURE(UpdateChromePolicy(policy_map)); | 
 |  | 
 |     EXPECT_TRUE(pref_service->GetBoolean(pref_name)); | 
 |     EXPECT_TRUE(pref_service->IsManagedPreference(pref_name)); | 
 |  | 
 |     // Wait for the updated SSL configuration to be sent to the network service, | 
 |     // to avoid a race. | 
 |     g_browser_process->system_network_context_manager() | 
 |         ->FlushSSLConfigManagerForTesting(); | 
 |   } | 
 |  | 
 |   void EnableRevocationChecking() { | 
 |     // OCSP checking is disabled by default. | 
 |     EXPECT_FALSE(last_ssl_config_.rev_checking_enabled); | 
 |     EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                      ->CreateDefaultNetworkContextParams() | 
 |                      ->initial_ssl_config->rev_checking_enabled); | 
 |  | 
 |     // Enable, and make sure the default network context params reflect the | 
 |     // change. | 
 |     base::RunLoop run_loop; | 
 |     set_ssl_config_updated_callback(run_loop.QuitClosure()); | 
 |     ASSERT_NO_FATAL_FAILURE( | 
 |         EnablePolicy(g_browser_process->local_state(), | 
 |                      policy::key::kEnableOnlineRevocationChecks, | 
 |                      prefs::kCertRevocationCheckingEnabled)); | 
 |     run_loop.Run(); | 
 |     EXPECT_TRUE(last_ssl_config_.rev_checking_enabled); | 
 |     EXPECT_TRUE(g_browser_process->system_network_context_manager() | 
 |                     ->CreateDefaultNetworkContextParams() | 
 |                     ->initial_ssl_config->rev_checking_enabled); | 
 |   } | 
 |  | 
 |   void DoConnection( | 
 |       const net::EmbeddedTestServer::ServerCertificateConfig& config) { | 
 |     net::EmbeddedTestServer server(net::EmbeddedTestServer::TYPE_HTTPS); | 
 |  | 
 |     server.SetSSLConfig(config); | 
 |     server.AddDefaultHandlers(GetChromeTestDataDir()); | 
 |     ASSERT_TRUE(server.Start()); | 
 |  | 
 |     ASSERT_TRUE(ui_test_utils::NavigateToURL( | 
 |         browser(), server.GetURL("/ssl/google.html"))); | 
 |   } | 
 |  | 
 |   net::CertStatus GetCurrentCertStatus() { | 
 |     content::NavigationEntry* entry = | 
 |         chrome_test_utils::GetActiveWebContents(this) | 
 |             ->GetController() | 
 |             .GetVisibleEntry(); | 
 |     return entry->GetSSL().cert_status; | 
 |   } | 
 |  | 
 |   void set_ssl_config_updated_callback( | 
 |       const base::RepeatingClosure& ssl_config_updated_callback) { | 
 |     ssl_config_updated_callback_ = std::move(ssl_config_updated_callback); | 
 |   } | 
 |  | 
 |   // network::mojom::SSLConfigClient implementation. | 
 |   void OnSSLConfigUpdated(network::mojom::SSLConfigPtr ssl_config) override { | 
 |     last_ssl_config_ = *ssl_config; | 
 |     if (ssl_config_updated_callback_) | 
 |       ssl_config_updated_callback_.Run(); | 
 |   } | 
 |  | 
 |   const network::mojom::SSLConfig& last_ssl_config() const { | 
 |     return last_ssl_config_; | 
 |   } | 
 |  | 
 |  private: | 
 |   void UpdateChromePolicy(const policy::PolicyMap& policies) { | 
 |     policy_provider_.UpdateChromePolicy(policies); | 
 |     ASSERT_TRUE(base::CurrentThread::Get()); | 
 |  | 
 |     base::RunLoop().RunUntilIdle(); | 
 |  | 
 |     content::FlushNetworkServiceInstanceForTesting(); | 
 |   } | 
 |  | 
 |   testing::NiceMock<policy::MockConfigurationPolicyProvider> policy_provider_; | 
 |  | 
 |   base::RepeatingClosure ssl_config_updated_callback_; | 
 |   network::mojom::SSLConfig last_ssl_config_; | 
 |   mojo::Receiver<network::mojom::SSLConfigClient> receiver_{this}; | 
 | }; | 
 |  | 
 | // Visits a page with revocation checking set to the default value (disabled) | 
 | // and a revoked OCSP response. | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPRevokedButNotChecked) { | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_enabled); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_enabled); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig revoked_cert_config; | 
 |   revoked_cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |   DoConnection(revoked_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_FALSE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | // Visits a page with revocation checking enabled and a valid OCSP response. | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPOk) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig ok_cert_config; | 
 |   ok_cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(ok_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | // Visits a page with revocation checking enabled and a revoked OCSP response. | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPRevoked) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig revoked_cert_config; | 
 |   revoked_cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(revoked_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticationBrokenState( | 
 |       chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |       AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPInvalid) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig invalid_cert_config; | 
 |   invalid_cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kInvalidResponse); | 
 |  | 
 |   DoConnection(invalid_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPIntermediateValid) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig | 
 |       intermediate_invalid_cert_config; | 
 |   intermediate_invalid_cert_config.intermediate = | 
 |       net::EmbeddedTestServer::IntermediateType::kInHandshake; | 
 |   intermediate_invalid_cert_config | 
 |       .ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |   intermediate_invalid_cert_config | 
 |       .intermediate_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(intermediate_invalid_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, | 
 |                        TestHTTPSOCSPIntermediateResponseOldButStillValid) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   cert_config.intermediate = | 
 |       net::EmbeddedTestServer::IntermediateType::kInHandshake; | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |   // Use an OCSP response for the intermediate that would be too old for a leaf | 
 |   // cert, but is still valid for an intermediate. | 
 |   cert_config.intermediate_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kLong}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   if (ssl_test_util::UsingBuiltinCertVerifier()) { | 
 |     ssl_test_util::CheckAuthenticationBrokenState( | 
 |         chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |         AuthState::SHOWING_INTERSTITIAL); | 
 |   } else { | 
 | #if BUILDFLAG(IS_WIN) | 
 |     // TODO(mattm): Seems to be flaky on Windows. Either returns | 
 |     // CERT_STATUS_UNABLE_TO_CHECK_REVOCATION (which gets masked off due to | 
 |     // soft-fail), or CERT_STATUS_REVOKED. | 
 |     EXPECT_THAT(cert_status & net::CERT_STATUS_ALL_ERRORS, | 
 |                 ::testing::AnyOf(0u, net::CERT_STATUS_REVOKED)); | 
 | #else | 
 |     ssl_test_util::CheckAuthenticationBrokenState( | 
 |         chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |         AuthState::SHOWING_INTERSTITIAL); | 
 | #endif | 
 |   } | 
 |  | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, | 
 |                        TestHTTPSOCSPIntermediateResponseTooOld) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   cert_config.intermediate = | 
 |       net::EmbeddedTestServer::IntermediateType::kInHandshake; | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |   // OCSP Response is too old and so should be ignored. | 
 |   cert_config.intermediate_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kLonger}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |  | 
 |   if (ssl_test_util::UsingBuiltinCertVerifier()) { | 
 |     // The builtin verifier enforces the baseline requirements for max age | 
 |     // of an intermediate's OCSP response. | 
 |     ssl_test_util::CheckAuthenticatedState( | 
 |         chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |   } else { | 
 | #if BUILDFLAG(IS_WIN) | 
 |     // TODO(mattm): Seems to be flaky on Windows. Either returns | 
 |     // CERT_STATUS_UNABLE_TO_CHECK_REVOCATION (which gets masked off due to | 
 |     // soft-fail), or CERT_STATUS_REVOKED. | 
 |  | 
 |     EXPECT_THAT(cert_status & net::CERT_STATUS_ALL_ERRORS, | 
 |                 ::testing::AnyOf(0u, net::CERT_STATUS_REVOKED)); | 
 | #else | 
 |     // The platform verifiers are more lenient. | 
 |     ssl_test_util::CheckAuthenticationBrokenState( | 
 |         chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |         AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 | #endif | 
 |   } | 
 |  | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPIntermediateRevoked) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   cert_config.intermediate = | 
 |       net::EmbeddedTestServer::IntermediateType::kInHandshake; | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |   cert_config.intermediate_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   if (ssl_test_util::UsingBuiltinCertVerifier()) { | 
 |     ssl_test_util::CheckAuthenticationBrokenState( | 
 |         chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |         AuthState::SHOWING_INTERSTITIAL); | 
 |   } else { | 
 | #if BUILDFLAG(IS_WIN) | 
 |     // TODO(mattm): Seems to be flaky on Windows. Either returns | 
 |     // CERT_STATUS_UNABLE_TO_CHECK_REVOCATION (which gets masked off due to | 
 |     // soft-fail), or CERT_STATUS_REVOKED. | 
 |     EXPECT_THAT(cert_status & net::CERT_STATUS_ALL_ERRORS, | 
 |                 ::testing::AnyOf(0u, net::CERT_STATUS_REVOKED)); | 
 | #else | 
 |     ssl_test_util::CheckAuthenticationBrokenState( | 
 |         chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |         AuthState::SHOWING_INTERSTITIAL); | 
 | #endif | 
 |   } | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPValidStapled) { | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |  | 
 |   // AIA OCSP url is included, but does not return a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kTryLater); | 
 |  | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPRevokedStapled) { | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |  | 
 |   // AIA OCSP url is included, but does not return a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kTryLater); | 
 |  | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticationBrokenState( | 
 |       chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |       AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPOldStapledAndInvalidAIA) { | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   // Stapled response indicates good, but is too old. | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kOld}}); | 
 |  | 
 |   // AIA OCSP url is included, but does not return a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kTryLater); | 
 |  | 
 |   DoConnection(cert_config); | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, TestHTTPSOCSPOldStapledButValidAIA) { | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |  | 
 |   // Stapled response indicates good, but response is too old. | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kOld}}); | 
 |  | 
 |   // AIA OCSP url is included, and returns a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | #if BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_WIN) || \ | 
 |     BUILDFLAG(IS_FUCHSIA) || BUILDFLAG(IS_MAC) | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, HardFailOnOCSPInvalid) { | 
 |   if (!ssl_test_util::SystemSupportsHardFailRevocationChecking()) { | 
 |     LOG(WARNING) << "Skipping test because system doesn't support hard fail " | 
 |                  << "revocation checking"; | 
 |     return; | 
 |   } | 
 |  | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   // Enable, and make sure the default network context params reflect the | 
 |   // change. | 
 |   base::RunLoop run_loop; | 
 |   set_ssl_config_updated_callback(run_loop.QuitClosure()); | 
 |   ASSERT_NO_FATAL_FAILURE( | 
 |       EnablePolicy(g_browser_process->local_state(), | 
 |                    policy::key::kRequireOnlineRevocationChecksForLocalAnchors, | 
 |                    prefs::kCertRevocationCheckingRequiredLocalAnchors)); | 
 |   run_loop.Run(); | 
 |   EXPECT_TRUE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_TRUE(g_browser_process->system_network_context_manager() | 
 |                   ->CreateDefaultNetworkContextParams() | 
 |                   ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kInvalidResponse); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticationBrokenState( | 
 |       chrome_test_utils::GetActiveWebContents(this), | 
 |       net::CERT_STATUS_UNABLE_TO_CHECK_REVOCATION, | 
 |       AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, HardFailOCSPInvalidUseStapled) { | 
 |   if (!ssl_test_util::SystemSupportsHardFailRevocationChecking()) { | 
 |     LOG(WARNING) << "Skipping test because system doesn't support hard fail " | 
 |                  << "revocation checking"; | 
 |     return; | 
 |   } | 
 |  | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   // Enable hard-fail, and make sure the default network context params reflect | 
 |   // the change. | 
 |   base::RunLoop run_loop; | 
 |   set_ssl_config_updated_callback(run_loop.QuitClosure()); | 
 |   ASSERT_NO_FATAL_FAILURE( | 
 |       EnablePolicy(g_browser_process->local_state(), | 
 |                    policy::key::kRequireOnlineRevocationChecksForLocalAnchors, | 
 |                    prefs::kCertRevocationCheckingRequiredLocalAnchors)); | 
 |   run_loop.Run(); | 
 |   EXPECT_TRUE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_TRUE(g_browser_process->system_network_context_manager() | 
 |                   ->CreateDefaultNetworkContextParams() | 
 |                   ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |  | 
 |   // AIA OCSP url is included, but does not return a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kTryLater); | 
 |  | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, | 
 |                        HardFailTestHTTPSOCSPOldStapledAndInvalidAIA) { | 
 |   if (!ssl_test_util::SystemSupportsHardFailRevocationChecking()) { | 
 |     LOG(WARNING) << "Skipping test because system doesn't support hard fail " | 
 |                  << "revocation checking"; | 
 |     return; | 
 |   } | 
 |  | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   // Enable hard-fail, and make sure the default network context params reflect | 
 |   // the change. | 
 |   base::RunLoop run_loop; | 
 |   set_ssl_config_updated_callback(run_loop.QuitClosure()); | 
 |   ASSERT_NO_FATAL_FAILURE( | 
 |       EnablePolicy(g_browser_process->local_state(), | 
 |                    policy::key::kRequireOnlineRevocationChecksForLocalAnchors, | 
 |                    prefs::kCertRevocationCheckingRequiredLocalAnchors)); | 
 |   run_loop.Run(); | 
 |   EXPECT_TRUE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_TRUE(g_browser_process->system_network_context_manager() | 
 |                   ->CreateDefaultNetworkContextParams() | 
 |                   ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   // Stapled response indicates good, but is too old. | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kOld}}); | 
 |  | 
 |   // AIA OCSP url is included, but does not return a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       net::EmbeddedTestServer::OCSPConfig::ResponseType::kTryLater); | 
 |  | 
 |   DoConnection(cert_config); | 
 |   ssl_test_util::CheckAuthenticationBrokenState( | 
 |       chrome_test_utils::GetActiveWebContents(this), | 
 |       net::CERT_STATUS_UNABLE_TO_CHECK_REVOCATION, | 
 |       AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(OCSPBrowserTest, | 
 |                        HardFailTestHTTPSOCSPOldStapledButValidAIA) { | 
 |   if (!ssl_test_util::SystemSupportsHardFailRevocationChecking()) { | 
 |     LOG(WARNING) << "Skipping test because system doesn't support hard fail " | 
 |                  << "revocation checking"; | 
 |     return; | 
 |   } | 
 |  | 
 |   if (!ssl_test_util::SystemSupportsOCSPStapling()) { | 
 |     LOG(WARNING) | 
 |         << "Skipping test because system doesn't support OCSP stapling"; | 
 |     return; | 
 |   } | 
 |  | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   // Enable hard-fail, and make sure the default network context params reflect | 
 |   // the change. | 
 |   base::RunLoop run_loop; | 
 |   set_ssl_config_updated_callback(run_loop.QuitClosure()); | 
 |   ASSERT_NO_FATAL_FAILURE( | 
 |       EnablePolicy(g_browser_process->local_state(), | 
 |                    policy::key::kRequireOnlineRevocationChecksForLocalAnchors, | 
 |                    prefs::kCertRevocationCheckingRequiredLocalAnchors)); | 
 |   run_loop.Run(); | 
 |   EXPECT_TRUE(last_ssl_config().rev_checking_required_local_anchors); | 
 |   EXPECT_TRUE(g_browser_process->system_network_context_manager() | 
 |                   ->CreateDefaultNetworkContextParams() | 
 |                   ->initial_ssl_config->rev_checking_required_local_anchors); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |  | 
 |   // Stapled response indicates good, but response is too old. | 
 |   cert_config.stapled_ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kOld}}); | 
 |  | 
 |   // AIA OCSP url is included, and returns a successful ocsp response. | 
 |   cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::GOOD, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(cert_config); | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 | #endif  // BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_WIN) | 
 |         // || BUILDFLAG(IS_FUCHSIA) || BUILDFLAG(IS_MAC) | 
 |  | 
 | using AIABrowserTest = OCSPBrowserTest; | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(AIABrowserTest, TestHTTPSAIA) { | 
 |   net::EmbeddedTestServer::ServerCertificateConfig cert_config; | 
 |   cert_config.intermediate = net::EmbeddedTestServer::IntermediateType::kByAIA; | 
 |  | 
 |   DoConnection(cert_config); | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 | } | 
 |  | 
 | class EVBrowserTest : public OCSPBrowserTest { | 
 |  public: | 
 |   void SetUpOnMainThread() override { | 
 |     OCSPBrowserTest::SetUpOnMainThread(); | 
 |  | 
 |     // TODO(https://crbug.com/1085233): when the CertVerifierService is moved | 
 |     // out of process, the ScopedTestEVPolicy needs to be instantiated in | 
 |     // that process. | 
 |     scoped_refptr<net::X509Certificate> root_cert = net::ImportCertFromFile( | 
 |         net::GetTestCertsDirectory(), "root_ca_cert.pem"); | 
 |     ASSERT_TRUE(root_cert); | 
 |  | 
 |     ev_test_policy_ = std::make_unique<net::ScopedTestEVPolicy>( | 
 |         net::EVRootCAMetadata::GetInstance(), | 
 |         net::X509Certificate::CalculateFingerprint256(root_cert->cert_buffer()), | 
 |         kOCSPTestCertPolicy); | 
 |   } | 
 |  | 
 |  private: | 
 |   std::unique_ptr<net::ScopedTestEVPolicy> ev_test_policy_; | 
 | }; | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(EVBrowserTest, TestHTTPSEVNoPolicySet) { | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_enabled); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_enabled); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig ok_cert_config; | 
 |   DoConnection(ok_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_FALSE(cert_status & net::CERT_STATUS_IS_EV); | 
 |   EXPECT_FALSE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | IN_PROC_BROWSER_TEST_F(EVBrowserTest, TestHTTPSEVNoOCSPCheck) { | 
 |   // OCSP checking is disabled by default. | 
 |   EXPECT_FALSE(last_ssl_config().rev_checking_enabled); | 
 |   EXPECT_FALSE(g_browser_process->system_network_context_manager() | 
 |                    ->CreateDefaultNetworkContextParams() | 
 |                    ->initial_ssl_config->rev_checking_enabled); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig ok_cert_config; | 
 |   ok_cert_config.policy_oids = {kOCSPTestCertPolicy}; | 
 |   DoConnection(ok_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticatedState( | 
 |       chrome_test_utils::GetActiveWebContents(this), AuthState::NONE); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_EQ(ssl_test_util::SystemUsesChromiumEVMetadata(), | 
 |             static_cast<bool>(cert_status & net::CERT_STATUS_IS_EV)); | 
 |   EXPECT_FALSE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } | 
 |  | 
 | // Test EV checking when revocation checking is explicitly enabled and we have a | 
 | // revoked OCSP response. | 
 | IN_PROC_BROWSER_TEST_F(EVBrowserTest, TestHTTPSOCSPRevoked) { | 
 |   EnableRevocationChecking(); | 
 |  | 
 |   net::EmbeddedTestServer::ServerCertificateConfig revoked_cert_config; | 
 |   revoked_cert_config.policy_oids = {kOCSPTestCertPolicy}; | 
 |   revoked_cert_config.ocsp_config = net::EmbeddedTestServer::OCSPConfig( | 
 |       {{net::OCSPRevocationStatus::REVOKED, | 
 |         net::EmbeddedTestServer::OCSPConfig::SingleResponse::Date::kValid}}); | 
 |  | 
 |   DoConnection(revoked_cert_config); | 
 |  | 
 |   ssl_test_util::CheckAuthenticationBrokenState( | 
 |       chrome_test_utils::GetActiveWebContents(this), net::CERT_STATUS_REVOKED, | 
 |       AuthState::SHOWING_INTERSTITIAL); | 
 |  | 
 |   net::CertStatus cert_status = GetCurrentCertStatus(); | 
 |   EXPECT_FALSE(cert_status & net::CERT_STATUS_IS_EV); | 
 |   EXPECT_TRUE(cert_status & net::CERT_STATUS_REV_CHECKING_ENABLED); | 
 | } |