Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(282)

Side by Side Diff: chrome/browser/safe_browsing/ui_manager.cc

Issue 2451623005: Remove Dangerous indicator after going back from interstitial (Closed)
Patch Set: another typo fix Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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 "chrome/browser/safe_browsing/ui_manager.h" 5 #include "chrome/browser/safe_browsing/ui_manager.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/bind_helpers.h" 8 #include "base/bind_helpers.h"
9 #include "base/callback.h" 9 #include "base/callback.h"
10 #include "base/debug/leak_tracker.h" 10 #include "base/debug/leak_tracker.h"
(...skipping 28 matching lines...) Expand all
39 using content::NavigationEntry; 39 using content::NavigationEntry;
40 using content::WebContents; 40 using content::WebContents;
41 using safe_browsing::HitReport; 41 using safe_browsing::HitReport;
42 42
43 namespace { 43 namespace {
44 44
45 const void* const kWhitelistKey = &kWhitelistKey; 45 const void* const kWhitelistKey = &kWhitelistKey;
46 46
47 // A WhitelistUrlSet holds the set of URLs that have been whitelisted for a 47 // A WhitelistUrlSet holds the set of URLs that have been whitelisted for a
48 // specific WebContents, along with pending entries that are still undecided. 48 // specific WebContents, along with pending entries that are still undecided.
49 // The URLs in this set should come from GetWhitelistUrl() or
50 // GetMainFrameWhitelistUrlForResource().
49 class WhitelistUrlSet : public base::SupportsUserData::Data { 51 class WhitelistUrlSet : public base::SupportsUserData::Data {
50 public: 52 public:
51 WhitelistUrlSet() {} 53 WhitelistUrlSet() {}
52 54
53 bool Contains(const GURL url) { 55 bool Contains(const GURL url) { return set_.find(url) != set_.end(); }
54 return set_.find(url.GetWithEmptyPath()) != set_.end(); 56
55 } 57 void RemovePending(const GURL& url) { pending_.erase(url); }
56 58
57 void Insert(const GURL url) { 59 void Insert(const GURL url) {
58 set_.insert(url.GetWithEmptyPath()); 60 set_.insert(url);
59 pending_.erase(url.GetWithEmptyPath()); 61 RemovePending(url);
60 } 62 }
61 63
62 bool ContainsPending(const GURL url) { 64 bool ContainsPending(const GURL url) {
63 return pending_.find(url.GetWithEmptyPath()) != pending_.end(); 65 return pending_.find(url) != pending_.end();
64 } 66 }
65 67
66 void InsertPending(const GURL url) { 68 void InsertPending(const GURL url) { pending_.insert(url); }
67 pending_.insert(url.GetWithEmptyPath());
68 }
69 69
70 private: 70 private:
71 std::set<GURL> set_; 71 std::set<GURL> set_;
72 std::set<GURL> pending_; 72 std::set<GURL> pending_;
73 73
74 DISALLOW_COPY_AND_ASSIGN(WhitelistUrlSet); 74 DISALLOW_COPY_AND_ASSIGN(WhitelistUrlSet);
75 }; 75 };
76 76
77 // Returns the URL that should be used in a WhitelistUrlSet for the given
78 // |resource|.
79 GURL GetMainFrameWhitelistUrlForResource(
80 const safe_browsing::SafeBrowsingUIManager::UnsafeResource& resource) {
81 if (resource.is_subresource) {
82 NavigationEntry* entry = resource.GetNavigationEntryForResource();
83 if (!entry)
84 return GURL();
85 return entry->GetURL().GetWithEmptyPath();
86 }
87 return resource.url.GetWithEmptyPath();
88 }
89
90 // Returns the URL that should be used in a WhitelistUrlSet for the
91 // resource loaded from |url| on a navigation |entry|.
92 GURL GetWhitelistUrl(const GURL& url,
93 bool is_subresource,
94 NavigationEntry* entry) {
95 if (is_subresource) {
96 if (!entry)
97 return GURL();
98 return entry->GetURL().GetWithEmptyPath();
99 }
100 return url.GetWithEmptyPath();
101 }
102
103 WhitelistUrlSet* GetOrCreateWhitelist(content::WebContents* web_contents) {
104 WhitelistUrlSet* site_list =
105 static_cast<WhitelistUrlSet*>(web_contents->GetUserData(kWhitelistKey));
106 if (!site_list) {
107 site_list = new WhitelistUrlSet;
108 web_contents->SetUserData(kWhitelistKey, site_list);
109 }
110 return site_list;
111 }
112
77 } // namespace 113 } // namespace
78 114
79 namespace safe_browsing { 115 namespace safe_browsing {
80 116
81 // SafeBrowsingUIManager::UnsafeResource --------------------------------------- 117 // SafeBrowsingUIManager::UnsafeResource ---------------------------------------
82 118
83 SafeBrowsingUIManager::UnsafeResource::UnsafeResource() 119 SafeBrowsingUIManager::UnsafeResource::UnsafeResource()
84 : is_subresource(false), 120 : is_subresource(false),
85 threat_type(SB_THREAT_TYPE_SAFE), 121 threat_type(SB_THREAT_TYPE_SAFE),
86 threat_source(safe_browsing::ThreatSource::UNKNOWN) {} 122 threat_source(safe_browsing::ThreatSource::UNKNOWN) {}
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after
145 if (shutdown) 181 if (shutdown)
146 sb_service_ = NULL; 182 sb_service_ = NULL;
147 } 183 }
148 184
149 void SafeBrowsingUIManager::LogPauseDelay(base::TimeDelta time) { 185 void SafeBrowsingUIManager::LogPauseDelay(base::TimeDelta time) {
150 UMA_HISTOGRAM_LONG_TIMES("SB2.Delay", time); 186 UMA_HISTOGRAM_LONG_TIMES("SB2.Delay", time);
151 } 187 }
152 188
153 void SafeBrowsingUIManager::OnBlockingPageDone( 189 void SafeBrowsingUIManager::OnBlockingPageDone(
154 const std::vector<UnsafeResource>& resources, 190 const std::vector<UnsafeResource>& resources,
155 bool proceed) { 191 bool proceed,
192 content::WebContents* web_contents,
193 const GURL& main_frame_url) {
156 DCHECK_CURRENTLY_ON(BrowserThread::UI); 194 DCHECK_CURRENTLY_ON(BrowserThread::UI);
157 for (const auto& resource : resources) { 195 for (const auto& resource : resources) {
158 if (!resource.callback.is_null()) { 196 if (!resource.callback.is_null()) {
159 DCHECK(resource.callback_thread); 197 DCHECK(resource.callback_thread);
160 resource.callback_thread->PostTask( 198 resource.callback_thread->PostTask(
161 FROM_HERE, base::Bind(resource.callback, proceed)); 199 FROM_HERE, base::Bind(resource.callback, proceed));
162 } 200 }
163 201
164 if (proceed) 202 GURL whitelist_url = GetWhitelistUrl(
165 AddToWhitelistUrlSet(resource, false /* Pending -> permanent */); 203 main_frame_url, false /* is subresource */,
204 nullptr /* no navigation entry needed for main resource */);
205 if (proceed) {
206 AddToWhitelistUrlSet(whitelist_url, web_contents,
207 false /* Pending -> permanent */);
208 } else if (web_contents) {
209 // |web_contents| doesn't exist if the tab has been closed.
210 RemoveFromPendingWhitelistUrlSet(whitelist_url, web_contents);
211 }
166 } 212 }
167 } 213 }
168 214
169 void SafeBrowsingUIManager::DisplayBlockingPage( 215 void SafeBrowsingUIManager::DisplayBlockingPage(
170 const UnsafeResource& resource) { 216 const UnsafeResource& resource) {
171 DCHECK_CURRENTLY_ON(BrowserThread::UI); 217 DCHECK_CURRENTLY_ON(BrowserThread::UI);
172 if (resource.is_subresource && !resource.is_subframe) { 218 if (resource.is_subresource && !resource.is_subframe) {
173 // Sites tagged as serving Unwanted Software should only show a warning for 219 // Sites tagged as serving Unwanted Software should only show a warning for
174 // main-frame or sub-frame resource. Similar warning restrictions should be 220 // main-frame or sub-frame resource. Similar warning restrictions should be
175 // applied to malware sites tagged as "landing sites" (see "Types of 221 // applied to malware sites tagged as "landing sites" (see "Types of
(...skipping 13 matching lines...) Expand all
189 return; 235 return;
190 } 236 }
191 } 237 }
192 238
193 // The tab might have been closed. If it was closed, just act as if "Don't 239 // The tab might have been closed. If it was closed, just act as if "Don't
194 // Proceed" had been chosen. 240 // Proceed" had been chosen.
195 WebContents* web_contents = resource.web_contents_getter.Run(); 241 WebContents* web_contents = resource.web_contents_getter.Run();
196 if (!web_contents) { 242 if (!web_contents) {
197 std::vector<UnsafeResource> resources; 243 std::vector<UnsafeResource> resources;
198 resources.push_back(resource); 244 resources.push_back(resource);
199 OnBlockingPageDone(resources, false); 245 OnBlockingPageDone(resources, false, web_contents,
246 GetMainFrameWhitelistUrlForResource(resource));
200 return; 247 return;
201 } 248 }
202 249
203 // Check if the user has already ignored a SB warning for the same WebContents 250 // Check if the user has already ignored a SB warning for the same WebContents
204 // and top-level domain. 251 // and top-level domain.
205 if (IsWhitelisted(resource)) { 252 if (IsWhitelisted(resource)) {
206 if (!resource.callback.is_null()) { 253 if (!resource.callback.is_null()) {
207 DCHECK(resource.callback_thread); 254 DCHECK(resource.callback_thread);
208 resource.callback_thread->PostTask(FROM_HERE, 255 resource.callback_thread->PostTask(FROM_HERE,
209 base::Bind(resource.callback, true)); 256 base::Bind(resource.callback, true));
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
245 hit_report.is_metrics_reporting_active = 292 hit_report.is_metrics_reporting_active =
246 ChromeMetricsServiceAccessor::IsMetricsAndCrashReportingEnabled(); 293 ChromeMetricsServiceAccessor::IsMetricsAndCrashReportingEnabled();
247 294
248 MaybeReportSafeBrowsingHit(hit_report); 295 MaybeReportSafeBrowsingHit(hit_report);
249 } 296 }
250 297
251 if (resource.threat_type != SB_THREAT_TYPE_SAFE) { 298 if (resource.threat_type != SB_THREAT_TYPE_SAFE) {
252 for (Observer& observer : observer_list_) 299 for (Observer& observer : observer_list_)
253 observer.OnSafeBrowsingHit(resource); 300 observer.OnSafeBrowsingHit(resource);
254 } 301 }
255 AddToWhitelistUrlSet(resource, true /* A decision is now pending */); 302 AddToWhitelistUrlSet(GetMainFrameWhitelistUrlForResource(resource),
303 resource.web_contents_getter.Run(),
304 true /* A decision is now pending */);
256 SafeBrowsingBlockingPage::ShowBlockingPage(this, resource); 305 SafeBrowsingBlockingPage::ShowBlockingPage(this, resource);
257 } 306 }
258 307
259 // A safebrowsing hit is sent after a blocking page for malware/phishing 308 // A safebrowsing hit is sent after a blocking page for malware/phishing
260 // or after the warning dialog for download urls, only for 309 // or after the warning dialog for download urls, only for
261 // UMA || extended_reporting users. 310 // UMA || extended_reporting users.
262 void SafeBrowsingUIManager::MaybeReportSafeBrowsingHit( 311 void SafeBrowsingUIManager::MaybeReportSafeBrowsingHit(
263 const HitReport& hit_report) { 312 const HitReport& hit_report) {
264 DCHECK_CURRENTLY_ON(BrowserThread::UI); 313 DCHECK_CURRENTLY_ON(BrowserThread::UI);
265 314
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
311 void SafeBrowsingUIManager::AddObserver(Observer* observer) { 360 void SafeBrowsingUIManager::AddObserver(Observer* observer) {
312 DCHECK_CURRENTLY_ON(BrowserThread::UI); 361 DCHECK_CURRENTLY_ON(BrowserThread::UI);
313 observer_list_.AddObserver(observer); 362 observer_list_.AddObserver(observer);
314 } 363 }
315 364
316 void SafeBrowsingUIManager::RemoveObserver(Observer* observer) { 365 void SafeBrowsingUIManager::RemoveObserver(Observer* observer) {
317 DCHECK_CURRENTLY_ON(BrowserThread::UI); 366 DCHECK_CURRENTLY_ON(BrowserThread::UI);
318 observer_list_.RemoveObserver(observer); 367 observer_list_.RemoveObserver(observer);
319 } 368 }
320 369
370 // Static.
371 void SafeBrowsingUIManager::CreateWhitelistForTesting(
372 content::WebContents* web_contents) {
373 GetOrCreateWhitelist(web_contents);
374 }
375
321 void SafeBrowsingUIManager::ReportInvalidCertificateChainOnIOThread( 376 void SafeBrowsingUIManager::ReportInvalidCertificateChainOnIOThread(
322 const std::string& serialized_report) { 377 const std::string& serialized_report) {
323 DCHECK_CURRENTLY_ON(BrowserThread::IO); 378 DCHECK_CURRENTLY_ON(BrowserThread::IO);
324 379
325 // The service may delete the ping manager (i.e. when user disabling service, 380 // The service may delete the ping manager (i.e. when user disabling service,
326 // etc). This happens on the IO thread. 381 // etc). This happens on the IO thread.
327 if (!sb_service_ || !sb_service_->ping_manager()) 382 if (!sb_service_ || !sb_service_->ping_manager())
328 return; 383 return;
329 384
330 sb_service_->ping_manager()->ReportInvalidCertificateChain(serialized_report); 385 sb_service_->ping_manager()->ReportInvalidCertificateChain(serialized_report);
(...skipping 21 matching lines...) Expand all
352 // etc). This happens on the IO thread. 407 // etc). This happens on the IO thread.
353 if (sb_service_.get() == NULL || sb_service_->ping_manager() == NULL) 408 if (sb_service_.get() == NULL || sb_service_->ping_manager() == NULL)
354 return; 409 return;
355 410
356 if (!serialized.empty()) { 411 if (!serialized.empty()) {
357 DVLOG(1) << "Sending serialized threat details."; 412 DVLOG(1) << "Sending serialized threat details.";
358 sb_service_->ping_manager()->ReportThreatDetails(serialized); 413 sb_service_->ping_manager()->ReportThreatDetails(serialized);
359 } 414 }
360 } 415 }
361 416
362 // Record this domain in the current WebContents as either whitelisted or 417 // Record this domain in the given WebContents as either whitelisted or
363 // pending whitelisting (if an interstitial is currently displayed). If an 418 // pending whitelisting (if an interstitial is currently displayed). If an
364 // existing WhitelistUrlSet does not yet exist, create a new WhitelistUrlSet. 419 // existing WhitelistUrlSet does not yet exist, create a new WhitelistUrlSet.
365 void SafeBrowsingUIManager::AddToWhitelistUrlSet(const UnsafeResource& resource, 420 void SafeBrowsingUIManager::AddToWhitelistUrlSet(
366 bool pending) { 421 const GURL& whitelist_url,
422 content::WebContents* web_contents,
423 bool pending) {
367 DCHECK_CURRENTLY_ON(BrowserThread::UI); 424 DCHECK_CURRENTLY_ON(BrowserThread::UI);
368 425
369 WebContents* web_contents = resource.web_contents_getter.Run(); 426 // A WebContents might not exist if the tab has been closed.
427 if (!web_contents)
428 return;
429
430 WhitelistUrlSet* site_list = GetOrCreateWhitelist(web_contents);
431
432 if (whitelist_url.is_empty())
433 return;
434
435 if (pending) {
436 site_list->InsertPending(whitelist_url);
437 } else {
438 site_list->Insert(whitelist_url);
439 }
440
441 // Notify security UI that security state has changed.
442 web_contents->DidChangeVisibleSecurityState();
443 }
444
445 void SafeBrowsingUIManager::RemoveFromPendingWhitelistUrlSet(
446 const GURL& whitelist_url,
447 content::WebContents* web_contents) {
448 DCHECK_CURRENTLY_ON(BrowserThread::UI);
449
450 // A WebContents might not exist if the tab has been closed.
451 if (!web_contents)
452 return;
453
454 // Use |web_contents| rather than |resource.web_contents_getter|
455 // here. By this point, a "Back" navigation could have already been
456 // committed, so the page loading |resource| might be gone and
457 // |web_contents_getter| may no longer be valid.
370 WhitelistUrlSet* site_list = 458 WhitelistUrlSet* site_list =
371 static_cast<WhitelistUrlSet*>(web_contents->GetUserData(kWhitelistKey)); 459 static_cast<WhitelistUrlSet*>(web_contents->GetUserData(kWhitelistKey));
372 if (!site_list) {
373 site_list = new WhitelistUrlSet;
374 web_contents->SetUserData(kWhitelistKey, site_list);
375 }
376 460
377 GURL whitelisted_url; 461 if (whitelist_url.is_empty())
378 if (resource.is_subresource) { 462 return;
379 NavigationEntry* entry = resource.GetNavigationEntryForResource();
380 if (!entry)
381 return;
382 whitelisted_url = entry->GetURL();
383 } else {
384 whitelisted_url = resource.url;
385 }
386 463
387 if (pending) { 464 // Note that this function does not DCHECK that |whitelist_url|
388 site_list->InsertPending(whitelisted_url); 465 // appears in the pending whitelist. In the common case, it's expected
389 } else { 466 // that a URL is in the pending whitelist when it is removed, but it's
390 site_list->Insert(whitelisted_url); 467 // not always the case. For example, if there are several blocking
391 } 468 // pages queued up for different resources on the same page, and the
469 // user goes back to dimiss the first one, the subsequent blocking
470 // pages get dismissed as well (as if the user had clicked "Back to
471 // safety" on each of them). In this case, the first dismissal will
472 // remove the main-frame URL from the pending whitelist, so the
473 // main-frame URL will have already been removed when the subsequent
474 // blocking pages are dismissed.
475 if (site_list->ContainsPending(whitelist_url))
476 site_list->RemovePending(whitelist_url);
392 477
393 // Notify security UI that security state has changed. 478 // Notify security UI that security state has changed.
394 web_contents->DidChangeVisibleSecurityState(); 479 web_contents->DidChangeVisibleSecurityState();
395 } 480 }
396 481
397 bool SafeBrowsingUIManager::IsWhitelisted(const UnsafeResource& resource) { 482 bool SafeBrowsingUIManager::IsWhitelisted(const UnsafeResource& resource) {
398 NavigationEntry* entry = nullptr; 483 NavigationEntry* entry = nullptr;
399 if (resource.is_subresource) { 484 if (resource.is_subresource) {
400 entry = resource.GetNavigationEntryForResource(); 485 entry = resource.GetNavigationEntryForResource();
401 } 486 }
402 return IsUrlWhitelistedOrPendingForWebContents( 487 return IsUrlWhitelistedOrPendingForWebContents(
403 resource.url, resource.is_subresource, entry, 488 resource.url, resource.is_subresource, entry,
404 resource.web_contents_getter.Run(), true); 489 resource.web_contents_getter.Run(), true);
405 } 490 }
406 491
407 // Check if the user has already seen and/or ignored a SB warning for this 492 // Check if the user has already seen and/or ignored a SB warning for this
408 // WebContents and top-level domain. 493 // WebContents and top-level domain.
409 bool SafeBrowsingUIManager::IsUrlWhitelistedOrPendingForWebContents( 494 bool SafeBrowsingUIManager::IsUrlWhitelistedOrPendingForWebContents(
410 const GURL& url, 495 const GURL& url,
411 bool is_subresource, 496 bool is_subresource,
412 NavigationEntry* entry, 497 NavigationEntry* entry,
413 content::WebContents* web_contents, 498 content::WebContents* web_contents,
414 bool whitelist_only) { 499 bool whitelist_only) {
415 DCHECK_CURRENTLY_ON(BrowserThread::UI); 500 DCHECK_CURRENTLY_ON(BrowserThread::UI);
416 501
417 GURL lookup_url; 502 GURL lookup_url = GetWhitelistUrl(url, is_subresource, entry);
418 if (is_subresource) { 503 if (lookup_url.is_empty())
419 if (!entry) 504 return false;
420 return false;
421 lookup_url = entry->GetURL();
422 } else {
423 lookup_url = url;
424 }
425 505
426 WhitelistUrlSet* site_list = 506 WhitelistUrlSet* site_list =
427 static_cast<WhitelistUrlSet*>(web_contents->GetUserData(kWhitelistKey)); 507 static_cast<WhitelistUrlSet*>(web_contents->GetUserData(kWhitelistKey));
428 if (!site_list) 508 if (!site_list)
429 return false; 509 return false;
430 510
431 bool whitelisted = site_list->Contains(lookup_url); 511 bool whitelisted = site_list->Contains(lookup_url);
432 if (whitelist_only) { 512 if (whitelist_only) {
433 return whitelisted; 513 return whitelisted;
434 } else { 514 } else {
435 return whitelisted || site_list->ContainsPending(lookup_url); 515 return whitelisted || site_list->ContainsPending(lookup_url);
436 } 516 }
437 } 517 }
438 518
519 // Static.
520 GURL SafeBrowsingUIManager::GetMainFrameWhitelistUrlForResourceForTesting(
521 const safe_browsing::SafeBrowsingUIManager::UnsafeResource& resource) {
522 return GetMainFrameWhitelistUrlForResource(resource);
523 }
524
439 } // namespace safe_browsing 525 } // namespace safe_browsing
OLDNEW
« no previous file with comments | « chrome/browser/safe_browsing/ui_manager.h ('k') | chrome/browser/safe_browsing/ui_manager_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698