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

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

Issue 10857002: Additional corruption instrumentation in safe-browsing filters. (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Created 8 years, 4 months 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
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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/safe_browsing_database.h" 5 #include "chrome/browser/safe_browsing/safe_browsing_database.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <iterator> 8 #include <iterator>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 278 matching lines...) Expand 10 before | Expand all | Expand 10 after
289 PREFIX_SET_CREATE_ADD_PREFIXES_CHECKSUM, 289 PREFIX_SET_CREATE_ADD_PREFIXES_CHECKSUM,
290 PREFIX_SET_CREATE_PREFIXES_CHECKSUM, 290 PREFIX_SET_CREATE_PREFIXES_CHECKSUM,
291 PREFIX_SET_CREATE_GET_PREFIXES_CHECKSUM, 291 PREFIX_SET_CREATE_GET_PREFIXES_CHECKSUM,
292 // Failed checksums when probing the filters. 292 // Failed checksums when probing the filters.
293 PREFIX_SET_MISMATCH_PREFIX_SET_CHECKSUM, 293 PREFIX_SET_MISMATCH_PREFIX_SET_CHECKSUM,
294 PREFIX_SET_MISMATCH_BLOOM_FILTER_CHECKSUM, 294 PREFIX_SET_MISMATCH_BLOOM_FILTER_CHECKSUM,
295 295
296 // Recorded once per update if the impossible occurs. 296 // Recorded once per update if the impossible occurs.
297 PREFIX_SET_BLOOM_MISS_PREFIX_HIT, 297 PREFIX_SET_BLOOM_MISS_PREFIX_HIT,
298 298
299 // Corrosponding CHECKSUM failed, but on retry it succeeded.
300 PREFIX_SET_CREATE_PREFIX_SET_CHECKSUM_SUCCEEDED,
ramant (doing other things) 2012/08/15 00:07:57 nit: Corrosponding -> Corresponding
301 PREFIX_SET_CREATE_BLOOM_FILTER_CHECKSUM_SUCCEEDED,
302
299 // Memory space for histograms is determined by the max. ALWAYS ADD 303 // Memory space for histograms is determined by the max. ALWAYS ADD
300 // NEW VALUES BEFORE THIS ONE. 304 // NEW VALUES BEFORE THIS ONE.
301 PREFIX_SET_EVENT_MAX 305 PREFIX_SET_EVENT_MAX
302 }; 306 };
303 307
304 void RecordPrefixSetInfo(PrefixSetEvent event_type) { 308 void RecordPrefixSetInfo(PrefixSetEvent event_type) {
305 UMA_HISTOGRAM_ENUMERATION("SB2.PrefixSetEvent", event_type, 309 UMA_HISTOGRAM_ENUMERATION("SB2.PrefixSetEvent", event_type,
306 PREFIX_SET_EVENT_MAX); 310 PREFIX_SET_EVENT_MAX);
307 } 311 }
308 312
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
424 428
425 std::vector<SBPrefix> restored; 429 std::vector<SBPrefix> restored;
426 prefix_set->get()->GetPrefixes(&restored); 430 prefix_set->get()->GetPrefixes(&restored);
427 DCHECK_EQ(0, ChecksumPrefixes(prefix_set->get()->GetPrefixesChecksum(), 431 DCHECK_EQ(0, ChecksumPrefixes(prefix_set->get()->GetPrefixesChecksum(),
428 restored)); 432 restored));
429 } 433 }
430 434
431 // TODO(shess): Need a barrier to prevent ordering checks above here 435 // TODO(shess): Need a barrier to prevent ordering checks above here
432 // or construction below here? 436 // or construction below here?
433 437
438 // NOTE(shess): So far, the fallout is:
439 // 605 PREFIX_SET_CHECKSUM (failed prefix_set->CheckChecksum()).
440 // 32 BLOOM_FILTER_CHECKSUM (failed bloom_filter->CheckChecksum()).
441 // 1 ADD_PREFIXES_CHECKSUM (contents of add_prefixes changed).
442 // 7 PREFIXES_CHECKSUM (contents of prefixes changed).
443
434 bool get_prefixes_broken = 444 bool get_prefixes_broken =
435 (unique_prefixes_checksum != prefix_set->get()->GetPrefixesChecksum()); 445 (unique_prefixes_checksum != prefix_set->get()->GetPrefixesChecksum());
436 bool prefix_set_broken = !prefix_set->get()->CheckChecksum(); 446 bool prefix_set_broken = !prefix_set->get()->CheckChecksum();
437 bool bloom_filter_broken = !bloom_filter->get()->CheckChecksum(); 447 bool bloom_filter_broken = !bloom_filter->get()->CheckChecksum();
438 bool prefixes_input_broken = 448 bool prefixes_input_broken =
439 (0 != ChecksumPrefixes(add_prefixes_checksum, prefixes)); 449 (0 != ChecksumPrefixes(add_prefixes_checksum, prefixes));
440 bool add_prefixes_input_broken = 450 bool add_prefixes_input_broken =
441 (0 != ChecksumAddPrefixes(add_prefixes_checksum, add_prefixes)); 451 (0 != ChecksumAddPrefixes(add_prefixes_checksum, add_prefixes));
442 452
443 if (add_prefixes_input_broken) { 453 if (add_prefixes_input_broken) {
444 RecordPrefixSetInfo(PREFIX_SET_CREATE_ADD_PREFIXES_CHECKSUM); 454 RecordPrefixSetInfo(PREFIX_SET_CREATE_ADD_PREFIXES_CHECKSUM);
445 } else if (prefixes_input_broken) { 455 } else if (prefixes_input_broken) {
446 RecordPrefixSetInfo(PREFIX_SET_CREATE_PREFIXES_CHECKSUM); 456 RecordPrefixSetInfo(PREFIX_SET_CREATE_PREFIXES_CHECKSUM);
447 } 457 }
448 458
449 if (prefix_set_broken) 459 if (prefix_set_broken) {
450 RecordPrefixSetInfo(PREFIX_SET_CREATE_PREFIX_SET_CHECKSUM); 460 RecordPrefixSetInfo(PREFIX_SET_CREATE_PREFIX_SET_CHECKSUM);
451 461
462 // Failing PrefixSet::CheckChecksum() implies that the set's
463 // internal data changed during construction. If the retry
464 // consistently succeeds, that implies memory corruption. If the
465 // retry consistently fails, that implies PrefixSet is broken.
466 scoped_ptr<safe_browsing::PrefixSet> retry_set(
467 new safe_browsing::PrefixSet(prefixes));
468 if (retry_set->CheckChecksum())
469 RecordPrefixSetInfo(PREFIX_SET_CREATE_PREFIX_SET_CHECKSUM_SUCCEEDED);
470
471 // TODO(shess): In case of double failure, consider pinning the
472 // data and calling NOTREACHED(). But it's a lot of data. Could
473 // also implement a binary search to constrain the amount of input
474 // to consider, but that's a lot of complexity.
475 }
476
452 // TODO(shess): Obviously this is a problem for operation of the 477 // TODO(shess): Obviously this is a problem for operation of the
453 // bloom filter! But for purposes of checking prefix set operation, 478 // bloom filter! But for purposes of checking prefix set operation,
454 // all that matters is not messing up the histograms recorded later. 479 // all that matters is not messing up the histograms recorded later.
455 if (bloom_filter_broken) 480 if (bloom_filter_broken) {
456 RecordPrefixSetInfo(PREFIX_SET_CREATE_BLOOM_FILTER_CHECKSUM); 481 RecordPrefixSetInfo(PREFIX_SET_CREATE_BLOOM_FILTER_CHECKSUM);
457 482
483 // As for PrefixSet, failing BloomFilter::CheckChecksum() implies
484 // that the filter's internal data was changed.
485 scoped_refptr<BloomFilter> retry_filter(new BloomFilter(filter_size));
486 for (std::vector<SBPrefix>::const_iterator iter = prefixes.begin();
487 iter != prefixes.end(); ++iter) {
488 retry_filter->Insert(*iter);
489 }
490 if (retry_filter->CheckChecksum())
491 RecordPrefixSetInfo(PREFIX_SET_CREATE_BLOOM_FILTER_CHECKSUM_SUCCEEDED);
492 }
493
458 // Attempt to isolate the case where the output of GetPrefixes() 494 // Attempt to isolate the case where the output of GetPrefixes()
459 // would differ from the input presented. This case implies that 495 // would differ from the input presented. This case implies that
460 // PrefixSet has an actual implementation flaw, and may in the 496 // PrefixSet has an actual implementation flaw, and may in the
461 // future warrant more aggressive action, such as somehow dumping 497 // future warrant more aggressive action, such as somehow dumping
462 // |prefixes| up to the crash server. 498 // |prefixes| up to the crash server.
463 if (get_prefixes_broken && !prefix_set_broken && !prefixes_input_broken) 499 if (get_prefixes_broken && !prefix_set_broken && !prefixes_input_broken)
464 RecordPrefixSetInfo(PREFIX_SET_CREATE_GET_PREFIXES_CHECKSUM); 500 RecordPrefixSetInfo(PREFIX_SET_CREATE_GET_PREFIXES_CHECKSUM);
465 501
466 // If anything broke, clear the prefix set to prevent pollution of 502 // If anything broke, clear the prefix set to prevent pollution of
467 // histograms generated later. 503 // histograms generated later.
(...skipping 1088 matching lines...) Expand 10 before | Expand all | Expand 10 after
1556 if (std::binary_search(new_whitelist.begin(), new_whitelist.end(), 1592 if (std::binary_search(new_whitelist.begin(), new_whitelist.end(),
1557 kill_switch)) { 1593 kill_switch)) {
1558 // The kill switch is whitelisted hence we whitelist all URLs. 1594 // The kill switch is whitelisted hence we whitelist all URLs.
1559 WhitelistEverything(whitelist); 1595 WhitelistEverything(whitelist);
1560 } else { 1596 } else {
1561 base::AutoLock locked(lookup_lock_); 1597 base::AutoLock locked(lookup_lock_);
1562 whitelist->second = false; 1598 whitelist->second = false;
1563 whitelist->first.swap(new_whitelist); 1599 whitelist->first.swap(new_whitelist);
1564 } 1600 }
1565 } 1601 }
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698