OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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/ftp/ftp_directory_listing_parser.h" | 5 #include "net/ftp/ftp_directory_listing_parser.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/callback.h" | 8 #include "base/callback.h" |
9 #include "base/i18n/icu_encoding_detection.h" | 9 #include "base/i18n/icu_encoding_detection.h" |
10 #include "base/i18n/icu_string_conversions.h" | 10 #include "base/i18n/icu_string_conversions.h" |
11 #include "base/stl_util.h" | 11 #include "base/stl_util.h" |
12 #include "base/string_split.h" | 12 #include "base/string_split.h" |
13 #include "base/string_util.h" | 13 #include "base/string_util.h" |
| 14 #include "base/utf_string_conversions.h" |
14 #include "net/base/net_errors.h" | 15 #include "net/base/net_errors.h" |
15 #include "net/ftp/ftp_directory_listing_parser_ls.h" | 16 #include "net/ftp/ftp_directory_listing_parser_ls.h" |
16 #include "net/ftp/ftp_directory_listing_parser_netware.h" | 17 #include "net/ftp/ftp_directory_listing_parser_netware.h" |
17 #include "net/ftp/ftp_directory_listing_parser_os2.h" | 18 #include "net/ftp/ftp_directory_listing_parser_os2.h" |
18 #include "net/ftp/ftp_directory_listing_parser_vms.h" | 19 #include "net/ftp/ftp_directory_listing_parser_vms.h" |
19 #include "net/ftp/ftp_directory_listing_parser_windows.h" | 20 #include "net/ftp/ftp_directory_listing_parser_windows.h" |
20 #include "net/ftp/ftp_server_type_histograms.h" | 21 #include "net/ftp/ftp_server_type_histograms.h" |
21 | 22 |
22 namespace net { | 23 namespace net { |
23 | 24 |
(...skipping 10 matching lines...) Expand all Loading... |
34 return ERR_ENCODING_CONVERSION_FAILED; | 35 return ERR_ENCODING_CONVERSION_FAILED; |
35 } | 36 } |
36 } | 37 } |
37 | 38 |
38 return OK; | 39 return OK; |
39 } | 40 } |
40 | 41 |
41 // Parses |text| as an FTP directory listing. Fills in |entries| | 42 // Parses |text| as an FTP directory listing. Fills in |entries| |
42 // and |server_type| and returns network error code. | 43 // and |server_type| and returns network error code. |
43 int ParseListing(const string16& text, | 44 int ParseListing(const string16& text, |
| 45 const string16& newline_separator, |
44 const std::string& encoding, | 46 const std::string& encoding, |
45 const base::Time& current_time, | 47 const base::Time& current_time, |
46 std::vector<FtpDirectoryListingEntry>* entries, | 48 std::vector<FtpDirectoryListingEntry>* entries, |
47 FtpServerType* server_type) { | 49 FtpServerType* server_type) { |
48 std::vector<string16> lines; | 50 std::vector<string16> lines; |
49 base::SplitString(text, '\n', &lines); | 51 base::SplitStringUsingSubstr(text, newline_separator, &lines); |
50 | 52 |
51 struct { | 53 struct { |
52 base::Callback<bool(void)> callback; | 54 base::Callback<bool(void)> callback; |
53 FtpServerType server_type; | 55 FtpServerType server_type; |
54 } parsers[] = { | 56 } parsers[] = { |
55 { | 57 { |
56 base::Bind(&ParseFtpDirectoryListingLs, lines, current_time, entries), | 58 base::Bind(&ParseFtpDirectoryListingLs, lines, current_time, entries), |
57 SERVER_LS | 59 SERVER_LS |
58 }, | 60 }, |
59 { | 61 { |
(...skipping 26 matching lines...) Expand all Loading... |
86 entries->clear(); | 88 entries->clear(); |
87 return ERR_UNRECOGNIZED_FTP_DIRECTORY_LISTING_FORMAT; | 89 return ERR_UNRECOGNIZED_FTP_DIRECTORY_LISTING_FORMAT; |
88 } | 90 } |
89 | 91 |
90 // Detects encoding of |text| and parses it as an FTP directory listing. | 92 // Detects encoding of |text| and parses it as an FTP directory listing. |
91 // Fills in |entries| and |server_type| and returns network error code. | 93 // Fills in |entries| and |server_type| and returns network error code. |
92 int DecodeAndParse(const std::string& text, | 94 int DecodeAndParse(const std::string& text, |
93 const base::Time& current_time, | 95 const base::Time& current_time, |
94 std::vector<FtpDirectoryListingEntry>* entries, | 96 std::vector<FtpDirectoryListingEntry>* entries, |
95 FtpServerType* server_type) { | 97 FtpServerType* server_type) { |
| 98 const char* kNewlineSeparators[] = { "\n", "\r\n" }; |
| 99 |
96 std::vector<std::string> encodings; | 100 std::vector<std::string> encodings; |
97 if (!base::DetectAllEncodings(text, &encodings)) | 101 if (!base::DetectAllEncodings(text, &encodings)) |
98 return ERR_ENCODING_DETECTION_FAILED; | 102 return ERR_ENCODING_DETECTION_FAILED; |
99 | 103 |
100 // Use first encoding that can be used to decode the text. | 104 // Use first encoding that can be used to decode the text. |
101 for (size_t i = 0; i < encodings.size(); i++) { | 105 for (size_t i = 0; i < encodings.size(); i++) { |
102 string16 converted_text; | 106 string16 converted_text; |
103 if (base::CodepageToUTF16(text, | 107 if (base::CodepageToUTF16(text, |
104 encodings[i].c_str(), | 108 encodings[i].c_str(), |
105 base::OnStringConversionError::FAIL, | 109 base::OnStringConversionError::FAIL, |
106 &converted_text)) { | 110 &converted_text)) { |
107 int rv = ParseListing(converted_text, | 111 for (size_t j = 0; j < arraysize(kNewlineSeparators); j++) { |
108 encodings[i], | 112 int rv = ParseListing(converted_text, |
109 current_time, | 113 ASCIIToUTF16(kNewlineSeparators[j]), |
110 entries, | 114 encodings[i], |
111 server_type); | 115 current_time, |
112 if (rv == OK) | 116 entries, |
113 return rv; | 117 server_type); |
| 118 if (rv == OK) |
| 119 return rv; |
| 120 } |
114 } | 121 } |
115 } | 122 } |
116 | 123 |
117 entries->clear(); | 124 entries->clear(); |
118 *server_type = SERVER_UNKNOWN; | 125 *server_type = SERVER_UNKNOWN; |
119 return ERR_UNRECOGNIZED_FTP_DIRECTORY_LISTING_FORMAT; | 126 return ERR_UNRECOGNIZED_FTP_DIRECTORY_LISTING_FORMAT; |
120 } | 127 } |
121 | 128 |
122 } // namespace | 129 } // namespace |
123 | 130 |
124 FtpDirectoryListingEntry::FtpDirectoryListingEntry() | 131 FtpDirectoryListingEntry::FtpDirectoryListingEntry() |
125 : type(UNKNOWN), | 132 : type(UNKNOWN), |
126 size(-1) { | 133 size(-1) { |
127 } | 134 } |
128 | 135 |
129 int ParseFtpDirectoryListing(const std::string& text, | 136 int ParseFtpDirectoryListing(const std::string& text, |
130 const base::Time& current_time, | 137 const base::Time& current_time, |
131 std::vector<FtpDirectoryListingEntry>* entries) { | 138 std::vector<FtpDirectoryListingEntry>* entries) { |
132 FtpServerType server_type = SERVER_UNKNOWN; | 139 FtpServerType server_type = SERVER_UNKNOWN; |
133 int rv = DecodeAndParse(text, current_time, entries, &server_type); | 140 int rv = DecodeAndParse(text, current_time, entries, &server_type); |
134 UpdateFtpServerTypeHistograms(server_type); | 141 UpdateFtpServerTypeHistograms(server_type); |
135 return rv; | 142 return rv; |
136 } | 143 } |
137 | 144 |
138 } // namespace net | 145 } // namespace net |
OLD | NEW |