OLD | NEW |
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 "net/base/net_util.h" | 5 #include "net/base/net_util.h" |
6 | 6 |
7 #include <string.h> | 7 #include <string.h> |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
10 | 10 |
11 #include "base/files/file_path.h" | 11 #include "base/files/file_path.h" |
12 #include "base/format_macros.h" | 12 #include "base/format_macros.h" |
13 #include "base/scoped_native_library.h" | 13 #include "base/scoped_native_library.h" |
14 #include "base/strings/string_number_conversions.h" | 14 #include "base/strings/string_number_conversions.h" |
15 #include "base/strings/string_util.h" | 15 #include "base/strings/string_util.h" |
16 #include "base/strings/stringprintf.h" | 16 #include "base/strings/stringprintf.h" |
17 #include "base/strings/sys_string_conversions.h" | 17 #include "base/strings/sys_string_conversions.h" |
18 #include "base/strings/utf_string_conversions.h" | 18 #include "base/strings/utf_string_conversions.h" |
19 #include "base/sys_byteorder.h" | 19 #include "base/sys_byteorder.h" |
20 #include "base/test/test_file_util.h" | |
21 #include "base/time/time.h" | 20 #include "base/time/time.h" |
22 #include "testing/gtest/include/gtest/gtest.h" | 21 #include "testing/gtest/include/gtest/gtest.h" |
23 #include "url/gurl.h" | 22 #include "url/gurl.h" |
24 | 23 |
25 #if defined(OS_WIN) | 24 #if defined(OS_WIN) |
26 #include <iphlpapi.h> | 25 #include <iphlpapi.h> |
27 #include <objbase.h> | 26 #include <objbase.h> |
28 #include "base/win/windows_version.h" | 27 #include "base/win/windows_version.h" |
29 #elif !defined(OS_ANDROID) | 28 #elif !defined(OS_ANDROID) |
30 #include <net/if.h> | 29 #include <net/if.h> |
31 #endif // OS_WIN | 30 #endif // OS_WIN |
32 | 31 |
33 using base::ASCIIToUTF16; | 32 using base::ASCIIToUTF16; |
34 using base::WideToUTF16; | 33 using base::WideToUTF16; |
35 | 34 |
36 namespace net { | 35 namespace net { |
37 | 36 |
38 namespace { | 37 namespace { |
39 | 38 |
40 static const size_t kNpos = base::string16::npos; | 39 static const size_t kNpos = base::string16::npos; |
41 | 40 |
42 struct FileCase { | |
43 const wchar_t* file; | |
44 const char* url; | |
45 }; | |
46 | |
47 struct HeaderCase { | 41 struct HeaderCase { |
48 const char* header_name; | 42 const char* header_name; |
49 const char* expected; | 43 const char* expected; |
50 }; | 44 }; |
51 | 45 |
52 struct HeaderParamCase { | 46 struct HeaderParamCase { |
53 const char* header_name; | 47 const char* header_name; |
54 const char* param_name; | 48 const char* param_name; |
55 const char* expected; | 49 const char* expected; |
56 }; | 50 }; |
57 | 51 |
58 struct FileNameCDCase { | |
59 const char* header_field; | |
60 const char* referrer_charset; | |
61 const wchar_t* expected; | |
62 }; | |
63 | |
64 const char* kLanguages[] = { | 52 const char* kLanguages[] = { |
65 "", "en", "zh-CN", "ja", "ko", | 53 "", "en", "zh-CN", "ja", "ko", |
66 "he", "ar", "ru", "el", "fr", | 54 "he", "ar", "ru", "el", "fr", |
67 "de", "pt", "sv", "th", "hi", | 55 "de", "pt", "sv", "th", "hi", |
68 "de,en", "el,en", "zh-TW,en", "ko,ja", "he,ru,en", | 56 "de,en", "el,en", "zh-TW,en", "ko,ja", "he,ru,en", |
69 "zh,ru,en" | 57 "zh,ru,en" |
70 }; | 58 }; |
71 | 59 |
72 struct IDNTestCase { | 60 struct IDNTestCase { |
73 const char* input; | 61 const char* input; |
(...skipping 315 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
389 size_t input_offset; | 377 size_t input_offset; |
390 size_t output_offset; | 378 size_t output_offset; |
391 }; | 379 }; |
392 | 380 |
393 struct CompliantHostCase { | 381 struct CompliantHostCase { |
394 const char* host; | 382 const char* host; |
395 const char* desired_tld; | 383 const char* desired_tld; |
396 bool expected_output; | 384 bool expected_output; |
397 }; | 385 }; |
398 | 386 |
399 struct GenerateFilenameCase { | |
400 int lineno; | |
401 const char* url; | |
402 const char* content_disp_header; | |
403 const char* referrer_charset; | |
404 const char* suggested_filename; | |
405 const char* mime_type; | |
406 const wchar_t* default_filename; | |
407 const wchar_t* expected_filename; | |
408 }; | |
409 | |
410 struct UrlTestData { | 387 struct UrlTestData { |
411 const char* description; | 388 const char* description; |
412 const char* input; | 389 const char* input; |
413 const char* languages; | 390 const char* languages; |
414 FormatUrlTypes format_types; | 391 FormatUrlTypes format_types; |
415 UnescapeRule::Type escape_rules; | 392 UnescapeRule::Type escape_rules; |
416 const wchar_t* output; // Use |wchar_t| to handle Unicode constants easily. | 393 const wchar_t* output; // Use |wchar_t| to handle Unicode constants easily. |
417 size_t prefix_len; | 394 size_t prefix_len; |
418 }; | 395 }; |
419 | 396 |
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
488 std::string DumpIPNumber(const IPAddressNumber& v) { | 465 std::string DumpIPNumber(const IPAddressNumber& v) { |
489 std::string out; | 466 std::string out; |
490 for (size_t i = 0; i < v.size(); ++i) { | 467 for (size_t i = 0; i < v.size(); ++i) { |
491 if (i != 0) | 468 if (i != 0) |
492 out.append(","); | 469 out.append(","); |
493 out.append(base::IntToString(static_cast<int>(v[i]))); | 470 out.append(base::IntToString(static_cast<int>(v[i]))); |
494 } | 471 } |
495 return out; | 472 return out; |
496 } | 473 } |
497 | 474 |
498 void RunGenerateFileNameTestCase(const GenerateFilenameCase* test_case) { | |
499 std::string default_filename(base::WideToUTF8(test_case->default_filename)); | |
500 base::FilePath file_path = GenerateFileName( | |
501 GURL(test_case->url), test_case->content_disp_header, | |
502 test_case->referrer_charset, test_case->suggested_filename, | |
503 test_case->mime_type, default_filename); | |
504 EXPECT_EQ(test_case->expected_filename, | |
505 file_util::FilePathAsWString(file_path)) | |
506 << "test case at line number: " << test_case->lineno; | |
507 } | |
508 | |
509 } // anonymous namespace | 475 } // anonymous namespace |
510 | 476 |
511 TEST(NetUtilTest, FileURLConversion) { | |
512 // a list of test file names and the corresponding URLs | |
513 const FileCase round_trip_cases[] = { | |
514 #if defined(OS_WIN) | |
515 {L"C:\\foo\\bar.txt", "file:///C:/foo/bar.txt"}, | |
516 {L"\\\\some computer\\foo\\bar.txt", | |
517 "file://some%20computer/foo/bar.txt"}, // UNC | |
518 {L"D:\\Name;with%some symbols*#", | |
519 "file:///D:/Name%3Bwith%25some%20symbols*%23"}, | |
520 // issue 14153: To be tested with the OS default codepage other than 1252. | |
521 {L"D:\\latin1\\caf\x00E9\x00DD.txt", | |
522 "file:///D:/latin1/caf%C3%A9%C3%9D.txt"}, | |
523 {L"D:\\otherlatin\\caf\x0119.txt", | |
524 "file:///D:/otherlatin/caf%C4%99.txt"}, | |
525 {L"D:\\greek\\\x03B1\x03B2\x03B3.txt", | |
526 "file:///D:/greek/%CE%B1%CE%B2%CE%B3.txt"}, | |
527 {L"D:\\Chinese\\\x6240\x6709\x4e2d\x6587\x7f51\x9875.doc", | |
528 "file:///D:/Chinese/%E6%89%80%E6%9C%89%E4%B8%AD%E6%96%87%E7%BD%91" | |
529 "%E9%A1%B5.doc"}, | |
530 {L"D:\\plane1\\\xD835\xDC00\xD835\xDC01.txt", // Math alphabet "AB" | |
531 "file:///D:/plane1/%F0%9D%90%80%F0%9D%90%81.txt"}, | |
532 #elif defined(OS_POSIX) | |
533 {L"/foo/bar.txt", "file:///foo/bar.txt"}, | |
534 {L"/foo/BAR.txt", "file:///foo/BAR.txt"}, | |
535 {L"/C:/foo/bar.txt", "file:///C:/foo/bar.txt"}, | |
536 {L"/foo/bar?.txt", "file:///foo/bar%3F.txt"}, | |
537 {L"/some computer/foo/bar.txt", "file:///some%20computer/foo/bar.txt"}, | |
538 {L"/Name;with%some symbols*#", "file:///Name%3Bwith%25some%20symbols*%23"}, | |
539 {L"/latin1/caf\x00E9\x00DD.txt", "file:///latin1/caf%C3%A9%C3%9D.txt"}, | |
540 {L"/otherlatin/caf\x0119.txt", "file:///otherlatin/caf%C4%99.txt"}, | |
541 {L"/greek/\x03B1\x03B2\x03B3.txt", "file:///greek/%CE%B1%CE%B2%CE%B3.txt"}, | |
542 {L"/Chinese/\x6240\x6709\x4e2d\x6587\x7f51\x9875.doc", | |
543 "file:///Chinese/%E6%89%80%E6%9C%89%E4%B8%AD%E6%96%87%E7%BD" | |
544 "%91%E9%A1%B5.doc"}, | |
545 {L"/plane1/\x1D400\x1D401.txt", // Math alphabet "AB" | |
546 "file:///plane1/%F0%9D%90%80%F0%9D%90%81.txt"}, | |
547 #endif | |
548 }; | |
549 | |
550 // First, we'll test that we can round-trip all of the above cases of URLs | |
551 base::FilePath output; | |
552 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(round_trip_cases); i++) { | |
553 // convert to the file URL | |
554 GURL file_url(FilePathToFileURL( | |
555 file_util::WStringAsFilePath(round_trip_cases[i].file))); | |
556 EXPECT_EQ(round_trip_cases[i].url, file_url.spec()); | |
557 | |
558 // Back to the filename. | |
559 EXPECT_TRUE(FileURLToFilePath(file_url, &output)); | |
560 EXPECT_EQ(round_trip_cases[i].file, file_util::FilePathAsWString(output)); | |
561 } | |
562 | |
563 // Test that various file: URLs get decoded into the correct file type | |
564 FileCase url_cases[] = { | |
565 #if defined(OS_WIN) | |
566 {L"C:\\foo\\bar.txt", "file:c|/foo\\bar.txt"}, | |
567 {L"C:\\foo\\bar.txt", "file:/c:/foo/bar.txt"}, | |
568 {L"\\\\foo\\bar.txt", "file://foo\\bar.txt"}, | |
569 {L"C:\\foo\\bar.txt", "file:///c:/foo/bar.txt"}, | |
570 {L"\\\\foo\\bar.txt", "file:////foo\\bar.txt"}, | |
571 {L"\\\\foo\\bar.txt", "file:/foo/bar.txt"}, | |
572 {L"\\\\foo\\bar.txt", "file://foo\\bar.txt"}, | |
573 {L"C:\\foo\\bar.txt", "file:\\\\\\c:/foo/bar.txt"}, | |
574 #elif defined(OS_POSIX) | |
575 {L"/c:/foo/bar.txt", "file:/c:/foo/bar.txt"}, | |
576 {L"/c:/foo/bar.txt", "file:///c:/foo/bar.txt"}, | |
577 {L"/foo/bar.txt", "file:/foo/bar.txt"}, | |
578 {L"/c:/foo/bar.txt", "file:\\\\\\c:/foo/bar.txt"}, | |
579 {L"/foo/bar.txt", "file:foo/bar.txt"}, | |
580 {L"/bar.txt", "file://foo/bar.txt"}, | |
581 {L"/foo/bar.txt", "file:///foo/bar.txt"}, | |
582 {L"/foo/bar.txt", "file:////foo/bar.txt"}, | |
583 {L"/foo/bar.txt", "file:////foo//bar.txt"}, | |
584 {L"/foo/bar.txt", "file:////foo///bar.txt"}, | |
585 {L"/foo/bar.txt", "file:////foo////bar.txt"}, | |
586 {L"/c:/foo/bar.txt", "file:\\\\\\c:/foo/bar.txt"}, | |
587 {L"/c:/foo/bar.txt", "file:c:/foo/bar.txt"}, | |
588 // We get these wrong because GURL turns back slashes into forward | |
589 // slashes. | |
590 //{L"/foo%5Cbar.txt", "file://foo\\bar.txt"}, | |
591 //{L"/c|/foo%5Cbar.txt", "file:c|/foo\\bar.txt"}, | |
592 //{L"/foo%5Cbar.txt", "file://foo\\bar.txt"}, | |
593 //{L"/foo%5Cbar.txt", "file:////foo\\bar.txt"}, | |
594 //{L"/foo%5Cbar.txt", "file://foo\\bar.txt"}, | |
595 #endif | |
596 }; | |
597 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(url_cases); i++) { | |
598 FileURLToFilePath(GURL(url_cases[i].url), &output); | |
599 EXPECT_EQ(url_cases[i].file, file_util::FilePathAsWString(output)); | |
600 } | |
601 | |
602 // Unfortunately, UTF8ToWide discards invalid UTF8 input. | |
603 #ifdef BUG_878908_IS_FIXED | |
604 // Test that no conversion happens if the UTF-8 input is invalid, and that | |
605 // the input is preserved in UTF-8 | |
606 const char invalid_utf8[] = "file:///d:/Blah/\xff.doc"; | |
607 const wchar_t invalid_wide[] = L"D:\\Blah\\\xff.doc"; | |
608 EXPECT_TRUE(FileURLToFilePath( | |
609 GURL(std::string(invalid_utf8)), &output)); | |
610 EXPECT_EQ(std::wstring(invalid_wide), output); | |
611 #endif | |
612 | |
613 // Test that if a file URL is malformed, we get a failure | |
614 EXPECT_FALSE(FileURLToFilePath(GURL("filefoobar"), &output)); | |
615 } | |
616 | |
617 TEST(NetUtilTest, GetIdentityFromURL) { | 477 TEST(NetUtilTest, GetIdentityFromURL) { |
618 struct { | 478 struct { |
619 const char* input_url; | 479 const char* input_url; |
620 const char* expected_username; | 480 const char* expected_username; |
621 const char* expected_password; | 481 const char* expected_password; |
622 } tests[] = { | 482 } tests[] = { |
623 { | 483 { |
624 "http://username:password@google.com", | 484 "http://username:password@google.com", |
625 "username", | 485 "username", |
626 "password", | 486 "password", |
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
797 } | 657 } |
798 } | 658 } |
799 | 659 |
800 TEST(NetUtilTest, StripWWW) { | 660 TEST(NetUtilTest, StripWWW) { |
801 EXPECT_EQ(base::string16(), StripWWW(base::string16())); | 661 EXPECT_EQ(base::string16(), StripWWW(base::string16())); |
802 EXPECT_EQ(base::string16(), StripWWW(ASCIIToUTF16("www."))); | 662 EXPECT_EQ(base::string16(), StripWWW(ASCIIToUTF16("www."))); |
803 EXPECT_EQ(ASCIIToUTF16("blah"), StripWWW(ASCIIToUTF16("www.blah"))); | 663 EXPECT_EQ(ASCIIToUTF16("blah"), StripWWW(ASCIIToUTF16("www.blah"))); |
804 EXPECT_EQ(ASCIIToUTF16("blah"), StripWWW(ASCIIToUTF16("blah"))); | 664 EXPECT_EQ(ASCIIToUTF16("blah"), StripWWW(ASCIIToUTF16("blah"))); |
805 } | 665 } |
806 | 666 |
807 #if defined(OS_WIN) | |
808 #define JPEG_EXT L".jpg" | |
809 #define HTML_EXT L".htm" | |
810 #elif defined(OS_MACOSX) | |
811 #define JPEG_EXT L".jpeg" | |
812 #define HTML_EXT L".html" | |
813 #else | |
814 #define JPEG_EXT L".jpg" | |
815 #define HTML_EXT L".html" | |
816 #endif | |
817 #define TXT_EXT L".txt" | |
818 #define TAR_EXT L".tar" | |
819 | |
820 TEST(NetUtilTest, GenerateSafeFileName) { | |
821 const struct { | |
822 const char* mime_type; | |
823 const base::FilePath::CharType* filename; | |
824 const base::FilePath::CharType* expected_filename; | |
825 } safe_tests[] = { | |
826 #if defined(OS_WIN) | |
827 { | |
828 "text/html", | |
829 FILE_PATH_LITERAL("C:\\foo\\bar.htm"), | |
830 FILE_PATH_LITERAL("C:\\foo\\bar.htm") | |
831 }, | |
832 { | |
833 "text/html", | |
834 FILE_PATH_LITERAL("C:\\foo\\bar.html"), | |
835 FILE_PATH_LITERAL("C:\\foo\\bar.html") | |
836 }, | |
837 { | |
838 "text/html", | |
839 FILE_PATH_LITERAL("C:\\foo\\bar"), | |
840 FILE_PATH_LITERAL("C:\\foo\\bar.htm") | |
841 }, | |
842 { | |
843 "image/png", | |
844 FILE_PATH_LITERAL("C:\\bar.html"), | |
845 FILE_PATH_LITERAL("C:\\bar.html") | |
846 }, | |
847 { | |
848 "image/png", | |
849 FILE_PATH_LITERAL("C:\\bar"), | |
850 FILE_PATH_LITERAL("C:\\bar.png") | |
851 }, | |
852 { | |
853 "text/html", | |
854 FILE_PATH_LITERAL("C:\\foo\\bar.exe"), | |
855 FILE_PATH_LITERAL("C:\\foo\\bar.exe") | |
856 }, | |
857 { | |
858 "image/gif", | |
859 FILE_PATH_LITERAL("C:\\foo\\bar.exe"), | |
860 FILE_PATH_LITERAL("C:\\foo\\bar.exe") | |
861 }, | |
862 { | |
863 "text/html", | |
864 FILE_PATH_LITERAL("C:\\foo\\google.com"), | |
865 FILE_PATH_LITERAL("C:\\foo\\google.com") | |
866 }, | |
867 { | |
868 "text/html", | |
869 FILE_PATH_LITERAL("C:\\foo\\con.htm"), | |
870 FILE_PATH_LITERAL("C:\\foo\\_con.htm") | |
871 }, | |
872 { | |
873 "text/html", | |
874 FILE_PATH_LITERAL("C:\\foo\\con"), | |
875 FILE_PATH_LITERAL("C:\\foo\\_con.htm") | |
876 }, | |
877 { | |
878 "text/html", | |
879 FILE_PATH_LITERAL("C:\\foo\\harmless.{not-really-this-may-be-a-guid}"), | |
880 FILE_PATH_LITERAL("C:\\foo\\harmless.download") | |
881 }, | |
882 { | |
883 "text/html", | |
884 FILE_PATH_LITERAL("C:\\foo\\harmless.local"), | |
885 FILE_PATH_LITERAL("C:\\foo\\harmless.download") | |
886 }, | |
887 { | |
888 "text/html", | |
889 FILE_PATH_LITERAL("C:\\foo\\harmless.lnk"), | |
890 FILE_PATH_LITERAL("C:\\foo\\harmless.download") | |
891 }, | |
892 { | |
893 "text/html", | |
894 FILE_PATH_LITERAL("C:\\foo\\harmless.{mismatched-"), | |
895 FILE_PATH_LITERAL("C:\\foo\\harmless.{mismatched-") | |
896 }, | |
897 // Allow extension synonyms. | |
898 { | |
899 "image/jpeg", | |
900 FILE_PATH_LITERAL("C:\\foo\\bar.jpg"), | |
901 FILE_PATH_LITERAL("C:\\foo\\bar.jpg") | |
902 }, | |
903 { | |
904 "image/jpeg", | |
905 FILE_PATH_LITERAL("C:\\foo\\bar.jpeg"), | |
906 FILE_PATH_LITERAL("C:\\foo\\bar.jpeg") | |
907 }, | |
908 #else // !defined(OS_WIN) | |
909 { | |
910 "text/html", | |
911 FILE_PATH_LITERAL("/foo/bar.htm"), | |
912 FILE_PATH_LITERAL("/foo/bar.htm") | |
913 }, | |
914 { | |
915 "text/html", | |
916 FILE_PATH_LITERAL("/foo/bar.html"), | |
917 FILE_PATH_LITERAL("/foo/bar.html") | |
918 }, | |
919 { | |
920 "text/html", | |
921 FILE_PATH_LITERAL("/foo/bar"), | |
922 FILE_PATH_LITERAL("/foo/bar.html") | |
923 }, | |
924 { | |
925 "image/png", | |
926 FILE_PATH_LITERAL("/bar.html"), | |
927 FILE_PATH_LITERAL("/bar.html") | |
928 }, | |
929 { | |
930 "image/png", | |
931 FILE_PATH_LITERAL("/bar"), | |
932 FILE_PATH_LITERAL("/bar.png") | |
933 }, | |
934 { | |
935 "image/gif", | |
936 FILE_PATH_LITERAL("/foo/bar.exe"), | |
937 FILE_PATH_LITERAL("/foo/bar.exe") | |
938 }, | |
939 { | |
940 "text/html", | |
941 FILE_PATH_LITERAL("/foo/google.com"), | |
942 FILE_PATH_LITERAL("/foo/google.com") | |
943 }, | |
944 { | |
945 "text/html", | |
946 FILE_PATH_LITERAL("/foo/con.htm"), | |
947 FILE_PATH_LITERAL("/foo/con.htm") | |
948 }, | |
949 { | |
950 "text/html", | |
951 FILE_PATH_LITERAL("/foo/con"), | |
952 FILE_PATH_LITERAL("/foo/con.html") | |
953 }, | |
954 // Allow extension synonyms. | |
955 { | |
956 "image/jpeg", | |
957 FILE_PATH_LITERAL("/bar.jpg"), | |
958 FILE_PATH_LITERAL("/bar.jpg") | |
959 }, | |
960 { | |
961 "image/jpeg", | |
962 FILE_PATH_LITERAL("/bar.jpeg"), | |
963 FILE_PATH_LITERAL("/bar.jpeg") | |
964 }, | |
965 #endif // !defined(OS_WIN) | |
966 }; | |
967 | |
968 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(safe_tests); ++i) { | |
969 base::FilePath file_path(safe_tests[i].filename); | |
970 GenerateSafeFileName(safe_tests[i].mime_type, false, &file_path); | |
971 EXPECT_EQ(safe_tests[i].expected_filename, file_path.value()) | |
972 << "Iteration " << i; | |
973 } | |
974 } | |
975 | |
976 TEST(NetUtilTest, GenerateFileName) { | |
977 #if defined(OS_POSIX) && !defined(OS_MACOSX) && !defined(OS_ANDROID) | |
978 // This test doesn't run when the locale is not UTF-8 because some of the | |
979 // string conversions fail. This is OK (we have the default value) but they | |
980 // don't match our expectations. | |
981 std::string locale = setlocale(LC_CTYPE, NULL); | |
982 StringToLowerASCII(&locale); | |
983 EXPECT_TRUE(locale.find("utf-8") != std::string::npos || | |
984 locale.find("utf8") != std::string::npos) | |
985 << "Your locale (" << locale << ") must be set to UTF-8 " | |
986 << "for this test to pass!"; | |
987 #endif | |
988 | |
989 // Tests whether the correct filename is selected from the the given | |
990 // parameters and that Content-Disposition headers are properly | |
991 // handled including failovers when the header is malformed. | |
992 const GenerateFilenameCase selection_tests[] = { | |
993 { | |
994 __LINE__, | |
995 "http://www.google.com/", | |
996 "attachment; filename=test.html", | |
997 "", | |
998 "", | |
999 "", | |
1000 L"", | |
1001 L"test.html" | |
1002 }, | |
1003 { | |
1004 __LINE__, | |
1005 "http://www.google.com/", | |
1006 "attachment; filename=\"test.html\"", | |
1007 "", | |
1008 "", | |
1009 "", | |
1010 L"", | |
1011 L"test.html" | |
1012 }, | |
1013 { | |
1014 __LINE__, | |
1015 "http://www.google.com/", | |
1016 "attachment; filename= \"test.html\"", | |
1017 "", | |
1018 "", | |
1019 "", | |
1020 L"", | |
1021 L"test.html" | |
1022 }, | |
1023 { | |
1024 __LINE__, | |
1025 "http://www.google.com/", | |
1026 "attachment; filename = \"test.html\"", | |
1027 "", | |
1028 "", | |
1029 "", | |
1030 L"", | |
1031 L"test.html" | |
1032 }, | |
1033 { // filename is whitespace. Should failover to URL host | |
1034 __LINE__, | |
1035 "http://www.google.com/", | |
1036 "attachment; filename= ", | |
1037 "", | |
1038 "", | |
1039 "", | |
1040 L"", | |
1041 L"www.google.com" | |
1042 }, | |
1043 { // No filename. | |
1044 __LINE__, | |
1045 "http://www.google.com/path/test.html", | |
1046 "attachment", | |
1047 "", | |
1048 "", | |
1049 "", | |
1050 L"", | |
1051 L"test.html" | |
1052 }, | |
1053 { // Ditto | |
1054 __LINE__, | |
1055 "http://www.google.com/path/test.html", | |
1056 "attachment;", | |
1057 "", | |
1058 "", | |
1059 "", | |
1060 L"", | |
1061 L"test.html" | |
1062 }, | |
1063 { // No C-D | |
1064 __LINE__, | |
1065 "http://www.google.com/", | |
1066 "", | |
1067 "", | |
1068 "", | |
1069 "", | |
1070 L"", | |
1071 L"www.google.com" | |
1072 }, | |
1073 { | |
1074 __LINE__, | |
1075 "http://www.google.com/test.html", | |
1076 "", | |
1077 "", | |
1078 "", | |
1079 "", | |
1080 L"", | |
1081 L"test.html" | |
1082 }, | |
1083 { // Now that we use src/url's ExtractFileName, this case falls back to | |
1084 // the hostname. If this behavior is not desirable, we'd better change | |
1085 // ExtractFileName (in url_parse). | |
1086 __LINE__, | |
1087 "http://www.google.com/path/", | |
1088 "", | |
1089 "", | |
1090 "", | |
1091 "", | |
1092 L"", | |
1093 L"www.google.com" | |
1094 }, | |
1095 { | |
1096 __LINE__, | |
1097 "http://www.google.com/path", | |
1098 "", | |
1099 "", | |
1100 "", | |
1101 "", | |
1102 L"", | |
1103 L"path" | |
1104 }, | |
1105 { | |
1106 __LINE__, | |
1107 "file:///", | |
1108 "", | |
1109 "", | |
1110 "", | |
1111 "", | |
1112 L"", | |
1113 L"download" | |
1114 }, | |
1115 { | |
1116 __LINE__, | |
1117 "file:///path/testfile", | |
1118 "", | |
1119 "", | |
1120 "", | |
1121 "", | |
1122 L"", | |
1123 L"testfile" | |
1124 }, | |
1125 { | |
1126 __LINE__, | |
1127 "non-standard-scheme:", | |
1128 "", | |
1129 "", | |
1130 "", | |
1131 "", | |
1132 L"", | |
1133 L"download" | |
1134 }, | |
1135 { // C-D should override default | |
1136 __LINE__, | |
1137 "http://www.google.com/", | |
1138 "attachment; filename =\"test.html\"", | |
1139 "", | |
1140 "", | |
1141 "", | |
1142 L"download", | |
1143 L"test.html" | |
1144 }, | |
1145 { // But the URL shouldn't | |
1146 __LINE__, | |
1147 "http://www.google.com/", | |
1148 "", | |
1149 "", | |
1150 "", | |
1151 "", | |
1152 L"download", | |
1153 L"download" | |
1154 }, | |
1155 { | |
1156 __LINE__, | |
1157 "http://www.google.com/", | |
1158 "attachment; filename=\"../test.html\"", | |
1159 "", | |
1160 "", | |
1161 "", | |
1162 L"", | |
1163 L"-test.html" | |
1164 }, | |
1165 { | |
1166 __LINE__, | |
1167 "http://www.google.com/", | |
1168 "attachment; filename=\"..\\test.html\"", | |
1169 "", | |
1170 "", | |
1171 "", | |
1172 L"", | |
1173 L"test.html" | |
1174 }, | |
1175 { | |
1176 __LINE__, | |
1177 "http://www.google.com/", | |
1178 "attachment; filename=\"..\\\\test.html\"", | |
1179 "", | |
1180 "", | |
1181 "", | |
1182 L"", | |
1183 L"-test.html" | |
1184 }, | |
1185 { // Filename disappears after leading and trailing periods are removed. | |
1186 __LINE__, | |
1187 "http://www.google.com/", | |
1188 "attachment; filename=\"..\"", | |
1189 "", | |
1190 "", | |
1191 "", | |
1192 L"default", | |
1193 L"default" | |
1194 }, | |
1195 { // C-D specified filename disappears. Failover to final filename. | |
1196 __LINE__, | |
1197 "http://www.google.com/test.html", | |
1198 "attachment; filename=\"..\"", | |
1199 "", | |
1200 "", | |
1201 "", | |
1202 L"default", | |
1203 L"default" | |
1204 }, | |
1205 // Below is a small subset of cases taken from HttpContentDisposition tests. | |
1206 { | |
1207 __LINE__, | |
1208 "http://www.google.com/", | |
1209 "attachment; filename=\"%EC%98%88%EC%88%A0%20" | |
1210 "%EC%98%88%EC%88%A0.jpg\"", | |
1211 "", | |
1212 "", | |
1213 "", | |
1214 L"", | |
1215 L"\uc608\uc220 \uc608\uc220.jpg" | |
1216 }, | |
1217 { | |
1218 __LINE__, | |
1219 "http://www.google.com/%EC%98%88%EC%88%A0%20%EC%98%88%EC%88%A0.jpg", | |
1220 "", | |
1221 "", | |
1222 "", | |
1223 "", | |
1224 L"download", | |
1225 L"\uc608\uc220 \uc608\uc220.jpg" | |
1226 }, | |
1227 { | |
1228 __LINE__, | |
1229 "http://www.google.com/", | |
1230 "attachment;", | |
1231 "", | |
1232 "", | |
1233 "", | |
1234 L"\uB2E4\uC6B4\uB85C\uB4DC", | |
1235 L"\uB2E4\uC6B4\uB85C\uB4DC" | |
1236 }, | |
1237 { | |
1238 __LINE__, | |
1239 "http://www.google.com/", | |
1240 "attachment; filename=\"=?EUC-JP?Q?=B7=DD=BD=" | |
1241 "D13=2Epng?=\"", | |
1242 "", | |
1243 "", | |
1244 "", | |
1245 L"download", | |
1246 L"\u82b8\u88533.png" | |
1247 }, | |
1248 { | |
1249 __LINE__, | |
1250 "http://www.example.com/images?id=3", | |
1251 "attachment; filename=caf\xc3\xa9.png", | |
1252 "iso-8859-1", | |
1253 "", | |
1254 "", | |
1255 L"", | |
1256 L"caf\u00e9.png" | |
1257 }, | |
1258 { | |
1259 __LINE__, | |
1260 "http://www.example.com/images?id=3", | |
1261 "attachment; filename=caf\xe5.png", | |
1262 "windows-1253", | |
1263 "", | |
1264 "", | |
1265 L"", | |
1266 L"caf\u03b5.png" | |
1267 }, | |
1268 { | |
1269 __LINE__, | |
1270 "http://www.example.com/file?id=3", | |
1271 "attachment; name=\xcf\xc2\xd4\xd8.zip", | |
1272 "GBK", | |
1273 "", | |
1274 "", | |
1275 L"", | |
1276 L"\u4e0b\u8f7d.zip" | |
1277 }, | |
1278 { // Invalid C-D header. Extracts filename from url. | |
1279 __LINE__, | |
1280 "http://www.google.com/test.html", | |
1281 "attachment; filename==?iiso88591?Q?caf=EG?=", | |
1282 "", | |
1283 "", | |
1284 "", | |
1285 L"", | |
1286 L"test.html" | |
1287 }, | |
1288 // about: and data: URLs | |
1289 { | |
1290 __LINE__, | |
1291 "about:chrome", | |
1292 "", | |
1293 "", | |
1294 "", | |
1295 "", | |
1296 L"", | |
1297 L"download" | |
1298 }, | |
1299 { | |
1300 __LINE__, | |
1301 "data:,looks/like/a.path", | |
1302 "", | |
1303 "", | |
1304 "", | |
1305 "", | |
1306 L"", | |
1307 L"download" | |
1308 }, | |
1309 { | |
1310 __LINE__, | |
1311 "data:text/plain;base64,VG8gYmUgb3Igbm90IHRvIGJlLg=", | |
1312 "", | |
1313 "", | |
1314 "", | |
1315 "", | |
1316 L"", | |
1317 L"download" | |
1318 }, | |
1319 { | |
1320 __LINE__, | |
1321 "data:,looks/like/a.path", | |
1322 "", | |
1323 "", | |
1324 "", | |
1325 "", | |
1326 L"default_filename_is_given", | |
1327 L"default_filename_is_given" | |
1328 }, | |
1329 { | |
1330 __LINE__, | |
1331 "data:,looks/like/a.path", | |
1332 "", | |
1333 "", | |
1334 "", | |
1335 "", | |
1336 L"\u65e5\u672c\u8a9e", // Japanese Kanji. | |
1337 L"\u65e5\u672c\u8a9e" | |
1338 }, | |
1339 { // The filename encoding is specified by the referrer charset. | |
1340 __LINE__, | |
1341 "http://example.com/V%FDvojov%E1%20psychologie.doc", | |
1342 "", | |
1343 "iso-8859-1", | |
1344 "", | |
1345 "", | |
1346 L"", | |
1347 L"V\u00fdvojov\u00e1 psychologie.doc" | |
1348 }, | |
1349 { // Suggested filename takes precedence over URL | |
1350 __LINE__, | |
1351 "http://www.google.com/test", | |
1352 "", | |
1353 "", | |
1354 "suggested", | |
1355 "", | |
1356 L"", | |
1357 L"suggested" | |
1358 }, | |
1359 { // The content-disposition has higher precedence over the suggested name. | |
1360 __LINE__, | |
1361 "http://www.google.com/test", | |
1362 "attachment; filename=test.html", | |
1363 "", | |
1364 "suggested", | |
1365 "", | |
1366 L"", | |
1367 L"test.html" | |
1368 }, | |
1369 #if 0 | |
1370 { // The filename encoding doesn't match the referrer charset, the system | |
1371 // charset, or UTF-8. | |
1372 // TODO(jshin): we need to handle this case. | |
1373 __LINE__, | |
1374 "http://example.com/V%FDvojov%E1%20psychologie.doc", | |
1375 "", | |
1376 "utf-8", | |
1377 "", | |
1378 "", | |
1379 L"", | |
1380 L"V\u00fdvojov\u00e1 psychologie.doc", | |
1381 }, | |
1382 #endif | |
1383 // Raw 8bit characters in C-D | |
1384 { | |
1385 __LINE__, | |
1386 "http://www.example.com/images?id=3", | |
1387 "attachment; filename=caf\xc3\xa9.png", | |
1388 "iso-8859-1", | |
1389 "", | |
1390 "image/png", | |
1391 L"", | |
1392 L"caf\u00e9.png" | |
1393 }, | |
1394 { | |
1395 __LINE__, | |
1396 "http://www.example.com/images?id=3", | |
1397 "attachment; filename=caf\xe5.png", | |
1398 "windows-1253", | |
1399 "", | |
1400 "image/png", | |
1401 L"", | |
1402 L"caf\u03b5.png" | |
1403 }, | |
1404 { // No 'filename' keyword in the disposition, use the URL | |
1405 __LINE__, | |
1406 "http://www.evil.com/my_download.txt", | |
1407 "a_file_name.txt", | |
1408 "", | |
1409 "", | |
1410 "text/plain", | |
1411 L"download", | |
1412 L"my_download.txt" | |
1413 }, | |
1414 { // Spaces in the disposition file name | |
1415 __LINE__, | |
1416 "http://www.frontpagehacker.com/a_download.exe", | |
1417 "filename=My Downloaded File.exe", | |
1418 "", | |
1419 "", | |
1420 "application/octet-stream", | |
1421 L"download", | |
1422 L"My Downloaded File.exe" | |
1423 }, | |
1424 { // % encoded | |
1425 __LINE__, | |
1426 "http://www.examples.com/", | |
1427 "attachment; " | |
1428 "filename=\"%EC%98%88%EC%88%A0%20%EC%98%88%EC%88%A0.jpg\"", | |
1429 "", | |
1430 "", | |
1431 "image/jpeg", | |
1432 L"download", | |
1433 L"\uc608\uc220 \uc608\uc220.jpg" | |
1434 }, | |
1435 { // name= parameter | |
1436 __LINE__, | |
1437 "http://www.examples.com/q.cgi?id=abc", | |
1438 "attachment; name=abc de.pdf", | |
1439 "", | |
1440 "", | |
1441 "application/octet-stream", | |
1442 L"download", | |
1443 L"abc de.pdf" | |
1444 }, | |
1445 { | |
1446 __LINE__, | |
1447 "http://www.example.com/path", | |
1448 "filename=\"=?EUC-JP?Q?=B7=DD=BD=D13=2Epng?=\"", | |
1449 "", | |
1450 "", | |
1451 "image/png", | |
1452 L"download", | |
1453 L"\x82b8\x8853" L"3.png" | |
1454 }, | |
1455 { // The following two have invalid CD headers and filenames come from the | |
1456 // URL. | |
1457 __LINE__, | |
1458 "http://www.example.com/test%20123", | |
1459 "attachment; filename==?iiso88591?Q?caf=EG?=", | |
1460 "", | |
1461 "", | |
1462 "image/jpeg", | |
1463 L"download", | |
1464 L"test 123" JPEG_EXT | |
1465 }, | |
1466 { | |
1467 __LINE__, | |
1468 "http://www.google.com/%EC%98%88%EC%88%A0%20%EC%98%88%EC%88%A0.jpg", | |
1469 "malformed_disposition", | |
1470 "", | |
1471 "", | |
1472 "image/jpeg", | |
1473 L"download", | |
1474 L"\uc608\uc220 \uc608\uc220.jpg" | |
1475 }, | |
1476 { // Invalid C-D. No filename from URL. Falls back to 'download'. | |
1477 __LINE__, | |
1478 "http://www.google.com/path1/path2/", | |
1479 "attachment; filename==?iso88591?Q?caf=E3?", | |
1480 "", | |
1481 "", | |
1482 "image/jpeg", | |
1483 L"download", | |
1484 L"download" JPEG_EXT | |
1485 }, | |
1486 }; | |
1487 | |
1488 // Tests filename generation. Once the correct filename is | |
1489 // selected, they should be passed through the validation steps and | |
1490 // a correct extension should be added if necessary. | |
1491 const GenerateFilenameCase generation_tests[] = { | |
1492 // Dotfiles. Ensures preceeding period(s) stripped. | |
1493 { | |
1494 __LINE__, | |
1495 "http://www.google.com/.test.html", | |
1496 "", | |
1497 "", | |
1498 "", | |
1499 "", | |
1500 L"", | |
1501 L"test.html" | |
1502 }, | |
1503 { | |
1504 __LINE__, | |
1505 "http://www.google.com/.test", | |
1506 "", | |
1507 "", | |
1508 "", | |
1509 "", | |
1510 L"", | |
1511 L"test" | |
1512 }, | |
1513 { | |
1514 __LINE__, | |
1515 "http://www.google.com/..test", | |
1516 "", | |
1517 "", | |
1518 "", | |
1519 "", | |
1520 L"", | |
1521 L"test" | |
1522 }, | |
1523 { // Disposition has relative paths, remove directory separators | |
1524 __LINE__, | |
1525 "http://www.evil.com/my_download.txt", | |
1526 "filename=../../../../././../a_file_name.txt", | |
1527 "", | |
1528 "", | |
1529 "text/plain", | |
1530 L"download", | |
1531 L"-..-..-..-.-.-..-a_file_name.txt" | |
1532 }, | |
1533 { // Disposition has parent directories, remove directory separators | |
1534 __LINE__, | |
1535 "http://www.evil.com/my_download.txt", | |
1536 "filename=dir1/dir2/a_file_name.txt", | |
1537 "", | |
1538 "", | |
1539 "text/plain", | |
1540 L"download", | |
1541 L"dir1-dir2-a_file_name.txt" | |
1542 }, | |
1543 { // Disposition has relative paths, remove directory separators | |
1544 __LINE__, | |
1545 "http://www.evil.com/my_download.txt", | |
1546 "filename=..\\..\\..\\..\\.\\.\\..\\a_file_name.txt", | |
1547 "", | |
1548 "", | |
1549 "text/plain", | |
1550 L"download", | |
1551 L"-..-..-..-.-.-..-a_file_name.txt" | |
1552 }, | |
1553 { // Disposition has parent directories, remove directory separators | |
1554 __LINE__, | |
1555 "http://www.evil.com/my_download.txt", | |
1556 "filename=dir1\\dir2\\a_file_name.txt", | |
1557 "", | |
1558 "", | |
1559 "text/plain", | |
1560 L"download", | |
1561 L"dir1-dir2-a_file_name.txt" | |
1562 }, | |
1563 { // No useful information in disposition or URL, use default | |
1564 __LINE__, | |
1565 "http://www.truncated.com/path/", | |
1566 "", | |
1567 "", | |
1568 "", | |
1569 "text/plain", | |
1570 L"download", | |
1571 L"download" TXT_EXT | |
1572 }, | |
1573 { // Filename looks like HTML? | |
1574 __LINE__, | |
1575 "http://www.evil.com/get/malware/here", | |
1576 "filename=\"<blink>Hello kitty</blink>\"", | |
1577 "", | |
1578 "", | |
1579 "text/plain", | |
1580 L"default", | |
1581 L"-blink-Hello kitty--blink-" TXT_EXT | |
1582 }, | |
1583 { // A normal avi should get .avi and not .avi.avi | |
1584 __LINE__, | |
1585 "https://blah.google.com/misc/2.avi", | |
1586 "", | |
1587 "", | |
1588 "", | |
1589 "video/x-msvideo", | |
1590 L"download", | |
1591 L"2.avi" | |
1592 }, | |
1593 { // Extension generation | |
1594 __LINE__, | |
1595 "http://www.example.com/my-cat", | |
1596 "filename=my-cat", | |
1597 "", | |
1598 "", | |
1599 "image/jpeg", | |
1600 L"download", | |
1601 L"my-cat" JPEG_EXT | |
1602 }, | |
1603 { | |
1604 __LINE__, | |
1605 "http://www.example.com/my-cat", | |
1606 "filename=my-cat", | |
1607 "", | |
1608 "", | |
1609 "text/plain", | |
1610 L"download", | |
1611 L"my-cat.txt" | |
1612 }, | |
1613 { | |
1614 __LINE__, | |
1615 "http://www.example.com/my-cat", | |
1616 "filename=my-cat", | |
1617 "", | |
1618 "", | |
1619 "text/html", | |
1620 L"download", | |
1621 L"my-cat" HTML_EXT | |
1622 }, | |
1623 { // Unknown MIME type | |
1624 __LINE__, | |
1625 "http://www.example.com/my-cat", | |
1626 "filename=my-cat", | |
1627 "", | |
1628 "", | |
1629 "dance/party", | |
1630 L"download", | |
1631 L"my-cat" | |
1632 }, | |
1633 { | |
1634 __LINE__, | |
1635 "http://www.example.com/my-cat.jpg", | |
1636 "filename=my-cat.jpg", | |
1637 "", | |
1638 "", | |
1639 "text/plain", | |
1640 L"download", | |
1641 L"my-cat.jpg" | |
1642 }, | |
1643 // Windows specific tests | |
1644 #if defined(OS_WIN) | |
1645 { | |
1646 __LINE__, | |
1647 "http://www.goodguy.com/evil.exe", | |
1648 "filename=evil.exe", | |
1649 "", | |
1650 "", | |
1651 "image/jpeg", | |
1652 L"download", | |
1653 L"evil.exe" | |
1654 }, | |
1655 { | |
1656 __LINE__, | |
1657 "http://www.goodguy.com/ok.exe", | |
1658 "filename=ok.exe", | |
1659 "", | |
1660 "", | |
1661 "binary/octet-stream", | |
1662 L"download", | |
1663 L"ok.exe" | |
1664 }, | |
1665 { | |
1666 __LINE__, | |
1667 "http://www.goodguy.com/evil.dll", | |
1668 "filename=evil.dll", | |
1669 "", | |
1670 "", | |
1671 "dance/party", | |
1672 L"download", | |
1673 L"evil.dll" | |
1674 }, | |
1675 { | |
1676 __LINE__, | |
1677 "http://www.goodguy.com/evil.exe", | |
1678 "filename=evil", | |
1679 "", | |
1680 "", | |
1681 "application/rss+xml", | |
1682 L"download", | |
1683 L"evil" | |
1684 }, | |
1685 // Test truncation of trailing dots and spaces | |
1686 { | |
1687 __LINE__, | |
1688 "http://www.goodguy.com/evil.exe ", | |
1689 "filename=evil.exe ", | |
1690 "", | |
1691 "", | |
1692 "binary/octet-stream", | |
1693 L"download", | |
1694 L"evil.exe" | |
1695 }, | |
1696 { | |
1697 __LINE__, | |
1698 "http://www.goodguy.com/evil.exe.", | |
1699 "filename=evil.exe.", | |
1700 "", | |
1701 "", | |
1702 "binary/octet-stream", | |
1703 L"download", | |
1704 L"evil.exe-" | |
1705 }, | |
1706 { | |
1707 __LINE__, | |
1708 "http://www.goodguy.com/evil.exe. . .", | |
1709 "filename=evil.exe. . .", | |
1710 "", | |
1711 "", | |
1712 "binary/octet-stream", | |
1713 L"download", | |
1714 L"evil.exe-------" | |
1715 }, | |
1716 { | |
1717 __LINE__, | |
1718 "http://www.goodguy.com/evil.", | |
1719 "filename=evil.", | |
1720 "", | |
1721 "", | |
1722 "binary/octet-stream", | |
1723 L"download", | |
1724 L"evil-" | |
1725 }, | |
1726 { | |
1727 __LINE__, | |
1728 "http://www.goodguy.com/. . . . .", | |
1729 "filename=. . . . .", | |
1730 "", | |
1731 "", | |
1732 "binary/octet-stream", | |
1733 L"download", | |
1734 L"download" | |
1735 }, | |
1736 { | |
1737 __LINE__, | |
1738 "http://www.badguy.com/attachment?name=meh.exe%C2%A0", | |
1739 "attachment; filename=\"meh.exe\xC2\xA0\"", | |
1740 "", | |
1741 "", | |
1742 "binary/octet-stream", | |
1743 L"", | |
1744 L"meh.exe-" | |
1745 }, | |
1746 #endif // OS_WIN | |
1747 { | |
1748 __LINE__, | |
1749 "http://www.goodguy.com/utils.js", | |
1750 "filename=utils.js", | |
1751 "", | |
1752 "", | |
1753 "application/x-javascript", | |
1754 L"download", | |
1755 L"utils.js" | |
1756 }, | |
1757 { | |
1758 __LINE__, | |
1759 "http://www.goodguy.com/contacts.js", | |
1760 "filename=contacts.js", | |
1761 "", | |
1762 "", | |
1763 "application/json", | |
1764 L"download", | |
1765 L"contacts.js" | |
1766 }, | |
1767 { | |
1768 __LINE__, | |
1769 "http://www.goodguy.com/utils.js", | |
1770 "filename=utils.js", | |
1771 "", | |
1772 "", | |
1773 "text/javascript", | |
1774 L"download", | |
1775 L"utils.js" | |
1776 }, | |
1777 { | |
1778 __LINE__, | |
1779 "http://www.goodguy.com/utils.js", | |
1780 "filename=utils.js", | |
1781 "", | |
1782 "", | |
1783 "text/javascript;version=2", | |
1784 L"download", | |
1785 L"utils.js" | |
1786 }, | |
1787 { | |
1788 __LINE__, | |
1789 "http://www.goodguy.com/utils.js", | |
1790 "filename=utils.js", | |
1791 "", | |
1792 "", | |
1793 "application/ecmascript", | |
1794 L"download", | |
1795 L"utils.js" | |
1796 }, | |
1797 { | |
1798 __LINE__, | |
1799 "http://www.goodguy.com/utils.js", | |
1800 "filename=utils.js", | |
1801 "", | |
1802 "", | |
1803 "application/ecmascript;version=4", | |
1804 L"download", | |
1805 L"utils.js" | |
1806 }, | |
1807 { | |
1808 __LINE__, | |
1809 "http://www.goodguy.com/program.exe", | |
1810 "filename=program.exe", | |
1811 "", | |
1812 "", | |
1813 "application/foo-bar", | |
1814 L"download", | |
1815 L"program.exe" | |
1816 }, | |
1817 { | |
1818 __LINE__, | |
1819 "http://www.evil.com/../foo.txt", | |
1820 "filename=../foo.txt", | |
1821 "", | |
1822 "", | |
1823 "text/plain", | |
1824 L"download", | |
1825 L"-foo.txt" | |
1826 }, | |
1827 { | |
1828 __LINE__, | |
1829 "http://www.evil.com/..\\foo.txt", | |
1830 "filename=..\\foo.txt", | |
1831 "", | |
1832 "", | |
1833 "text/plain", | |
1834 L"download", | |
1835 L"-foo.txt" | |
1836 }, | |
1837 { | |
1838 __LINE__, | |
1839 "http://www.evil.com/.hidden", | |
1840 "filename=.hidden", | |
1841 "", | |
1842 "", | |
1843 "text/plain", | |
1844 L"download", | |
1845 L"hidden" TXT_EXT | |
1846 }, | |
1847 { | |
1848 __LINE__, | |
1849 "http://www.evil.com/trailing.", | |
1850 "filename=trailing.", | |
1851 "", | |
1852 "", | |
1853 "dance/party", | |
1854 L"download", | |
1855 #if defined(OS_WIN) | |
1856 L"trailing-" | |
1857 #else | |
1858 L"trailing" | |
1859 #endif | |
1860 }, | |
1861 { | |
1862 __LINE__, | |
1863 "http://www.evil.com/trailing.", | |
1864 "filename=trailing.", | |
1865 "", | |
1866 "", | |
1867 "text/plain", | |
1868 L"download", | |
1869 #if defined(OS_WIN) | |
1870 L"trailing-" TXT_EXT | |
1871 #else | |
1872 L"trailing" TXT_EXT | |
1873 #endif | |
1874 }, | |
1875 { | |
1876 __LINE__, | |
1877 "http://www.evil.com/.", | |
1878 "filename=.", | |
1879 "", | |
1880 "", | |
1881 "dance/party", | |
1882 L"download", | |
1883 L"download" | |
1884 }, | |
1885 { | |
1886 __LINE__, | |
1887 "http://www.evil.com/..", | |
1888 "filename=..", | |
1889 "", | |
1890 "", | |
1891 "dance/party", | |
1892 L"download", | |
1893 L"download" | |
1894 }, | |
1895 { | |
1896 __LINE__, | |
1897 "http://www.evil.com/...", | |
1898 "filename=...", | |
1899 "", | |
1900 "", | |
1901 "dance/party", | |
1902 L"download", | |
1903 L"download" | |
1904 }, | |
1905 { // Note that this one doesn't have "filename=" on it. | |
1906 __LINE__, | |
1907 "http://www.evil.com/", | |
1908 "a_file_name.txt", | |
1909 "", | |
1910 "", | |
1911 "image/jpeg", | |
1912 L"download", | |
1913 L"download" JPEG_EXT | |
1914 }, | |
1915 { | |
1916 __LINE__, | |
1917 "http://www.evil.com/", | |
1918 "filename=", | |
1919 "", | |
1920 "", | |
1921 "image/jpeg", | |
1922 L"download", | |
1923 L"download" JPEG_EXT | |
1924 }, | |
1925 { | |
1926 __LINE__, | |
1927 "http://www.example.com/simple", | |
1928 "filename=simple", | |
1929 "", | |
1930 "", | |
1931 "application/octet-stream", | |
1932 L"download", | |
1933 L"simple" | |
1934 }, | |
1935 // Reserved words on Windows | |
1936 { | |
1937 __LINE__, | |
1938 "http://www.goodguy.com/COM1", | |
1939 "filename=COM1", | |
1940 "", | |
1941 "", | |
1942 "application/foo-bar", | |
1943 L"download", | |
1944 #if defined(OS_WIN) | |
1945 L"_COM1" | |
1946 #else | |
1947 L"COM1" | |
1948 #endif | |
1949 }, | |
1950 { | |
1951 __LINE__, | |
1952 "http://www.goodguy.com/COM4.txt", | |
1953 "filename=COM4.txt", | |
1954 "", | |
1955 "", | |
1956 "text/plain", | |
1957 L"download", | |
1958 #if defined(OS_WIN) | |
1959 L"_COM4.txt" | |
1960 #else | |
1961 L"COM4.txt" | |
1962 #endif | |
1963 }, | |
1964 { | |
1965 __LINE__, | |
1966 "http://www.goodguy.com/lpt1.TXT", | |
1967 "filename=lpt1.TXT", | |
1968 "", | |
1969 "", | |
1970 "text/plain", | |
1971 L"download", | |
1972 #if defined(OS_WIN) | |
1973 L"_lpt1.TXT" | |
1974 #else | |
1975 L"lpt1.TXT" | |
1976 #endif | |
1977 }, | |
1978 { | |
1979 __LINE__, | |
1980 "http://www.goodguy.com/clock$.txt", | |
1981 "filename=clock$.txt", | |
1982 "", | |
1983 "", | |
1984 "text/plain", | |
1985 L"download", | |
1986 #if defined(OS_WIN) | |
1987 L"_clock$.txt" | |
1988 #else | |
1989 L"clock$.txt" | |
1990 #endif | |
1991 }, | |
1992 { // Validation should also apply to sugested name | |
1993 __LINE__, | |
1994 "http://www.goodguy.com/blah$.txt", | |
1995 "filename=clock$.txt", | |
1996 "", | |
1997 "clock$.txt", | |
1998 "text/plain", | |
1999 L"download", | |
2000 #if defined(OS_WIN) | |
2001 L"_clock$.txt" | |
2002 #else | |
2003 L"clock$.txt" | |
2004 #endif | |
2005 }, | |
2006 { | |
2007 __LINE__, | |
2008 "http://www.goodguy.com/mycom1.foo", | |
2009 "filename=mycom1.foo", | |
2010 "", | |
2011 "", | |
2012 "text/plain", | |
2013 L"download", | |
2014 L"mycom1.foo" | |
2015 }, | |
2016 { | |
2017 __LINE__, | |
2018 "http://www.badguy.com/Setup.exe.local", | |
2019 "filename=Setup.exe.local", | |
2020 "", | |
2021 "", | |
2022 "application/foo-bar", | |
2023 L"download", | |
2024 #if defined(OS_WIN) | |
2025 L"Setup.exe.download" | |
2026 #else | |
2027 L"Setup.exe.local" | |
2028 #endif | |
2029 }, | |
2030 { | |
2031 __LINE__, | |
2032 "http://www.badguy.com/Setup.exe.local", | |
2033 "filename=Setup.exe.local.local", | |
2034 "", | |
2035 "", | |
2036 "application/foo-bar", | |
2037 L"download", | |
2038 #if defined(OS_WIN) | |
2039 L"Setup.exe.local.download" | |
2040 #else | |
2041 L"Setup.exe.local.local" | |
2042 #endif | |
2043 }, | |
2044 { | |
2045 __LINE__, | |
2046 "http://www.badguy.com/Setup.exe.lnk", | |
2047 "filename=Setup.exe.lnk", | |
2048 "", | |
2049 "", | |
2050 "application/foo-bar", | |
2051 L"download", | |
2052 #if defined(OS_WIN) | |
2053 L"Setup.exe.download" | |
2054 #else | |
2055 L"Setup.exe.lnk" | |
2056 #endif | |
2057 }, | |
2058 { | |
2059 __LINE__, | |
2060 "http://www.badguy.com/Desktop.ini", | |
2061 "filename=Desktop.ini", | |
2062 "", | |
2063 "", | |
2064 "application/foo-bar", | |
2065 L"download", | |
2066 #if defined(OS_WIN) | |
2067 L"_Desktop.ini" | |
2068 #else | |
2069 L"Desktop.ini" | |
2070 #endif | |
2071 }, | |
2072 { | |
2073 __LINE__, | |
2074 "http://www.badguy.com/Thumbs.db", | |
2075 "filename=Thumbs.db", | |
2076 "", | |
2077 "", | |
2078 "application/foo-bar", | |
2079 L"download", | |
2080 #if defined(OS_WIN) | |
2081 L"_Thumbs.db" | |
2082 #else | |
2083 L"Thumbs.db" | |
2084 #endif | |
2085 }, | |
2086 { | |
2087 __LINE__, | |
2088 "http://www.hotmail.com", | |
2089 "filename=source.jpg", | |
2090 "", | |
2091 "", | |
2092 "application/x-javascript", | |
2093 L"download", | |
2094 L"source.jpg" | |
2095 }, | |
2096 { // http://crbug.com/5772. | |
2097 __LINE__, | |
2098 "http://www.example.com/foo.tar.gz", | |
2099 "", | |
2100 "", | |
2101 "", | |
2102 "application/x-tar", | |
2103 L"download", | |
2104 L"foo.tar.gz" | |
2105 }, | |
2106 { // http://crbug.com/52250. | |
2107 __LINE__, | |
2108 "http://www.example.com/foo.tgz", | |
2109 "", | |
2110 "", | |
2111 "", | |
2112 "application/x-tar", | |
2113 L"download", | |
2114 L"foo.tgz" | |
2115 }, | |
2116 { // http://crbug.com/7337. | |
2117 __LINE__, | |
2118 "http://maged.lordaeron.org/blank.reg", | |
2119 "", | |
2120 "", | |
2121 "", | |
2122 "text/x-registry", | |
2123 L"download", | |
2124 L"blank.reg" | |
2125 }, | |
2126 { | |
2127 __LINE__, | |
2128 "http://www.example.com/bar.tar", | |
2129 "", | |
2130 "", | |
2131 "", | |
2132 "application/x-tar", | |
2133 L"download", | |
2134 L"bar.tar" | |
2135 }, | |
2136 { | |
2137 __LINE__, | |
2138 "http://www.example.com/bar.bogus", | |
2139 "", | |
2140 "", | |
2141 "", | |
2142 "application/x-tar", | |
2143 L"download", | |
2144 L"bar.bogus" | |
2145 }, | |
2146 { // http://crbug.com/20337 | |
2147 __LINE__, | |
2148 "http://www.example.com/.download.txt", | |
2149 "filename=.download.txt", | |
2150 "", | |
2151 "", | |
2152 "text/plain", | |
2153 L"-download", | |
2154 L"download.txt" | |
2155 }, | |
2156 { // http://crbug.com/56855. | |
2157 __LINE__, | |
2158 "http://www.example.com/bar.sh", | |
2159 "", | |
2160 "", | |
2161 "", | |
2162 "application/x-sh", | |
2163 L"download", | |
2164 L"bar.sh" | |
2165 }, | |
2166 { // http://crbug.com/61571 | |
2167 __LINE__, | |
2168 "http://www.example.com/npdf.php?fn=foobar.pdf", | |
2169 "", | |
2170 "", | |
2171 "", | |
2172 "text/plain", | |
2173 L"download", | |
2174 L"npdf" TXT_EXT | |
2175 }, | |
2176 { // Shouldn't overwrite C-D specified extension. | |
2177 __LINE__, | |
2178 "http://www.example.com/npdf.php?fn=foobar.pdf", | |
2179 "filename=foobar.jpg", | |
2180 "", | |
2181 "", | |
2182 "text/plain", | |
2183 L"download", | |
2184 L"foobar.jpg" | |
2185 }, | |
2186 { // http://crbug.com/87719 | |
2187 __LINE__, | |
2188 "http://www.example.com/image.aspx?id=blargh", | |
2189 "", | |
2190 "", | |
2191 "", | |
2192 "image/jpeg", | |
2193 L"download", | |
2194 L"image" JPEG_EXT | |
2195 }, | |
2196 #if defined(OS_CHROMEOS) | |
2197 { // http://crosbug.com/26028 | |
2198 __LINE__, | |
2199 "http://www.example.com/fooa%cc%88.txt", | |
2200 "", | |
2201 "", | |
2202 "", | |
2203 "image/jpeg", | |
2204 L"foo\xe4", | |
2205 L"foo\xe4.txt" | |
2206 }, | |
2207 #endif | |
2208 }; | |
2209 | |
2210 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(selection_tests); ++i) | |
2211 RunGenerateFileNameTestCase(&selection_tests[i]); | |
2212 | |
2213 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(generation_tests); ++i) | |
2214 RunGenerateFileNameTestCase(&generation_tests[i]); | |
2215 | |
2216 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(generation_tests); ++i) { | |
2217 GenerateFilenameCase test_case = generation_tests[i]; | |
2218 test_case.referrer_charset = "GBK"; | |
2219 RunGenerateFileNameTestCase(&test_case); | |
2220 } | |
2221 } | |
2222 | |
2223 // This is currently a windows specific function. | 667 // This is currently a windows specific function. |
2224 #if defined(OS_WIN) | 668 #if defined(OS_WIN) |
2225 namespace { | 669 namespace { |
2226 | 670 |
2227 struct GetDirectoryListingEntryCase { | 671 struct GetDirectoryListingEntryCase { |
2228 const wchar_t* name; | 672 const wchar_t* name; |
2229 const char* raw_bytes; | 673 const char* raw_bytes; |
2230 bool is_dir; | 674 bool is_dir; |
2231 int64 filesize; | 675 int64 filesize; |
2232 base::Time time; | 676 base::Time time; |
(...skipping 1128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3361 EXPECT_NE(it->interface_index, 0u); // 0 means to use default. | 1805 EXPECT_NE(it->interface_index, 0u); // 0 means to use default. |
3362 } | 1806 } |
3363 #elif !defined(OS_ANDROID) | 1807 #elif !defined(OS_ANDROID) |
3364 char name[IF_NAMESIZE]; | 1808 char name[IF_NAMESIZE]; |
3365 EXPECT_TRUE(if_indextoname(it->interface_index, name)); | 1809 EXPECT_TRUE(if_indextoname(it->interface_index, name)); |
3366 EXPECT_STREQ(it->name.c_str(), name); | 1810 EXPECT_STREQ(it->name.c_str(), name); |
3367 #endif | 1811 #endif |
3368 } | 1812 } |
3369 } | 1813 } |
3370 | 1814 |
3371 static const base::FilePath::CharType* kSafePortableBasenames[] = { | |
3372 FILE_PATH_LITERAL("a"), | |
3373 FILE_PATH_LITERAL("a.txt"), | |
3374 FILE_PATH_LITERAL("a b.txt"), | |
3375 FILE_PATH_LITERAL("a-b.txt"), | |
3376 FILE_PATH_LITERAL("My Computer"), | |
3377 FILE_PATH_LITERAL(" Computer"), | |
3378 }; | |
3379 | |
3380 static const base::FilePath::CharType* kUnsafePortableBasenames[] = { | |
3381 FILE_PATH_LITERAL(""), | |
3382 FILE_PATH_LITERAL("."), | |
3383 FILE_PATH_LITERAL(".."), | |
3384 FILE_PATH_LITERAL("..."), | |
3385 FILE_PATH_LITERAL("con"), | |
3386 FILE_PATH_LITERAL("con.zip"), | |
3387 FILE_PATH_LITERAL("NUL"), | |
3388 FILE_PATH_LITERAL("NUL.zip"), | |
3389 FILE_PATH_LITERAL(".a"), | |
3390 FILE_PATH_LITERAL("a."), | |
3391 FILE_PATH_LITERAL("a\"a"), | |
3392 FILE_PATH_LITERAL("a<a"), | |
3393 FILE_PATH_LITERAL("a>a"), | |
3394 FILE_PATH_LITERAL("a?a"), | |
3395 FILE_PATH_LITERAL("a/"), | |
3396 FILE_PATH_LITERAL("a\\"), | |
3397 FILE_PATH_LITERAL("a "), | |
3398 FILE_PATH_LITERAL("a . ."), | |
3399 FILE_PATH_LITERAL("My Computer.{a}"), | |
3400 FILE_PATH_LITERAL("My Computer.{20D04FE0-3AEA-1069-A2D8-08002B30309D}"), | |
3401 #if !defined(OS_WIN) | |
3402 FILE_PATH_LITERAL("a\\a"), | |
3403 #endif | |
3404 }; | |
3405 | |
3406 static const base::FilePath::CharType* kSafePortableRelativePaths[] = { | |
3407 FILE_PATH_LITERAL("a/a"), | |
3408 #if defined(OS_WIN) | |
3409 FILE_PATH_LITERAL("a\\a"), | |
3410 #endif | |
3411 }; | |
3412 | |
3413 TEST(NetUtilTest, IsSafePortablePathComponent) { | |
3414 for (size_t i = 0 ; i < arraysize(kSafePortableBasenames); ++i) { | |
3415 EXPECT_TRUE(IsSafePortablePathComponent(base::FilePath( | |
3416 kSafePortableBasenames[i]))) << kSafePortableBasenames[i]; | |
3417 } | |
3418 for (size_t i = 0 ; i < arraysize(kUnsafePortableBasenames); ++i) { | |
3419 EXPECT_FALSE(IsSafePortablePathComponent(base::FilePath( | |
3420 kUnsafePortableBasenames[i]))) << kUnsafePortableBasenames[i]; | |
3421 } | |
3422 for (size_t i = 0 ; i < arraysize(kSafePortableRelativePaths); ++i) { | |
3423 EXPECT_FALSE(IsSafePortablePathComponent(base::FilePath( | |
3424 kSafePortableRelativePaths[i]))) << kSafePortableRelativePaths[i]; | |
3425 } | |
3426 } | |
3427 | |
3428 TEST(NetUtilTest, IsSafePortableRelativePath) { | |
3429 base::FilePath safe_dirname(FILE_PATH_LITERAL("a")); | |
3430 for (size_t i = 0 ; i < arraysize(kSafePortableBasenames); ++i) { | |
3431 EXPECT_TRUE(IsSafePortableRelativePath(base::FilePath( | |
3432 kSafePortableBasenames[i]))) << kSafePortableBasenames[i]; | |
3433 EXPECT_TRUE(IsSafePortableRelativePath(safe_dirname.Append(base::FilePath( | |
3434 kSafePortableBasenames[i])))) << kSafePortableBasenames[i]; | |
3435 } | |
3436 for (size_t i = 0 ; i < arraysize(kSafePortableRelativePaths); ++i) { | |
3437 EXPECT_TRUE(IsSafePortableRelativePath(base::FilePath( | |
3438 kSafePortableRelativePaths[i]))) << kSafePortableRelativePaths[i]; | |
3439 EXPECT_TRUE(IsSafePortableRelativePath(safe_dirname.Append(base::FilePath( | |
3440 kSafePortableRelativePaths[i])))) << kSafePortableRelativePaths[i]; | |
3441 } | |
3442 for (size_t i = 0 ; i < arraysize(kUnsafePortableBasenames); ++i) { | |
3443 EXPECT_FALSE(IsSafePortableRelativePath(base::FilePath( | |
3444 kUnsafePortableBasenames[i]))) << kUnsafePortableBasenames[i]; | |
3445 if (!base::FilePath::StringType(kUnsafePortableBasenames[i]).empty()) { | |
3446 EXPECT_FALSE(IsSafePortableRelativePath(safe_dirname.Append( | |
3447 base::FilePath(kUnsafePortableBasenames[i])))) | |
3448 << kUnsafePortableBasenames[i]; | |
3449 } | |
3450 } | |
3451 } | |
3452 | |
3453 struct NonUniqueNameTestData { | 1815 struct NonUniqueNameTestData { |
3454 bool is_unique; | 1816 bool is_unique; |
3455 const char* hostname; | 1817 const char* hostname; |
3456 }; | 1818 }; |
3457 | 1819 |
3458 // Google Test pretty-printer. | 1820 // Google Test pretty-printer. |
3459 void PrintTo(const NonUniqueNameTestData& data, std::ostream* os) { | 1821 void PrintTo(const NonUniqueNameTestData& data, std::ostream* os) { |
3460 ASSERT_TRUE(data.hostname); | 1822 ASSERT_TRUE(data.hostname); |
3461 *os << " hostname: " << testing::PrintToString(data.hostname) | 1823 *os << " hostname: " << testing::PrintToString(data.hostname) |
3462 << "; is_unique: " << testing::PrintToString(data.is_unique); | 1824 << "; is_unique: " << testing::PrintToString(data.is_unique); |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3524 TEST_P(NetUtilNonUniqueNameTest, IsHostnameNonUnique) { | 1886 TEST_P(NetUtilNonUniqueNameTest, IsHostnameNonUnique) { |
3525 const NonUniqueNameTestData& test_data = GetParam(); | 1887 const NonUniqueNameTestData& test_data = GetParam(); |
3526 | 1888 |
3527 EXPECT_EQ(test_data.is_unique, IsUnique(test_data.hostname)); | 1889 EXPECT_EQ(test_data.is_unique, IsUnique(test_data.hostname)); |
3528 } | 1890 } |
3529 | 1891 |
3530 INSTANTIATE_TEST_CASE_P(, NetUtilNonUniqueNameTest, | 1892 INSTANTIATE_TEST_CASE_P(, NetUtilNonUniqueNameTest, |
3531 testing::ValuesIn(kNonUniqueNameTestData)); | 1893 testing::ValuesIn(kNonUniqueNameTestData)); |
3532 | 1894 |
3533 } // namespace net | 1895 } // namespace net |
OLD | NEW |