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

Side by Side Diff: content/child/multipart_response_delegate.cc

Issue 1166953002: Use net's response header parser for parsing multipart headers. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Address more comments Created 5 years, 6 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 | net/http/http_util.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 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 "content/child/multipart_response_delegate.h" 5 #include "content/child/multipart_response_delegate.h"
6 6
7 #include "base/logging.h" 7 #include "base/logging.h"
8 #include "base/memory/ref_counted.h"
8 #include "base/strings/string_number_conversions.h" 9 #include "base/strings/string_number_conversions.h"
9 #include "base/strings/string_util.h" 10 #include "base/strings/string_util.h"
10 #include "net/base/net_util.h" 11 #include "net/base/net_util.h"
12 #include "net/http/http_response_headers.h"
11 #include "net/http/http_util.h" 13 #include "net/http/http_util.h"
12 #include "third_party/WebKit/public/platform/WebHTTPHeaderVisitor.h" 14 #include "third_party/WebKit/public/platform/WebHTTPHeaderVisitor.h"
13 #include "third_party/WebKit/public/platform/WebString.h" 15 #include "third_party/WebKit/public/platform/WebString.h"
14 #include "third_party/WebKit/public/platform/WebURL.h" 16 #include "third_party/WebKit/public/platform/WebURL.h"
15 #include "third_party/WebKit/public/platform/WebURLLoaderClient.h" 17 #include "third_party/WebKit/public/platform/WebURLLoaderClient.h"
16 18
17 using blink::WebHTTPHeaderVisitor; 19 using blink::WebHTTPHeaderVisitor;
18 using blink::WebString; 20 using blink::WebString;
19 using blink::WebURLLoader; 21 using blink::WebURLLoader;
20 using blink::WebURLLoaderClient; 22 using blink::WebURLLoaderClient;
(...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after
202 int offset = 0; 204 int offset = 0;
203 if (pos < data.length() && (data[pos] == '\r' || data[pos] == '\n')) { 205 if (pos < data.length() && (data[pos] == '\r' || data[pos] == '\n')) {
204 ++offset; 206 ++offset;
205 if (pos + 1 < data.length() && data[pos + 1] == '\n') 207 if (pos + 1 < data.length() && data[pos + 1] == '\n')
206 ++offset; 208 ++offset;
207 } 209 }
208 return offset; 210 return offset;
209 } 211 }
210 212
211 bool MultipartResponseDelegate::ParseHeaders() { 213 bool MultipartResponseDelegate::ParseHeaders() {
212 int line_feed_increment = 1; 214 int headers_end_pos = net::HttpUtil::LocateEndOfAdditionalHeaders(
215 data_.c_str(), data_.size(), 0);
213 216
214 // Grab the headers being liberal about line endings. 217 if (headers_end_pos < 0)
215 size_t line_start_pos = 0;
216 size_t line_end_pos = data_.find('\n');
217 while (line_end_pos != std::string::npos) {
218 // Handle CRLF
219 if (line_end_pos > line_start_pos && data_[line_end_pos - 1] == '\r') {
220 line_feed_increment = 2;
221 --line_end_pos;
222 } else {
223 line_feed_increment = 1;
224 }
225 if (line_start_pos == line_end_pos) {
226 // A blank line, end of headers
227 line_end_pos += line_feed_increment;
228 break;
229 }
230 // Find the next header line.
231 line_start_pos = line_end_pos + line_feed_increment;
232 line_end_pos = data_.find('\n', line_start_pos);
233 }
234 // Truncated in the middle of a header, stop parsing.
235 if (line_end_pos == std::string::npos)
236 return false; 218 return false;
237 219
238 // Eat headers 220 // Eat headers and prepend a status line as is required by
239 std::string headers("\n"); 221 // HttpResponseHeaders.
240 headers.append(data_, 0, line_end_pos); 222 std::string headers("HTTP/1.1 200 OK\r\n");
241 data_ = data_.substr(line_end_pos); 223 headers.append(data_, 0, headers_end_pos);
224 data_ = data_.substr(headers_end_pos);
225
226 scoped_refptr<net::HttpResponseHeaders> response_headers =
227 new net::HttpResponseHeaders(
228 net::HttpUtil::AssembleRawHeaders(headers.c_str(), headers.size()));
242 229
243 // Create a WebURLResponse based on the original set of headers + the 230 // Create a WebURLResponse based on the original set of headers + the
244 // replacement headers. We only replace the same few headers that gecko 231 // replacement headers. We only replace the same few headers that gecko
245 // does. See netwerk/streamconv/converters/nsMultiMixedConv.cpp. 232 // does. See netwerk/streamconv/converters/nsMultiMixedConv.cpp.
246 std::string content_type = net::GetSpecificHeader(headers, "content-type"); 233 WebURLResponse response(original_response_.url());
234
247 std::string mime_type; 235 std::string mime_type;
236 response_headers->GetMimeType(&mime_type);
237 response.setMIMEType(WebString::fromUTF8(mime_type));
238
248 std::string charset; 239 std::string charset;
249 bool has_charset = false; 240 response_headers->GetCharset(&charset);
250 net::HttpUtil::ParseContentType(content_type, &mime_type, &charset,
251 &has_charset, NULL);
252 WebURLResponse response(original_response_.url());
253 response.setMIMEType(WebString::fromUTF8(mime_type));
254 response.setTextEncodingName(WebString::fromUTF8(charset)); 241 response.setTextEncodingName(WebString::fromUTF8(charset));
255 242
243 // Copy the response headers from the original response.
256 HeaderCopier copier(&response); 244 HeaderCopier copier(&response);
257 original_response_.visitHTTPHeaderFields(&copier); 245 original_response_.visitHTTPHeaderFields(&copier);
258 246
247 // Replace original headers with multipart headers listed in kReplaceHeaders.
259 for (size_t i = 0; i < arraysize(kReplaceHeaders); ++i) { 248 for (size_t i = 0; i < arraysize(kReplaceHeaders); ++i) {
260 std::string name(kReplaceHeaders[i]); 249 std::string name(kReplaceHeaders[i]);
261 std::string value = net::GetSpecificHeader(headers, name); 250 std::string value;
262 if (!value.empty()) { 251 void* iterator = nullptr;
263 response.setHTTPHeaderField(WebString::fromUTF8(name), 252 while (response_headers->EnumerateHeader(&iterator, name, &value)) {
264 WebString::fromUTF8(value)); 253 response.addHTTPHeaderField(WebString::fromLatin1(name),
254 WebString::fromLatin1(value));
265 } 255 }
266 } 256 }
267 // To avoid recording every multipart load as a separate visit in 257 // To avoid recording every multipart load as a separate visit in
268 // the history database, we want to keep track of whether the response 258 // the history database, we want to keep track of whether the response
269 // is part of a multipart payload. We do want to record the first visit, 259 // is part of a multipart payload. We do want to record the first visit,
270 // so we only set isMultipartPayload to true after the first visit. 260 // so we only set isMultipartPayload to true after the first visit.
271 response.setIsMultipartPayload(has_sent_first_response_); 261 response.setIsMultipartPayload(has_sent_first_response_);
272 has_sent_first_response_ = true; 262 has_sent_first_response_ = true;
273 // Send the response! 263 // Send the response!
274 if (client_) 264 if (client_)
(...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after
395 if (!base::StringToInt64(byte_range_upper_bound, content_range_upper_bound)) 385 if (!base::StringToInt64(byte_range_upper_bound, content_range_upper_bound))
396 return false; 386 return false;
397 if (!base::StringToInt64(byte_range_instance_size, 387 if (!base::StringToInt64(byte_range_instance_size,
398 content_range_instance_size)) { 388 content_range_instance_size)) {
399 return false; 389 return false;
400 } 390 }
401 return true; 391 return true;
402 } 392 }
403 393
404 } // namespace content 394 } // namespace content
OLDNEW
« no previous file with comments | « no previous file | net/http/http_util.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698