Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 "chrome/browser/ssl/ssl_error_handler.h" | 5 #include "chrome/browser/ssl/ssl_error_handler.h" |
| 6 | 6 |
| 7 #include <stdint.h> | 7 #include <stdint.h> |
| 8 #include <utility> | 8 #include <utility> |
| 9 | 9 |
| 10 #include "base/callback_helpers.h" | 10 #include "base/callback_helpers.h" |
| 11 #include "base/feature_list.h" | 11 #include "base/feature_list.h" |
| 12 #include "base/lazy_instance.h" | |
| 12 #include "base/macros.h" | 13 #include "base/macros.h" |
| 13 #include "base/metrics/histogram_macros.h" | 14 #include "base/metrics/histogram_macros.h" |
| 14 #include "base/strings/stringprintf.h" | 15 #include "base/strings/stringprintf.h" |
| 16 #include "base/threading/non_thread_safe.h" | |
| 15 #include "base/time/clock.h" | 17 #include "base/time/clock.h" |
| 16 #include "base/time/time.h" | 18 #include "base/time/time.h" |
| 17 #include "chrome/browser/browser_process.h" | 19 #include "chrome/browser/browser_process.h" |
| 18 #include "chrome/browser/profiles/profile.h" | 20 #include "chrome/browser/profiles/profile.h" |
| 19 #include "chrome/browser/ssl/bad_clock_blocking_page.h" | 21 #include "chrome/browser/ssl/bad_clock_blocking_page.h" |
| 20 #include "chrome/browser/ssl/ssl_blocking_page.h" | 22 #include "chrome/browser/ssl/ssl_blocking_page.h" |
| 21 #include "chrome/browser/ssl/ssl_cert_reporter.h" | 23 #include "chrome/browser/ssl/ssl_cert_reporter.h" |
| 22 #include "chrome/common/features.h" | 24 #include "chrome/common/features.h" |
| 23 #include "components/network_time/network_time_tracker.h" | 25 #include "components/network_time/network_time_tracker.h" |
| 24 #include "components/ssl_errors/error_classification.h" | 26 #include "components/ssl_errors/error_classification.h" |
| 25 #include "components/ssl_errors/error_info.h" | 27 #include "components/ssl_errors/error_info.h" |
| 26 #include "content/public/browser/notification_service.h" | 28 #include "content/public/browser/notification_service.h" |
| 27 #include "content/public/browser/notification_source.h" | 29 #include "content/public/browser/notification_source.h" |
| 28 #include "content/public/browser/render_frame_host.h" | 30 #include "content/public/browser/render_frame_host.h" |
| 29 #include "content/public/browser/web_contents.h" | 31 #include "content/public/browser/web_contents.h" |
| 30 #include "net/base/net_errors.h" | 32 #include "net/base/net_errors.h" |
| 31 | 33 |
| 32 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) | 34 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) |
| 33 #include "chrome/browser/captive_portal/captive_portal_service.h" | 35 #include "chrome/browser/captive_portal/captive_portal_service.h" |
| 34 #include "chrome/browser/captive_portal/captive_portal_service_factory.h" | 36 #include "chrome/browser/captive_portal/captive_portal_service_factory.h" |
| 35 #include "chrome/browser/captive_portal/captive_portal_tab_helper.h" | 37 #include "chrome/browser/captive_portal/captive_portal_tab_helper.h" |
| 36 #include "chrome/browser/ssl/captive_portal_blocking_page.h" | 38 #include "chrome/browser/ssl/captive_portal_blocking_page.h" |
| 37 #endif | 39 #endif |
| 38 | 40 |
| 39 namespace network_time { | |
| 40 class NetworkTimeTracker; | |
|
estark
2017/01/08 17:01:51
doh. thanks for cleaning up my mess :)
meacer
2017/01/09 20:48:26
Np :)
| |
| 41 } | |
| 42 | |
| 43 namespace { | 41 namespace { |
| 44 | 42 |
| 45 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) | 43 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) |
| 46 const base::Feature kCaptivePortalInterstitial{ | 44 const base::Feature kCaptivePortalInterstitial{ |
| 47 "CaptivePortalInterstitial", base::FEATURE_ENABLED_BY_DEFAULT}; | 45 "CaptivePortalInterstitial", base::FEATURE_ENABLED_BY_DEFAULT}; |
| 48 #endif | 46 #endif |
| 49 | 47 |
| 50 const base::Feature kSSLCommonNameMismatchHandling{ | 48 const base::Feature kSSLCommonNameMismatchHandling{ |
| 51 "SSLCommonNameMismatchHandling", base::FEATURE_ENABLED_BY_DEFAULT}; | 49 "SSLCommonNameMismatchHandling", base::FEATURE_ENABLED_BY_DEFAULT}; |
| 52 | 50 |
| 53 // The delay in milliseconds before displaying the SSL interstitial. | 51 // Default delay in milliseconds before displaying the SSL interstitial. |
| 54 // This can be changed in tests. | 52 // This can be changed in tests. |
| 55 // - If there is a name mismatch and a suggested URL available result arrives | 53 // - If there is a name mismatch and a suggested URL available result arrives |
| 56 // during this time, the user is redirected to the suggester URL. | 54 // during this time, the user is redirected to the suggester URL. |
| 57 // - If a "captive portal detected" result arrives during this time, | 55 // - If a "captive portal detected" result arrives during this time, |
| 58 // a captive portal interstitial is displayed. | 56 // a captive portal interstitial is displayed. |
| 59 // - Otherwise, an SSL interstitial is displayed. | 57 // - Otherwise, an SSL interstitial is displayed. |
| 60 int64_t g_interstitial_delay_in_milliseconds = 3000; | 58 const int64_t kInterstitialDelayInMilliseconds = 3000; |
| 61 | |
| 62 // Callback to call when the interstitial timer is started. Used for testing. | |
| 63 SSLErrorHandler::TimerStartedCallback* g_timer_started_callback = nullptr; | |
| 64 | |
| 65 // The clock to use when deciding which error type to display. Used for testing. | |
| 66 base::Clock* g_testing_clock = nullptr; | |
| 67 | |
| 68 network_time::NetworkTimeTracker* g_network_time_tracker = nullptr; | |
| 69 | 59 |
| 70 // Events for UMA. | 60 // Events for UMA. |
| 71 enum SSLErrorHandlerEvent { | 61 enum SSLErrorHandlerEvent { |
| 72 HANDLE_ALL, | 62 HANDLE_ALL, |
| 73 SHOW_CAPTIVE_PORTAL_INTERSTITIAL_NONOVERRIDABLE, | 63 SHOW_CAPTIVE_PORTAL_INTERSTITIAL_NONOVERRIDABLE, |
| 74 SHOW_CAPTIVE_PORTAL_INTERSTITIAL_OVERRIDABLE, | 64 SHOW_CAPTIVE_PORTAL_INTERSTITIAL_OVERRIDABLE, |
| 75 SHOW_SSL_INTERSTITIAL_NONOVERRIDABLE, | 65 SHOW_SSL_INTERSTITIAL_NONOVERRIDABLE, |
| 76 SHOW_SSL_INTERSTITIAL_OVERRIDABLE, | 66 SHOW_SSL_INTERSTITIAL_OVERRIDABLE, |
| 77 WWW_MISMATCH_FOUND, | 67 WWW_MISMATCH_FOUND, |
| 78 WWW_MISMATCH_URL_AVAILABLE, | 68 WWW_MISMATCH_URL_AVAILABLE, |
| (...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 146 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) | 136 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) |
| 147 bool IsCaptivePortalInterstitialEnabled() { | 137 bool IsCaptivePortalInterstitialEnabled() { |
| 148 return base::FeatureList::IsEnabled(kCaptivePortalInterstitial); | 138 return base::FeatureList::IsEnabled(kCaptivePortalInterstitial); |
| 149 } | 139 } |
| 150 #endif | 140 #endif |
| 151 | 141 |
| 152 bool IsSSLCommonNameMismatchHandlingEnabled() { | 142 bool IsSSLCommonNameMismatchHandlingEnabled() { |
| 153 return base::FeatureList::IsEnabled(kSSLCommonNameMismatchHandling); | 143 return base::FeatureList::IsEnabled(kSSLCommonNameMismatchHandling); |
| 154 } | 144 } |
| 155 | 145 |
| 146 // Configuration for SSLErrorHandler. | |
| 147 class ConfigSingleton : public base::NonThreadSafe { | |
| 148 public: | |
| 149 ConfigSingleton(); | |
| 150 | |
| 151 base::TimeDelta interstitial_delay() const; | |
| 152 SSLErrorHandler::TimerStartedCallback* timer_started_callback() const; | |
| 153 base::Clock* clock() const; | |
| 154 network_time::NetworkTimeTracker* network_time_tracker() const; | |
| 155 | |
| 156 void SetInterstitialDelayForTest(const base::TimeDelta& delay); | |
|
estark
2017/01/08 17:01:51
tiny nit: I think the suffix is technically suppos
meacer
2017/01/09 20:48:26
Done, removed ForTest* suffixes from ConfigSinglet
| |
| 157 void SetTimerStartedCallback(SSLErrorHandler::TimerStartedCallback* callback); | |
|
estark
2017/01/08 17:01:51
tiny nit: set_timer_started_callback() for consist
meacer
2017/01/09 20:48:26
Hmm, I feel like I'm missing something. Why would
estark
2017/01/09 23:13:41
Oh, I had missed that this setter was for testing
meacer
2017/01/09 23:38:06
I see. I'm by no means an expert on these, but I s
| |
| 158 void SetClockForTest(base::Clock* clock); | |
| 159 void SetNetworkTimeTrackerForTest(network_time::NetworkTimeTracker* tracker); | |
| 160 | |
| 161 private: | |
| 162 base::TimeDelta interstitial_delay_; | |
| 163 | |
| 164 // Callback to call when the interstitial timer is started. Used for | |
| 165 // testing. | |
| 166 SSLErrorHandler::TimerStartedCallback* timer_started_callback_ = nullptr; | |
|
estark
2017/01/08 17:01:51
Not particular to this CL, but it's a little weird
meacer
2017/01/09 20:48:26
The original idea was so that it could be left as
estark
2017/01/09 23:13:41
Acknowledged.
| |
| 167 | |
| 168 // The clock to use when deciding which error type to display. Used for | |
| 169 // testing. | |
| 170 base::Clock* testing_clock_ = nullptr; | |
| 171 | |
| 172 network_time::NetworkTimeTracker* network_time_tracker_ = nullptr; | |
| 173 }; | |
| 174 | |
| 175 ConfigSingleton::ConfigSingleton() | |
| 176 : interstitial_delay_( | |
| 177 base::TimeDelta::FromMilliseconds(kInterstitialDelayInMilliseconds)) { | |
| 178 } | |
| 179 | |
| 180 base::TimeDelta ConfigSingleton::interstitial_delay() const { | |
| 181 return interstitial_delay_; | |
| 182 } | |
| 183 | |
| 184 SSLErrorHandler::TimerStartedCallback* ConfigSingleton::timer_started_callback() | |
| 185 const { | |
| 186 return timer_started_callback_; | |
| 187 } | |
| 188 | |
| 189 network_time::NetworkTimeTracker* ConfigSingleton::network_time_tracker() | |
| 190 const { | |
| 191 return network_time_tracker_ ? network_time_tracker_ | |
| 192 : g_browser_process->network_time_tracker(); | |
| 193 } | |
| 194 | |
| 195 base::Clock* ConfigSingleton::clock() const { | |
| 196 return testing_clock_; | |
| 197 } | |
| 198 | |
| 199 void ConfigSingleton::SetInterstitialDelayForTest( | |
| 200 const base::TimeDelta& delay) { | |
| 201 interstitial_delay_ = delay; | |
| 202 } | |
| 203 | |
| 204 void ConfigSingleton::SetTimerStartedCallback( | |
| 205 SSLErrorHandler::TimerStartedCallback* callback) { | |
| 206 DCHECK(!callback || !callback->is_null()); | |
| 207 timer_started_callback_ = callback; | |
| 208 } | |
| 209 | |
| 210 void ConfigSingleton::SetClockForTest(base::Clock* clock) { | |
| 211 testing_clock_ = clock; | |
| 212 } | |
| 213 | |
| 214 void ConfigSingleton::SetNetworkTimeTrackerForTest( | |
| 215 network_time::NetworkTimeTracker* tracker) { | |
| 216 network_time_tracker_ = tracker; | |
| 217 } | |
| 218 | |
| 219 static base::LazyInstance<ConfigSingleton>::Leaky g_config = | |
| 220 LAZY_INSTANCE_INITIALIZER; | |
| 221 | |
| 156 } // namespace | 222 } // namespace |
| 157 | 223 |
| 158 DEFINE_WEB_CONTENTS_USER_DATA_KEY(SSLErrorHandler); | 224 DEFINE_WEB_CONTENTS_USER_DATA_KEY(SSLErrorHandler); |
| 159 DEFINE_WEB_CONTENTS_USER_DATA_KEY(CommonNameMismatchRedirectObserver); | 225 DEFINE_WEB_CONTENTS_USER_DATA_KEY(CommonNameMismatchRedirectObserver); |
| 160 | 226 |
| 161 void SSLErrorHandler::HandleSSLError( | 227 void SSLErrorHandler::HandleSSLError( |
| 162 content::WebContents* web_contents, | 228 content::WebContents* web_contents, |
| 163 int cert_error, | 229 int cert_error, |
| 164 const net::SSLInfo& ssl_info, | 230 const net::SSLInfo& ssl_info, |
| 165 const GURL& request_url, | 231 const GURL& request_url, |
| 166 int options_mask, | 232 int options_mask, |
| 167 std::unique_ptr<SSLCertReporter> ssl_cert_reporter, | 233 std::unique_ptr<SSLCertReporter> ssl_cert_reporter, |
| 168 const base::Callback<void(content::CertificateRequestResultType)>& | 234 const base::Callback<void(content::CertificateRequestResultType)>& |
| 169 callback) { | 235 callback) { |
| 170 DCHECK(!FromWebContents(web_contents)); | 236 DCHECK(!FromWebContents(web_contents)); |
| 171 SSLErrorHandler* error_handler = | 237 SSLErrorHandler* error_handler = |
| 172 new SSLErrorHandler(web_contents, cert_error, ssl_info, request_url, | 238 new SSLErrorHandler(web_contents, cert_error, ssl_info, request_url, |
| 173 options_mask, std::move(ssl_cert_reporter), callback); | 239 options_mask, std::move(ssl_cert_reporter), callback); |
| 174 web_contents->SetUserData(UserDataKey(), error_handler); | 240 web_contents->SetUserData(UserDataKey(), error_handler); |
| 175 error_handler->StartHandlingError(); | 241 error_handler->StartHandlingError(); |
| 176 } | 242 } |
| 177 | 243 |
| 178 // static | 244 // static |
| 179 void SSLErrorHandler::SetInterstitialDelayForTest(base::TimeDelta delay) { | 245 void SSLErrorHandler::SetInterstitialDelayForTest( |
| 180 g_interstitial_delay_in_milliseconds = delay.InMilliseconds(); | 246 const base::TimeDelta& delay) { |
| 247 g_config.Pointer()->SetInterstitialDelayForTest(delay); | |
| 181 } | 248 } |
| 182 | 249 |
| 183 // static | 250 // static |
| 184 void SSLErrorHandler::SetInterstitialTimerStartedCallbackForTest( | 251 void SSLErrorHandler::SetInterstitialTimerStartedCallbackForTest( |
| 185 TimerStartedCallback* callback) { | 252 TimerStartedCallback* callback) { |
| 186 DCHECK(!callback || !callback->is_null()); | 253 g_config.Pointer()->SetTimerStartedCallback(callback); |
| 187 g_timer_started_callback = callback; | |
| 188 } | 254 } |
| 189 | 255 |
| 190 // static | 256 // static |
| 191 void SSLErrorHandler::SetClockForTest(base::Clock* testing_clock) { | 257 void SSLErrorHandler::SetClockForTest(base::Clock* testing_clock) { |
| 192 g_testing_clock = testing_clock; | 258 g_config.Pointer()->SetClockForTest(testing_clock); |
| 193 } | 259 } |
| 194 | 260 |
| 195 // static | 261 // static |
| 196 void SSLErrorHandler::SetNetworkTimeTrackerForTest( | 262 void SSLErrorHandler::SetNetworkTimeTrackerForTest( |
| 197 network_time::NetworkTimeTracker* tracker) { | 263 network_time::NetworkTimeTracker* tracker) { |
| 198 g_network_time_tracker = tracker; | 264 g_config.Pointer()->SetNetworkTimeTrackerForTest(tracker); |
| 199 } | 265 } |
| 200 | 266 |
| 201 SSLErrorHandler::SSLErrorHandler( | 267 SSLErrorHandler::SSLErrorHandler( |
| 202 content::WebContents* web_contents, | 268 content::WebContents* web_contents, |
| 203 int cert_error, | 269 int cert_error, |
| 204 const net::SSLInfo& ssl_info, | 270 const net::SSLInfo& ssl_info, |
| 205 const GURL& request_url, | 271 const GURL& request_url, |
| 206 int options_mask, | 272 int options_mask, |
| 207 std::unique_ptr<SSLCertReporter> ssl_cert_reporter, | 273 std::unique_ptr<SSLCertReporter> ssl_cert_reporter, |
| 208 const base::Callback<void(content::CertificateRequestResultType)>& callback) | 274 const base::Callback<void(content::CertificateRequestResultType)>& callback) |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 242 | 308 |
| 243 // Show the SSL intersitial if |CERT_STATUS_COMMON_NAME_INVALID| is not | 309 // Show the SSL intersitial if |CERT_STATUS_COMMON_NAME_INVALID| is not |
| 244 // the only error. Need not check for captive portal in this case. | 310 // the only error. Need not check for captive portal in this case. |
| 245 // (See the comment below). | 311 // (See the comment below). |
| 246 if (net::IsCertStatusError(extra_cert_errors) && | 312 if (net::IsCertStatusError(extra_cert_errors) && |
| 247 !net::IsCertStatusMinorError(ssl_info_.cert_status)) { | 313 !net::IsCertStatusMinorError(ssl_info_.cert_status)) { |
| 248 ShowSSLInterstitial(); | 314 ShowSSLInterstitial(); |
| 249 return; | 315 return; |
| 250 } | 316 } |
| 251 CheckSuggestedUrl(suggested_url); | 317 CheckSuggestedUrl(suggested_url); |
| 252 timer_.Start(FROM_HERE, base::TimeDelta::FromMilliseconds( | 318 timer_.Start(FROM_HERE, g_config.Pointer()->interstitial_delay(), this, |
| 253 g_interstitial_delay_in_milliseconds), | 319 &SSLErrorHandler::ShowSSLInterstitial); |
| 254 this, &SSLErrorHandler::ShowSSLInterstitial); | 320 |
| 255 if (g_timer_started_callback) | 321 if (g_config.Pointer()->timer_started_callback()) |
| 256 g_timer_started_callback->Run(web_contents_); | 322 g_config.Pointer()->timer_started_callback()->Run(web_contents_); |
| 257 | 323 |
| 258 // Do not check for a captive portal in this case, because a captive | 324 // Do not check for a captive portal in this case, because a captive |
| 259 // portal most likely cannot serve a valid certificate which passes the | 325 // portal most likely cannot serve a valid certificate which passes the |
| 260 // similarity check. | 326 // similarity check. |
| 261 return; | 327 return; |
| 262 } | 328 } |
| 263 | 329 |
| 264 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) | 330 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) |
| 265 CaptivePortalTabHelper* captive_portal_tab_helper = | 331 CaptivePortalTabHelper* captive_portal_tab_helper = |
| 266 CaptivePortalTabHelper::FromWebContents(web_contents_); | 332 CaptivePortalTabHelper::FromWebContents(web_contents_); |
| 267 if (captive_portal_tab_helper) { | 333 if (captive_portal_tab_helper) { |
| 268 captive_portal_tab_helper->OnSSLCertError(ssl_info_); | 334 captive_portal_tab_helper->OnSSLCertError(ssl_info_); |
| 269 } | 335 } |
| 270 | 336 |
| 271 registrar_.Add(this, chrome::NOTIFICATION_CAPTIVE_PORTAL_CHECK_RESULT, | 337 registrar_.Add(this, chrome::NOTIFICATION_CAPTIVE_PORTAL_CHECK_RESULT, |
| 272 content::Source<Profile>(profile_)); | 338 content::Source<Profile>(profile_)); |
| 273 | 339 |
| 274 if (IsCaptivePortalInterstitialEnabled()) { | 340 if (IsCaptivePortalInterstitialEnabled()) { |
| 275 CheckForCaptivePortal(); | 341 CheckForCaptivePortal(); |
| 276 timer_.Start(FROM_HERE, base::TimeDelta::FromMilliseconds( | 342 timer_.Start(FROM_HERE, g_config.Pointer()->interstitial_delay(), this, |
| 277 g_interstitial_delay_in_milliseconds), | 343 &SSLErrorHandler::ShowSSLInterstitial); |
| 278 this, &SSLErrorHandler::ShowSSLInterstitial); | 344 if (g_config.Pointer()->timer_started_callback()) |
| 279 if (g_timer_started_callback) | 345 g_config.Pointer()->timer_started_callback()->Run(web_contents_); |
| 280 g_timer_started_callback->Run(web_contents_); | |
| 281 return; | 346 return; |
| 282 } | 347 } |
| 283 #endif | 348 #endif |
| 284 // Display an SSL interstitial. | 349 // Display an SSL interstitial. |
| 285 ShowSSLInterstitial(); | 350 ShowSSLInterstitial(); |
| 286 } | 351 } |
| 287 | 352 |
| 288 void SSLErrorHandler::CheckForCaptivePortal() { | 353 void SSLErrorHandler::CheckForCaptivePortal() { |
| 289 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) | 354 #if BUILDFLAG(ENABLE_CAPTIVE_PORTAL_DETECTION) |
| 290 CaptivePortalService* captive_portal_service = | 355 CaptivePortalService* captive_portal_service = |
| (...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 425 if (common_name_mismatch_handler_) { | 490 if (common_name_mismatch_handler_) { |
| 426 common_name_mismatch_handler_->Cancel(); | 491 common_name_mismatch_handler_->Cancel(); |
| 427 common_name_mismatch_handler_.reset(); | 492 common_name_mismatch_handler_.reset(); |
| 428 } | 493 } |
| 429 // Deletes |this| and also destroys the timer. | 494 // Deletes |this| and also destroys the timer. |
| 430 web_contents_->RemoveUserData(UserDataKey()); | 495 web_contents_->RemoveUserData(UserDataKey()); |
| 431 } | 496 } |
| 432 | 497 |
| 433 void SSLErrorHandler::HandleCertDateInvalidError() { | 498 void SSLErrorHandler::HandleCertDateInvalidError() { |
| 434 const base::TimeTicks now = base::TimeTicks::Now(); | 499 const base::TimeTicks now = base::TimeTicks::Now(); |
| 435 network_time::NetworkTimeTracker* tracker = | 500 timer_.Start(FROM_HERE, g_config.Pointer()->interstitial_delay(), |
| 436 g_network_time_tracker ? g_network_time_tracker | |
| 437 : g_browser_process->network_time_tracker(); | |
| 438 timer_.Start(FROM_HERE, base::TimeDelta::FromMilliseconds( | |
| 439 g_interstitial_delay_in_milliseconds), | |
| 440 base::Bind(&SSLErrorHandler::HandleCertDateInvalidErrorImpl, | 501 base::Bind(&SSLErrorHandler::HandleCertDateInvalidErrorImpl, |
| 441 base::Unretained(this), now)); | 502 base::Unretained(this), now)); |
| 442 // Try kicking off a time fetch to get an up-to-date estimate of the | 503 // Try kicking off a time fetch to get an up-to-date estimate of the |
| 443 // true time. This will only have an effect if network time is | 504 // true time. This will only have an effect if network time is |
| 444 // unavailable or if there is not already a query in progress. | 505 // unavailable or if there is not already a query in progress. |
| 445 // | 506 // |
| 446 // Pass a weak pointer as the callback; if the timer fires before the | 507 // Pass a weak pointer as the callback; if the timer fires before the |
| 447 // fetch completes and shows an interstitial, this SSLErrorHandler | 508 // fetch completes and shows an interstitial, this SSLErrorHandler |
| 448 // will be deleted. | 509 // will be deleted. |
| 510 network_time::NetworkTimeTracker* tracker = | |
| 511 g_config.Pointer()->network_time_tracker(); | |
| 449 if (!tracker->StartTimeFetch( | 512 if (!tracker->StartTimeFetch( |
| 450 base::Bind(&SSLErrorHandler::HandleCertDateInvalidErrorImpl, | 513 base::Bind(&SSLErrorHandler::HandleCertDateInvalidErrorImpl, |
| 451 weak_ptr_factory_.GetWeakPtr(), now))) { | 514 weak_ptr_factory_.GetWeakPtr(), now))) { |
| 452 HandleCertDateInvalidErrorImpl(now); | 515 HandleCertDateInvalidErrorImpl(now); |
| 453 return; | 516 return; |
| 454 } | 517 } |
| 455 | 518 |
| 456 if (g_timer_started_callback) | 519 if (g_config.Pointer()->timer_started_callback()) |
| 457 g_timer_started_callback->Run(web_contents_); | 520 g_config.Pointer()->timer_started_callback()->Run(web_contents_); |
| 458 } | 521 } |
| 459 | 522 |
| 460 void SSLErrorHandler::HandleCertDateInvalidErrorImpl( | 523 void SSLErrorHandler::HandleCertDateInvalidErrorImpl( |
| 461 base::TimeTicks started_handling_error) { | 524 base::TimeTicks started_handling_error) { |
| 462 UMA_HISTOGRAM_CUSTOM_TIMES( | 525 UMA_HISTOGRAM_CUSTOM_TIMES( |
| 463 "interstitial.ssl_error_handler.cert_date_error_delay", | 526 "interstitial.ssl_error_handler.cert_date_error_delay", |
| 464 base::TimeTicks::Now() - started_handling_error, | 527 base::TimeTicks::Now() - started_handling_error, |
| 465 base::TimeDelta::FromMilliseconds(1), base::TimeDelta::FromSeconds(4), | 528 base::TimeDelta::FromMilliseconds(1), base::TimeDelta::FromSeconds(4), |
| 466 50); | 529 50); |
| 467 | 530 |
| 531 timer_.Stop(); | |
| 532 base::Clock* testing_clock = g_config.Pointer()->clock(); | |
| 533 const base::Time now = | |
| 534 testing_clock ? testing_clock->Now() : base::Time::NowFromSystemTime(); | |
| 535 | |
| 468 network_time::NetworkTimeTracker* tracker = | 536 network_time::NetworkTimeTracker* tracker = |
| 469 g_network_time_tracker ? g_network_time_tracker | 537 g_config.Pointer()->network_time_tracker(); |
| 470 : g_browser_process->network_time_tracker(); | |
| 471 timer_.Stop(); | |
| 472 const base::Time now = g_testing_clock == nullptr | |
| 473 ? base::Time::NowFromSystemTime() | |
| 474 : g_testing_clock->Now(); | |
| 475 ssl_errors::ClockState clock_state = ssl_errors::GetClockState(now, tracker); | 538 ssl_errors::ClockState clock_state = ssl_errors::GetClockState(now, tracker); |
| 476 if (clock_state == ssl_errors::CLOCK_STATE_FUTURE || | 539 if (clock_state == ssl_errors::CLOCK_STATE_FUTURE || |
| 477 clock_state == ssl_errors::CLOCK_STATE_PAST) { | 540 clock_state == ssl_errors::CLOCK_STATE_PAST) { |
| 478 ShowBadClockInterstitial(now, clock_state); | 541 ShowBadClockInterstitial(now, clock_state); |
| 479 return; // |this| is deleted after showing the interstitial. | 542 return; // |this| is deleted after showing the interstitial. |
| 480 } | 543 } |
| 481 ShowSSLInterstitial(); | 544 ShowSSLInterstitial(); |
| 482 } | 545 } |
| OLD | NEW |