diff options
author | aa@chromium.org <aa@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-07-25 03:15:58 +0000 |
---|---|---|
committer | aa@chromium.org <aa@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-07-25 03:15:58 +0000 |
commit | e435d6b7103f0d0c57133121454458bda6ccb69f (patch) | |
tree | 191cc13161304ec78aed429ff47c1000a3fb97c6 /net | |
parent | 354589750cf3959506e5c2a34e66cc462fb7f3c4 (diff) | |
download | chromium_src-e435d6b7103f0d0c57133121454458bda6ccb69f.zip chromium_src-e435d6b7103f0d0c57133121454458bda6ccb69f.tar.gz chromium_src-e435d6b7103f0d0c57133121454458bda6ccb69f.tar.bz2 |
Implement mimetype sniffing for extensions.
abarth: can you review the changes to mime_sniffer.cc?
paul: everything else?
BUG=13296
TEST=Added unit tests
Review URL: http://codereview.chromium.org/159345
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@21612 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'net')
-rw-r--r-- | net/base/mime_sniffer.cc | 44 | ||||
-rw-r--r-- | net/base/mime_sniffer_unittest.cc | 64 |
2 files changed, 107 insertions, 1 deletions
diff --git a/net/base/mime_sniffer.cc b/net/base/mime_sniffer.cc index 0a8bc57..07feb33 100644 --- a/net/base/mime_sniffer.cc +++ b/net/base/mime_sniffer.cc @@ -256,7 +256,7 @@ static bool CheckForMagicNumbers(const char* content, size_t size, Histogram* counter, std::string* result) { for (size_t i = 0; i < magic_len; ++i) { if (MatchMagicNumber(content, size, &(magic[i]), result)) { - counter->Add(static_cast<int>(i)); + if (counter) counter->Add(static_cast<int>(i)); return true; } } @@ -438,6 +438,43 @@ static bool IsUnknownMimeType(const std::string& mime_type) { return false; } +// Sniff a crx (chrome extension) file. +static bool SniffCRX(const char* content, size_t content_size, const GURL& url, + const std::string& type_hint, std::string* result) { + static SnifferHistogram counter("mime_sniffer.kSniffCRX", 3); + + // Technically, the crx magic number is just Cr24, but the bytes after that + // are a version number which changes infrequently. Including it in the + // sniffing gives us less room for error. If the version number ever changes, + // we can just add an entry to this list. + // + // TODO(aa): If we ever have another magic number, we'll want to pass a + // histogram into CheckForMagicNumbers(), below, to see which one matched. + const struct MagicNumber kCRXMagicNumbers[] = { + MAGIC_NUMBER("application/x-chrome-extension", "Cr24\x02\x00\x00\x00") + }; + + // Only consider files that have the extension ".crx". + const char kCRXExtension[] = ".crx"; + const int kExtensionLength = arraysize(kCRXExtension) - 1; // ignore null + if (url.path().rfind(kCRXExtension, std::string::npos, kExtensionLength) == + url.path().size() - kExtensionLength) { + counter.Add(1); + } else { + return false; + } + + if (CheckForMagicNumbers(content, content_size, + kCRXMagicNumbers, arraysize(kCRXMagicNumbers), + NULL, result)) { + counter.Add(2); + } else { + return false; + } + + return true; +} + bool ShouldSniffMimeType(const GURL& url, const std::string& mime_type) { static SnifferHistogram should_sniff_counter( "mime_sniffer.ShouldSniffMimeType2", 3); @@ -535,6 +572,11 @@ bool SniffMimeType(const char* content, size_t content_size, return content_size >= kMaxBytesToSniff; } + // CRX files (chrome extensions) have a special sniffing algorithm. It is + // tighter than the others because we don't have to match legacy behavior. + if (SniffCRX(content, content_size, url, type_hint, result)) + return true; + // Now we look in our large table of magic numbers to see if we can find // anything that matches the content. if (SniffForMagicNumbers(content, content_size, result)) diff --git a/net/base/mime_sniffer_unittest.cc b/net/base/mime_sniffer_unittest.cc index 96eb441..ed1634c 100644 --- a/net/base/mime_sniffer_unittest.cc +++ b/net/base/mime_sniffer_unittest.cc @@ -90,6 +90,70 @@ TEST(MimeSnifferTest, BasicSniffingTest) { TestArray(tests, arraysize(tests)); } +TEST(MimeSnifferTest, ChromeExtensionsTest) { + SnifferTest tests[] = { + // schemes + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.crx", + "", "application/x-chrome-extension" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "https://www.example.com/foo.crx", + "", "application/x-chrome-extension" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "ftp://www.example.com/foo.crx", + "", "application/x-chrome-extension" }, + + // some other mimetypes that should get converted + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.crx", + "text/plain", "application/x-chrome-extension" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.crx", + "application/octet-stream", "application/x-chrome-extension" }, + + // success edge cases + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.crx?query=string", + "", "application/x-chrome-extension" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo..crx", + "", "application/x-chrome-extension" }, + + // wrong file extension + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.bin", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.bin?monkey", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "invalid-url", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foocrx", + "", "application/octet-stream" }, + { "Cr24\x02\x00\x00\x00", sizeof("Cr24\x02\x00\x00\x00")-1, + "http://www.example.com/foo.crx.blech", + "", "application/octet-stream" }, + + // wrong magic + { "Cr24\x02\x00\x00\x01", sizeof("Cr24\x02\x00\x00\x01")-1, + "http://www.example.com/foo.crx?monkey", + "", "application/octet-stream" }, + }; + + TestArray(tests, arraysize(tests)); +} + TEST(MimeSnifferTest, MozillaCompatibleTest) { SnifferTest tests[] = { { " \n <hTmL>\n <hea", sizeof(" \n <hTmL>\n <hea")-1, |