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

Side by Side Diff: content/browser/loader/async_resource_handler.cc

Issue 2481093003: Introduce ResourceRequesterInfo to abstract the requester of resource request (Closed)
Patch Set: Created 4 years, 1 month 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
OLDNEW
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 "content/browser/loader/async_resource_handler.h" 5 #include "content/browser/loader/async_resource_handler.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <vector> 8 #include <vector>
9 9
10 #include "base/command_line.h" 10 #include "base/command_line.h"
11 #include "base/containers/hash_tables.h" 11 #include "base/containers/hash_tables.h"
12 #include "base/debug/alias.h" 12 #include "base/debug/alias.h"
13 #include "base/feature_list.h" 13 #include "base/feature_list.h"
14 #include "base/logging.h" 14 #include "base/logging.h"
15 #include "base/macros.h" 15 #include "base/macros.h"
16 #include "base/memory/shared_memory.h" 16 #include "base/memory/shared_memory.h"
17 #include "base/metrics/histogram_macros.h" 17 #include "base/metrics/histogram_macros.h"
18 #include "base/strings/string_number_conversions.h" 18 #include "base/strings/string_number_conversions.h"
19 #include "base/time/time.h" 19 #include "base/time/time.h"
20 #include "content/browser/loader/netlog_observer.h" 20 #include "content/browser/loader/netlog_observer.h"
21 #include "content/browser/loader/resource_buffer.h" 21 #include "content/browser/loader/resource_buffer.h"
22 #include "content/browser/loader/resource_dispatcher_host_impl.h" 22 #include "content/browser/loader/resource_dispatcher_host_impl.h"
23 #include "content/browser/loader/resource_message_filter.h" 23 #include "content/browser/loader/resource_message_filter.h"
yhirano 2016/11/10 06:42:29 Not needed.
horo 2016/11/10 14:46:33 Done.
24 #include "content/browser/loader/resource_request_info_impl.h" 24 #include "content/browser/loader/resource_request_info_impl.h"
25 #include "content/common/resource_messages.h" 25 #include "content/common/resource_messages.h"
26 #include "content/common/resource_request_completion_status.h" 26 #include "content/common/resource_request_completion_status.h"
27 #include "content/common/view_messages.h" 27 #include "content/common/view_messages.h"
28 #include "content/public/browser/resource_dispatcher_host_delegate.h" 28 #include "content/public/browser/resource_dispatcher_host_delegate.h"
29 #include "content/public/common/content_features.h" 29 #include "content/public/common/content_features.h"
30 #include "content/public/common/resource_response.h" 30 #include "content/public/common/resource_response.h"
31 #include "ipc/ipc_message_macros.h" 31 #include "ipc/ipc_message_macros.h"
32 #include "net/base/io_buffer.h" 32 #include "net/base/io_buffer.h"
33 #include "net/base/load_flags.h" 33 #include "net/base/load_flags.h"
(...skipping 174 matching lines...) Expand 10 before | Expand all | Expand 10 after
208 pending_data_count_(0), 208 pending_data_count_(0),
209 allocation_size_(0), 209 allocation_size_(0),
210 did_defer_(false), 210 did_defer_(false),
211 has_checked_for_sufficient_resources_(false), 211 has_checked_for_sufficient_resources_(false),
212 sent_received_response_msg_(false), 212 sent_received_response_msg_(false),
213 sent_data_buffer_msg_(false), 213 sent_data_buffer_msg_(false),
214 inlining_helper_(new InliningHelper), 214 inlining_helper_(new InliningHelper),
215 last_upload_position_(0), 215 last_upload_position_(0),
216 waiting_for_upload_progress_ack_(false), 216 waiting_for_upload_progress_ack_(false),
217 reported_transfer_size_(0), 217 reported_transfer_size_(0),
218 reported_encoded_body_length_(0) { 218 reported_encoded_body_length_(0) {
yhirano 2016/11/10 06:42:29 Adding DCHECK(GetRequestInfo()->requester_info().I
horo 2016/11/10 14:46:33 Done.
219 InitializeResourceBufferConstants(); 219 InitializeResourceBufferConstants();
220 } 220 }
221 221
222 AsyncResourceHandler::~AsyncResourceHandler() { 222 AsyncResourceHandler::~AsyncResourceHandler() {
223 if (has_checked_for_sufficient_resources_) 223 if (has_checked_for_sufficient_resources_)
224 rdh_->FinishedWithResourcesForRequest(request()); 224 rdh_->FinishedWithResourcesForRequest(request());
225 } 225 }
226 226
227 bool AsyncResourceHandler::OnMessageReceived(const IPC::Message& message) { 227 bool AsyncResourceHandler::OnMessageReceived(const IPC::Message& message) {
228 bool handled = true; 228 bool handled = true;
(...skipping 24 matching lines...) Expand all
253 ResumeIfDeferred(); 253 ResumeIfDeferred();
254 } 254 }
255 } 255 }
256 256
257 void AsyncResourceHandler::OnUploadProgressACK(int request_id) { 257 void AsyncResourceHandler::OnUploadProgressACK(int request_id) {
258 waiting_for_upload_progress_ack_ = false; 258 waiting_for_upload_progress_ack_ = false;
259 } 259 }
260 260
261 void AsyncResourceHandler::ReportUploadProgress() { 261 void AsyncResourceHandler::ReportUploadProgress() {
262 DCHECK(GetRequestInfo()->is_upload_progress_enabled()); 262 DCHECK(GetRequestInfo()->is_upload_progress_enabled());
263 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
263 if (waiting_for_upload_progress_ack_) 264 if (waiting_for_upload_progress_ack_)
264 return; // Send one progress event at a time. 265 return; // Send one progress event at a time.
265 266
266 net::UploadProgress progress = request()->GetUploadProgress(); 267 net::UploadProgress progress = request()->GetUploadProgress();
267 if (!progress.size()) 268 if (!progress.size())
268 return; // Nothing to upload. 269 return; // Nothing to upload.
269 270
270 if (progress.position() == last_upload_position_) 271 if (progress.position() == last_upload_position_)
271 return; // No progress made since last time. 272 return; // No progress made since last time.
272 273
273 const uint64_t kHalfPercentIncrements = 200; 274 const uint64_t kHalfPercentIncrements = 200;
274 const TimeDelta kOneSecond = TimeDelta::FromMilliseconds(1000); 275 const TimeDelta kOneSecond = TimeDelta::FromMilliseconds(1000);
275 276
276 uint64_t amt_since_last = progress.position() - last_upload_position_; 277 uint64_t amt_since_last = progress.position() - last_upload_position_;
277 TimeDelta time_since_last = TimeTicks::Now() - last_upload_ticks_; 278 TimeDelta time_since_last = TimeTicks::Now() - last_upload_ticks_;
278 279
279 bool is_finished = (progress.size() == progress.position()); 280 bool is_finished = (progress.size() == progress.position());
280 bool enough_new_progress = 281 bool enough_new_progress =
281 (amt_since_last > (progress.size() / kHalfPercentIncrements)); 282 (amt_since_last > (progress.size() / kHalfPercentIncrements));
282 bool too_much_time_passed = time_since_last > kOneSecond; 283 bool too_much_time_passed = time_since_last > kOneSecond;
283 284
284 if (is_finished || enough_new_progress || too_much_time_passed) { 285 if (is_finished || enough_new_progress || too_much_time_passed) {
285 ResourceMessageFilter* filter = GetFilter(); 286 BrowserMessageFilter* filter = GetFilter();
286 if (filter) { 287 if (filter) {
287 filter->Send( 288 filter->Send(
288 new ResourceMsg_UploadProgress(GetRequestID(), 289 new ResourceMsg_UploadProgress(GetRequestID(),
289 progress.position(), 290 progress.position(),
290 progress.size())); 291 progress.size()));
291 } 292 }
292 waiting_for_upload_progress_ack_ = true; 293 waiting_for_upload_progress_ack_ = true;
293 last_upload_ticks_ = TimeTicks::Now(); 294 last_upload_ticks_ = TimeTicks::Now();
294 last_upload_position_ = progress.position(); 295 last_upload_position_ = progress.position();
295 } 296 }
296 } 297 }
297 298
298 bool AsyncResourceHandler::OnRequestRedirected( 299 bool AsyncResourceHandler::OnRequestRedirected(
299 const net::RedirectInfo& redirect_info, 300 const net::RedirectInfo& redirect_info,
300 ResourceResponse* response, 301 ResourceResponse* response,
301 bool* defer) { 302 bool* defer) {
302 const ResourceRequestInfoImpl* info = GetRequestInfo(); 303 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
303 if (!info->filter()) 304 BrowserMessageFilter* filter = GetFilter();
305 if (!filter)
304 return false; 306 return false;
305 307
306 *defer = did_defer_ = true; 308 *defer = did_defer_ = true;
307 OnDefer(); 309 OnDefer();
308 310
309 NetLogObserver::PopulateResponseInfo(request(), response); 311 NetLogObserver::PopulateResponseInfo(request(), response);
310 response->head.encoded_data_length = request()->GetTotalReceivedBytes(); 312 response->head.encoded_data_length = request()->GetTotalReceivedBytes();
311 reported_transfer_size_ = 0; 313 reported_transfer_size_ = 0;
312 response->head.request_start = request()->creation_time(); 314 response->head.request_start = request()->creation_time();
313 response->head.response_start = TimeTicks::Now(); 315 response->head.response_start = TimeTicks::Now();
314 // TODO(davidben): Is it necessary to pass the new first party URL for 316 // TODO(davidben): Is it necessary to pass the new first party URL for
315 // cookies? The only case where it can change is top-level navigation requests 317 // cookies? The only case where it can change is top-level navigation requests
316 // and hopefully those will eventually all be owned by the browser. It's 318 // and hopefully those will eventually all be owned by the browser. It's
317 // possible this is still needed while renderer-owned ones exist. 319 // possible this is still needed while renderer-owned ones exist.
318 return info->filter()->Send(new ResourceMsg_ReceivedRedirect( 320 return filter->Send(new ResourceMsg_ReceivedRedirect(
319 GetRequestID(), redirect_info, response->head)); 321 GetRequestID(), redirect_info, response->head));
320 } 322 }
321 323
322 bool AsyncResourceHandler::OnResponseStarted(ResourceResponse* response, 324 bool AsyncResourceHandler::OnResponseStarted(ResourceResponse* response,
323 bool* defer) { 325 bool* defer) {
326 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
324 // For changes to the main frame, inform the renderer of the new URL's 327 // For changes to the main frame, inform the renderer of the new URL's
325 // per-host settings before the request actually commits. This way the 328 // per-host settings before the request actually commits. This way the
326 // renderer will be able to set these precisely at the time the 329 // renderer will be able to set these precisely at the time the
327 // request commits, avoiding the possibility of e.g. zooming the old content 330 // request commits, avoiding the possibility of e.g. zooming the old content
328 // or of having to layout the new content twice. 331 // or of having to layout the new content twice.
329 332
330 response_started_ticks_ = base::TimeTicks::Now(); 333 response_started_ticks_ = base::TimeTicks::Now();
331 334
332 progress_timer_.Stop(); 335 progress_timer_.Stop();
333 const ResourceRequestInfoImpl* info = GetRequestInfo(); 336 const ResourceRequestInfoImpl* info = GetRequestInfo();
334 if (!info->filter()) 337 BrowserMessageFilter* filter = GetFilter();
338 if (!filter)
335 return false; 339 return false;
336 340
337 // We want to send a final upload progress message prior to sending the 341 // We want to send a final upload progress message prior to sending the
338 // response complete message even if we're waiting for an ack to to a 342 // response complete message even if we're waiting for an ack to to a
339 // previous upload progress message. 343 // previous upload progress message.
340 if (info->is_upload_progress_enabled()) { 344 if (info->is_upload_progress_enabled()) {
341 waiting_for_upload_progress_ack_ = false; 345 waiting_for_upload_progress_ack_ = false;
342 ReportUploadProgress(); 346 ReportUploadProgress();
343 } 347 }
344 348
345 if (rdh_->delegate()) { 349 if (rdh_->delegate()) {
346 rdh_->delegate()->OnResponseStarted(request(), info->GetContext(), 350 rdh_->delegate()->OnResponseStarted(request(), info->GetContext(),
347 response); 351 response);
348 } 352 }
349 353
350 NetLogObserver::PopulateResponseInfo(request(), response); 354 NetLogObserver::PopulateResponseInfo(request(), response);
351 response->head.encoded_data_length = request()->raw_header_size(); 355 response->head.encoded_data_length = request()->raw_header_size();
352 356
353 // If the parent handler downloaded the resource to a file, grant the child 357 // If the parent handler downloaded the resource to a file, grant the child
354 // read permissions on it. 358 // read permissions on it.
355 if (!response->head.download_file_path.empty()) { 359 if (!response->head.download_file_path.empty()) {
356 rdh_->RegisterDownloadedTempFile( 360 rdh_->RegisterDownloadedTempFile(
357 info->GetChildID(), info->GetRequestID(), 361 info->GetChildID(), info->GetRequestID(),
358 response->head.download_file_path); 362 response->head.download_file_path);
359 } 363 }
360 364
361 response->head.request_start = request()->creation_time(); 365 response->head.request_start = request()->creation_time();
362 response->head.response_start = TimeTicks::Now(); 366 response->head.response_start = TimeTicks::Now();
363 info->filter()->Send(new ResourceMsg_ReceivedResponse(GetRequestID(), 367 filter->Send(
364 response->head)); 368 new ResourceMsg_ReceivedResponse(GetRequestID(), response->head));
365 sent_received_response_msg_ = true; 369 sent_received_response_msg_ = true;
366 370
367 if (request()->response_info().metadata.get()) { 371 if (request()->response_info().metadata.get()) {
368 std::vector<char> copy(request()->response_info().metadata->data(), 372 std::vector<char> copy(request()->response_info().metadata->data(),
369 request()->response_info().metadata->data() + 373 request()->response_info().metadata->data() +
370 request()->response_info().metadata->size()); 374 request()->response_info().metadata->size());
371 info->filter()->Send(new ResourceMsg_ReceivedCachedMetadata(GetRequestID(), 375 filter->Send(new ResourceMsg_ReceivedCachedMetadata(GetRequestID(), copy));
372 copy));
373 } 376 }
374 377
375 inlining_helper_->OnResponseReceived(*response); 378 inlining_helper_->OnResponseReceived(*response);
376 return true; 379 return true;
377 } 380 }
378 381
379 bool AsyncResourceHandler::OnWillStart(const GURL& url, bool* defer) { 382 bool AsyncResourceHandler::OnWillStart(const GURL& url, bool* defer) {
383 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
380 if (GetRequestInfo()->is_upload_progress_enabled() && 384 if (GetRequestInfo()->is_upload_progress_enabled() &&
381 request()->has_upload()) { 385 request()->has_upload()) {
382 ReportUploadProgress(); 386 ReportUploadProgress();
383 progress_timer_.Start( 387 progress_timer_.Start(
384 FROM_HERE, 388 FROM_HERE,
385 base::TimeDelta::FromMilliseconds(kUploadProgressIntervalMsec), 389 base::TimeDelta::FromMilliseconds(kUploadProgressIntervalMsec),
386 this, 390 this,
387 &AsyncResourceHandler::ReportUploadProgress); 391 &AsyncResourceHandler::ReportUploadProgress);
388 } 392 }
389 return true; 393 return true;
390 } 394 }
391 395
392 bool AsyncResourceHandler::OnWillRead(scoped_refptr<net::IOBuffer>* buf, 396 bool AsyncResourceHandler::OnWillRead(scoped_refptr<net::IOBuffer>* buf,
393 int* buf_size, 397 int* buf_size,
394 int min_size) { 398 int min_size) {
399 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
395 DCHECK_EQ(-1, min_size); 400 DCHECK_EQ(-1, min_size);
396 401
397 if (!CheckForSufficientResource()) 402 if (!CheckForSufficientResource())
398 return false; 403 return false;
399 404
400 // Return early if InliningHelper allocates the buffer, so that we should 405 // Return early if InliningHelper allocates the buffer, so that we should
401 // inline the data into the IPC message without allocating SharedMemory. 406 // inline the data into the IPC message without allocating SharedMemory.
402 if (inlining_helper_->PrepareInlineBufferIfApplicable(buf, buf_size)) 407 if (inlining_helper_->PrepareInlineBufferIfApplicable(buf, buf_size))
403 return true; 408 return true;
404 409
405 if (!EnsureResourceBufferIsInitialized()) 410 if (!EnsureResourceBufferIsInitialized())
406 return false; 411 return false;
407 412
408 DCHECK(buffer_->CanAllocate()); 413 DCHECK(buffer_->CanAllocate());
409 char* memory = buffer_->Allocate(&allocation_size_); 414 char* memory = buffer_->Allocate(&allocation_size_);
410 CHECK(memory); 415 CHECK(memory);
411 416
412 *buf = new DependentIOBuffer(buffer_.get(), memory); 417 *buf = new DependentIOBuffer(buffer_.get(), memory);
413 *buf_size = allocation_size_; 418 *buf_size = allocation_size_;
414 419
415 return true; 420 return true;
416 } 421 }
417 422
418 bool AsyncResourceHandler::OnReadCompleted(int bytes_read, bool* defer) { 423 bool AsyncResourceHandler::OnReadCompleted(int bytes_read, bool* defer) {
424 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
419 DCHECK_GE(bytes_read, 0); 425 DCHECK_GE(bytes_read, 0);
420 426
421 if (!bytes_read) 427 if (!bytes_read)
422 return true; 428 return true;
423 429
424 ResourceMessageFilter* filter = GetFilter(); 430 BrowserMessageFilter* filter = GetFilter();
425 if (!filter) 431 if (!filter)
426 return false; 432 return false;
427 433
428 int encoded_data_length = CalculateEncodedDataLengthToReport(); 434 int encoded_data_length = CalculateEncodedDataLengthToReport();
429 if (!first_chunk_read_) 435 if (!first_chunk_read_)
430 encoded_data_length -= request()->raw_header_size(); 436 encoded_data_length -= request()->raw_header_size();
431 437
432 int encoded_body_length = CalculateEncodedBodyLengthToReport(); 438 int encoded_body_length = CalculateEncodedBodyLengthToReport();
433 first_chunk_read_ = true; 439 first_chunk_read_ = true;
434 440
(...skipping 25 matching lines...) Expand all
460 466
461 if (!buffer_->CanAllocate()) { 467 if (!buffer_->CanAllocate()) {
462 *defer = did_defer_ = true; 468 *defer = did_defer_ = true;
463 OnDefer(); 469 OnDefer();
464 } 470 }
465 471
466 return true; 472 return true;
467 } 473 }
468 474
469 void AsyncResourceHandler::OnDataDownloaded(int bytes_downloaded) { 475 void AsyncResourceHandler::OnDataDownloaded(int bytes_downloaded) {
476 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
470 int encoded_data_length = CalculateEncodedDataLengthToReport(); 477 int encoded_data_length = CalculateEncodedDataLengthToReport();
471 478
472 ResourceMessageFilter* filter = GetFilter(); 479 BrowserMessageFilter* filter = GetFilter();
473 if (filter) { 480 if (filter) {
474 filter->Send(new ResourceMsg_DataDownloaded( 481 filter->Send(new ResourceMsg_DataDownloaded(
475 GetRequestID(), bytes_downloaded, encoded_data_length)); 482 GetRequestID(), bytes_downloaded, encoded_data_length));
476 } 483 }
477 } 484 }
478 485
479 void AsyncResourceHandler::OnResponseCompleted( 486 void AsyncResourceHandler::OnResponseCompleted(
480 const net::URLRequestStatus& status, 487 const net::URLRequestStatus& status,
481 bool* defer) { 488 bool* defer) {
489 DCHECK(GetRequestInfo()->requester_info().IsRenderer());
482 const ResourceRequestInfoImpl* info = GetRequestInfo(); 490 const ResourceRequestInfoImpl* info = GetRequestInfo();
483 if (!info->filter()) 491 BrowserMessageFilter* filter = GetFilter();
492 if (!filter)
484 return; 493 return;
485 494
486 // If we crash here, figure out what URL the renderer was requesting. 495 // If we crash here, figure out what URL the renderer was requesting.
487 // http://crbug.com/107692 496 // http://crbug.com/107692
488 char url_buf[128]; 497 char url_buf[128];
489 base::strlcpy(url_buf, request()->url().spec().c_str(), arraysize(url_buf)); 498 base::strlcpy(url_buf, request()->url().spec().c_str(), arraysize(url_buf));
490 base::debug::Alias(url_buf); 499 base::debug::Alias(url_buf);
491 500
492 // TODO(gavinp): Remove this CHECK when we figure out the cause of 501 // TODO(gavinp): Remove this CHECK when we figure out the cause of
493 // http://crbug.com/124680 . This check mirrors closely check in 502 // http://crbug.com/124680 . This check mirrors closely check in
(...skipping 12 matching lines...) Expand all
506 // the ERR_ABORTED error code). 515 // the ERR_ABORTED error code).
507 DCHECK(!was_ignored_by_handler || error_code == net::ERR_ABORTED); 516 DCHECK(!was_ignored_by_handler || error_code == net::ERR_ABORTED);
508 517
509 ResourceRequestCompletionStatus request_complete_data; 518 ResourceRequestCompletionStatus request_complete_data;
510 request_complete_data.error_code = error_code; 519 request_complete_data.error_code = error_code;
511 request_complete_data.was_ignored_by_handler = was_ignored_by_handler; 520 request_complete_data.was_ignored_by_handler = was_ignored_by_handler;
512 request_complete_data.exists_in_cache = request()->response_info().was_cached; 521 request_complete_data.exists_in_cache = request()->response_info().was_cached;
513 request_complete_data.completion_time = TimeTicks::Now(); 522 request_complete_data.completion_time = TimeTicks::Now();
514 request_complete_data.encoded_data_length = 523 request_complete_data.encoded_data_length =
515 request()->GetTotalReceivedBytes(); 524 request()->GetTotalReceivedBytes();
516 info->filter()->Send( 525 filter->Send(
517 new ResourceMsg_RequestComplete(GetRequestID(), request_complete_data)); 526 new ResourceMsg_RequestComplete(GetRequestID(), request_complete_data));
518 527
519 if (status.is_success()) 528 if (status.is_success())
520 RecordHistogram(); 529 RecordHistogram();
521 } 530 }
522 531
523 bool AsyncResourceHandler::EnsureResourceBufferIsInitialized() { 532 bool AsyncResourceHandler::EnsureResourceBufferIsInitialized() {
524 DCHECK(has_checked_for_sufficient_resources_); 533 DCHECK(has_checked_for_sufficient_resources_);
525 534
526 if (buffer_.get() && buffer_->IsInitialized()) 535 if (buffer_.get() && buffer_->IsInitialized())
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after
586 } else { 595 } else {
587 UMA_HISTOGRAM_CUSTOM_COUNTS( 596 UMA_HISTOGRAM_CUSTOM_COUNTS(
588 "Net.ResourceLoader.ResponseStartToEnd.Over_512kB", 597 "Net.ResourceLoader.ResponseStartToEnd.Over_512kB",
589 elapsed_time, 1, 100000, 100); 598 elapsed_time, 1, 100000, 100);
590 } 599 }
591 600
592 inlining_helper_->RecordHistogram(elapsed_time); 601 inlining_helper_->RecordHistogram(elapsed_time);
593 } 602 }
594 603
595 } // namespace content 604 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698