diff options
author | pkasting@chromium.org <pkasting@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-12-02 03:59:28 +0000 |
---|---|---|
committer | pkasting@chromium.org <pkasting@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-12-02 03:59:28 +0000 |
commit | 7753c3f48f5d3fea1ac91575de75d78f8085be83 (patch) | |
tree | f208cc49a35359cd4fee7f0f9f4b1ff3015e7e1e | |
parent | 3fb0ed2d312be00f356a9c5b3bca7ed522dc9e06 (diff) | |
download | chromium_src-7753c3f48f5d3fea1ac91575de75d78f8085be83.zip chromium_src-7753c3f48f5d3fea1ac91575de75d78f8085be83.tar.gz chromium_src-7753c3f48f5d3fea1ac91575de75d78f8085be83.tar.bz2 |
Make the safe_browsing_util.cc function definition order match the declaration order.
BUG=none
TEST=none
Review URL: http://codereview.chromium.org/460008
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@33545 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | chrome/browser/safe_browsing/safe_browsing_util.cc | 494 | ||||
-rw-r--r-- | chrome/browser/safe_browsing/safe_browsing_util.h | 6 |
2 files changed, 257 insertions, 243 deletions
diff --git a/chrome/browser/safe_browsing/safe_browsing_util.cc b/chrome/browser/safe_browsing/safe_browsing_util.cc index 3553beb..f8af1b2 100644 --- a/chrome/browser/safe_browsing/safe_browsing_util.cc +++ b/chrome/browser/safe_browsing/safe_browsing_util.cc @@ -22,192 +22,12 @@ static const char kContinueUrlFormat[] = static const char kReportParams[] = "?tpl=chrome&continue=%s&url=%s"; -namespace safe_browsing_util { - -const char kMalwareList[] = "goog-malware-shavar"; -const char kPhishingList[] = "goog-phish-shavar"; - -int GetListId(const std::string& name) { - if (name == kMalwareList) - return MALWARE; - else if (name == kPhishingList) - return PHISH; - - return -1; -} - -std::string GetListName(int list_id) { - switch (list_id) { - case MALWARE: - return kMalwareList; - case PHISH: - return kPhishingList; - default: - return ""; - } -} - -void GenerateHostsToCheck(const GURL& url, std::vector<std::string>* hosts) { - // Per Safe Browsing Protocol 2 spec, first we try the host. Then we try up - // to 4 hostnames starting with the last 5 components and successively - // removing the leading component. The TLD is skipped. - hosts->clear(); - int hostnames_checked = 0; - - std::string host = url.host(); - if (host.empty()) - return; - - const char* host_start = host.c_str(); - const char* index = host_start + host.size() - 1; - bool skipped_tld = false; - while (index != host_start && hostnames_checked < 4) { - if (*index == '.') { - if (!skipped_tld) { - skipped_tld = true; - } else { - const char* host_to_check = index + 1; - hosts->push_back(host_to_check); - hostnames_checked++; - } - } - - index--; - } - - // Check the full host too. - hosts->push_back(host.c_str()); -} - -// Per the Safe Browsing 2 spec, we try the exact path with/without the query -// parameters, and also the 4 paths formed by starting at the root and adding -// more path components. -void GeneratePathsToCheck(const GURL& url, std::vector<std::string>* paths) { - paths->clear(); - std::string path = url.path(); - if (path.empty()) - return; - - if (url.has_query()) - paths->push_back(path + "?" + url.query()); - - paths->push_back(path); - if (path == "/") - return; - - int path_components_checked = 0; - const char* path_start = path.c_str(); - const char* index = path_start; - const char* last_char = path_start + path.size() - 1; - while (*index && index != last_char && path_components_checked < 4) { - if (*index == '/') { - paths->push_back(std::string(path_start, index - path_start + 1)); - path_components_checked++; - } - - index++; - } -} - -int CompareFullHashes(const GURL& url, - const std::vector<SBFullHashResult>& full_hashes) { - if (full_hashes.empty()) - return -1; - - std::vector<std::string> hosts, paths; - GenerateHostsToCheck(url, &hosts); - GeneratePathsToCheck(url, &paths); - - for (size_t h = 0; h < hosts.size(); ++h) { - for (size_t p = 0; p < paths.size(); ++p) { - SBFullHash key; - base::SHA256HashString(hosts[h] + paths[p], - key.full_hash, - sizeof(SBFullHash)); - - for (size_t i = 0; i < full_hashes.size(); ++i) { - if (key == full_hashes[i].hash) - return static_cast<int>(i); - } - } - } - - return -1; -} - -bool IsPhishingList(const std::string& list_name) { - return list_name.find("-phish-") != std::string::npos; -} - -bool IsMalwareList(const std::string& list_name) { - return list_name.find("-malware-") != std::string::npos; -} - -static void DecodeWebSafe(std::string* decoded) { - DCHECK(decoded); - for (size_t i = 0; i < decoded->size(); ++i) { - switch ((*decoded)[i]) { - case '_': - (*decoded)[i] = '/'; - break; - case '-': - (*decoded)[i] = '+'; - break; - } - } -} -bool VerifyMAC(const std::string& key, const std::string& mac, - const char* data, int data_length) { - std::string key_copy = key; - DecodeWebSafe(&key_copy); - std::string decoded_key; - base::Base64Decode(key_copy, &decoded_key); - - std::string mac_copy = mac; - DecodeWebSafe(&mac_copy); - std::string decoded_mac; - base::Base64Decode(mac_copy, &decoded_mac); - - base::HMAC hmac(base::HMAC::SHA1); - if (!hmac.Init(decoded_key)) - return false; - const std::string data_str(data, data_length); - unsigned char digest[kSafeBrowsingMacDigestSize]; - if (!hmac.Sign(data_str, digest, kSafeBrowsingMacDigestSize)) - return false; - - return memcmp(digest, decoded_mac.data(), kSafeBrowsingMacDigestSize) == 0; -} - -void FreeChunks(std::deque<SBChunk>* chunks) { - while (!chunks->empty()) { - while (!chunks->front().hosts.empty()) { - chunks->front().hosts.front().entry->Destroy(); - chunks->front().hosts.pop_front(); - } - chunks->pop_front(); - } -} - -GURL GeneratePhishingReportUrl(const std::string& report_page, - const std::string& url_to_report) { - icu::Locale locale = icu::Locale::getDefault(); - const char* lang = locale.getLanguage(); - if (!lang) - lang = "en"; // fallback - const std::string continue_esc = - EscapeQueryParamValue(StringPrintf(kContinueUrlFormat, lang)); - const std::string current_esc = EscapeQueryParamValue(url_to_report); - GURL report_url(report_page + - StringPrintf(kReportParams, continue_esc.c_str(), current_esc.c_str())); - return google_util::AppendGoogleLocaleParam(report_url); -} - -} // namespace safe_browsing_util +// SBEntry --------------------------------------------------------------------- const int SBEntry::kMinSize = sizeof(SBEntry::Data); +// static SBEntry* SBEntry::Create(Type type, int prefix_count) { int size = Size(type, prefix_count); SBEntry *rv = static_cast<SBEntry*>(malloc(size)); @@ -237,6 +57,7 @@ int SBEntry::Size() const { return Size(type(), prefix_count()); } +// static int SBEntry::Size(Type type, int prefix_count) { return sizeof(Data) + prefix_count * PrefixSize(type); } @@ -319,6 +140,7 @@ int SBEntry::HashLen() const { return sizeof(SBFullHash); } +// static int SBEntry::PrefixSize(Type type) { switch (type) { case ADD_PREFIX: @@ -394,6 +216,7 @@ void SBEntry::SetFullHashAt(int index, const SBFullHash& full_hash) { } +// SBHostInfo ------------------------------------------------------------------ SBHostInfo::SBHostInfo() : size_(0) { } @@ -414,25 +237,6 @@ bool SBHostInfo::Initialize(const void* data, int size) { return true; } -bool SBHostInfo::IsValid() { - const SBEntry* entry = NULL; - while (GetNextEntry(&entry)) { - if (!entry->IsValid()) - return false; - } - return true; -} - -void SBHostInfo::Add(const SBEntry* entry) { - int new_size = size_ + entry->Size(); - char* new_data = new char[new_size]; - memcpy(new_data, data_.get(), size_); - memcpy(new_data + size_, entry, entry->Size()); - data_.reset(new_data); - size_ = new_size; - DCHECK(IsValid()); -} - void SBHostInfo::AddPrefixes(SBEntry* entry) { DCHECK(entry->IsAdd()); bool insert_entry = true; @@ -477,47 +281,6 @@ void SBHostInfo::AddPrefixes(SBEntry* entry) { DCHECK(IsValid()); } -void SBHostInfo::RemoveSubEntry(int list_id, int chunk_id) { - scoped_array<char> new_data(new char[size_]); // preallocate new data - char* write_ptr = new_data.get(); - int new_size = 0; - const SBEntry* entry = NULL; - while (GetNextEntry(&entry)) { - if (entry->list_id() == list_id && - entry->chunk_id() == chunk_id && - entry->IsSub() && - entry->prefix_count() == 0) { - continue; - } - - SBEntry* new_sub_entry = const_cast<SBEntry*>(entry); - scoped_array<char> data; - if (entry->IsSub() && entry->list_id() == list_id && - entry->prefix_count()) { - // Make a copy of the entry so that we can modify it. - data.reset(new char[entry->Size()]); - new_sub_entry = reinterpret_cast<SBEntry*>(data.get()); - memcpy(new_sub_entry, entry, entry->Size()); - // Remove any matching prefixes. - for (int i = 0; i < new_sub_entry->prefix_count(); ++i) { - if (new_sub_entry->ChunkIdAtPrefix(i) == chunk_id) - new_sub_entry->RemovePrefix(i--); - } - - if (new_sub_entry->prefix_count() == 0) - continue; // We removed the last prefix in the entry, so remove it. - } - - memcpy(write_ptr, new_sub_entry, new_sub_entry->Size()); - new_size += new_sub_entry->Size(); - write_ptr += new_sub_entry->Size(); - } - - size_ = new_size; - data_.reset(new_data.release()); - DCHECK(IsValid()); -} - void SBHostInfo::RemovePrefixes(SBEntry* sub_entry, bool persist) { DCHECK(sub_entry->IsSub()); scoped_array<char> new_data(new char[size_]); @@ -614,6 +377,15 @@ bool SBHostInfo::Contains(const std::vector<SBFullHash>& prefixes, return hits; } +bool SBHostInfo::IsValid() { + const SBEntry* entry = NULL; + while (GetNextEntry(&entry)) { + if (!entry->IsValid()) + return false; + } + return true; +} + bool SBHostInfo::GetNextEntry(const SBEntry** entry) { const char* current = reinterpret_cast<const char*>(*entry); @@ -634,3 +406,241 @@ bool SBHostInfo::GetNextEntry(const SBEntry** entry) { return false; } + +void SBHostInfo::Add(const SBEntry* entry) { + int new_size = size_ + entry->Size(); + char* new_data = new char[new_size]; + memcpy(new_data, data_.get(), size_); + memcpy(new_data + size_, entry, entry->Size()); + data_.reset(new_data); + size_ = new_size; + DCHECK(IsValid()); +} + +void SBHostInfo::RemoveSubEntry(int list_id, int chunk_id) { + scoped_array<char> new_data(new char[size_]); // preallocate new data + char* write_ptr = new_data.get(); + int new_size = 0; + const SBEntry* entry = NULL; + while (GetNextEntry(&entry)) { + if (entry->list_id() == list_id && + entry->chunk_id() == chunk_id && + entry->IsSub() && + entry->prefix_count() == 0) { + continue; + } + + SBEntry* new_sub_entry = const_cast<SBEntry*>(entry); + scoped_array<char> data; + if (entry->IsSub() && entry->list_id() == list_id && + entry->prefix_count()) { + // Make a copy of the entry so that we can modify it. + data.reset(new char[entry->Size()]); + new_sub_entry = reinterpret_cast<SBEntry*>(data.get()); + memcpy(new_sub_entry, entry, entry->Size()); + // Remove any matching prefixes. + for (int i = 0; i < new_sub_entry->prefix_count(); ++i) { + if (new_sub_entry->ChunkIdAtPrefix(i) == chunk_id) + new_sub_entry->RemovePrefix(i--); + } + + if (new_sub_entry->prefix_count() == 0) + continue; // We removed the last prefix in the entry, so remove it. + } + + memcpy(write_ptr, new_sub_entry, new_sub_entry->Size()); + new_size += new_sub_entry->Size(); + write_ptr += new_sub_entry->Size(); + } + + size_ = new_size; + data_.reset(new_data.release()); + DCHECK(IsValid()); +} + + +// Utility functions ----------------------------------------------------------- + +namespace safe_browsing_util { + +const char kMalwareList[] = "goog-malware-shavar"; +const char kPhishingList[] = "goog-phish-shavar"; + +int GetListId(const std::string& name) { + if (name == kMalwareList) + return MALWARE; + else if (name == kPhishingList) + return PHISH; + + return -1; +} + +std::string GetListName(int list_id) { + switch (list_id) { + case MALWARE: + return kMalwareList; + case PHISH: + return kPhishingList; + default: + return ""; + } +} + +void FreeChunks(std::deque<SBChunk>* chunks) { + while (!chunks->empty()) { + while (!chunks->front().hosts.empty()) { + chunks->front().hosts.front().entry->Destroy(); + chunks->front().hosts.pop_front(); + } + chunks->pop_front(); + } +} + +void GenerateHostsToCheck(const GURL& url, std::vector<std::string>* hosts) { + // Per Safe Browsing Protocol 2 spec, first we try the host. Then we try up + // to 4 hostnames starting with the last 5 components and successively + // removing the leading component. The TLD is skipped. + hosts->clear(); + int hostnames_checked = 0; + + std::string host = url.host(); + if (host.empty()) + return; + + const char* host_start = host.c_str(); + const char* index = host_start + host.size() - 1; + bool skipped_tld = false; + while (index != host_start && hostnames_checked < 4) { + if (*index == '.') { + if (!skipped_tld) { + skipped_tld = true; + } else { + const char* host_to_check = index + 1; + hosts->push_back(host_to_check); + hostnames_checked++; + } + } + + index--; + } + + // Check the full host too. + hosts->push_back(host.c_str()); +} + +// Per the Safe Browsing 2 spec, we try the exact path with/without the query +// parameters, and also the 4 paths formed by starting at the root and adding +// more path components. +void GeneratePathsToCheck(const GURL& url, std::vector<std::string>* paths) { + paths->clear(); + std::string path = url.path(); + if (path.empty()) + return; + + if (url.has_query()) + paths->push_back(path + "?" + url.query()); + + paths->push_back(path); + if (path == "/") + return; + + int path_components_checked = 0; + const char* path_start = path.c_str(); + const char* index = path_start; + const char* last_char = path_start + path.size() - 1; + while (*index && index != last_char && path_components_checked < 4) { + if (*index == '/') { + paths->push_back(std::string(path_start, index - path_start + 1)); + path_components_checked++; + } + + index++; + } +} + +int CompareFullHashes(const GURL& url, + const std::vector<SBFullHashResult>& full_hashes) { + if (full_hashes.empty()) + return -1; + + std::vector<std::string> hosts, paths; + GenerateHostsToCheck(url, &hosts); + GeneratePathsToCheck(url, &paths); + + for (size_t h = 0; h < hosts.size(); ++h) { + for (size_t p = 0; p < paths.size(); ++p) { + SBFullHash key; + base::SHA256HashString(hosts[h] + paths[p], + key.full_hash, + sizeof(SBFullHash)); + + for (size_t i = 0; i < full_hashes.size(); ++i) { + if (key == full_hashes[i].hash) + return static_cast<int>(i); + } + } + } + + return -1; +} + +bool IsPhishingList(const std::string& list_name) { + return list_name.find("-phish-") != std::string::npos; +} + +bool IsMalwareList(const std::string& list_name) { + return list_name.find("-malware-") != std::string::npos; +} + +static void DecodeWebSafe(std::string* decoded) { + DCHECK(decoded); + for (size_t i = 0; i < decoded->size(); ++i) { + switch ((*decoded)[i]) { + case '_': + (*decoded)[i] = '/'; + break; + case '-': + (*decoded)[i] = '+'; + break; + } + } +} + +bool VerifyMAC(const std::string& key, const std::string& mac, + const char* data, int data_length) { + std::string key_copy = key; + DecodeWebSafe(&key_copy); + std::string decoded_key; + base::Base64Decode(key_copy, &decoded_key); + + std::string mac_copy = mac; + DecodeWebSafe(&mac_copy); + std::string decoded_mac; + base::Base64Decode(mac_copy, &decoded_mac); + + base::HMAC hmac(base::HMAC::SHA1); + if (!hmac.Init(decoded_key)) + return false; + const std::string data_str(data, data_length); + unsigned char digest[kSafeBrowsingMacDigestSize]; + if (!hmac.Sign(data_str, digest, kSafeBrowsingMacDigestSize)) + return false; + + return memcmp(digest, decoded_mac.data(), kSafeBrowsingMacDigestSize) == 0; +} + +GURL GeneratePhishingReportUrl(const std::string& report_page, + const std::string& url_to_report) { + icu::Locale locale = icu::Locale::getDefault(); + const char* lang = locale.getLanguage(); + if (!lang) + lang = "en"; // fallback + const std::string continue_esc = + EscapeQueryParamValue(StringPrintf(kContinueUrlFormat, lang)); + const std::string current_esc = EscapeQueryParamValue(url_to_report); + GURL report_url(report_page + + StringPrintf(kReportParams, continue_esc.c_str(), current_esc.c_str())); + return google_util::AppendGoogleLocaleParam(report_url); +} + +} // namespace safe_browsing_util diff --git a/chrome/browser/safe_browsing/safe_browsing_util.h b/chrome/browser/safe_browsing/safe_browsing_util.h index 0a3c75da..fe69d0e 100644 --- a/chrome/browser/safe_browsing/safe_browsing_util.h +++ b/chrome/browser/safe_browsing/safe_browsing_util.h @@ -83,6 +83,8 @@ struct SBChunkDelete { }; +// SBEntry --------------------------------------------------------------------- + // Holds information about the prefixes for a hostkey. prefixes can either be // 4 bytes (truncated hash) or 32 bytes (full hash). // For adds: @@ -215,6 +217,8 @@ class SBEntry { }; +// SBHostInfo ------------------------------------------------------------------ + // Holds the hostkey specific information in the database. This is basically a // collection of SBEntry objects. class SBHostInfo { @@ -265,7 +269,7 @@ class SBHostInfo { }; -// Helper functions ----------------------------------------------------------- +// Utility functions ----------------------------------------------------------- namespace safe_browsing_util { |