OLD | NEW |
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 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 // See http://dev.chromium.org/developers/design-documents/multi-process-resourc
e-loading | 5 // See http://dev.chromium.org/developers/design-documents/multi-process-resourc
e-loading |
6 | 6 |
7 #include "chrome/common/resource_dispatcher.h" | 7 #include "chrome/common/resource_dispatcher.h" |
8 | 8 |
9 #include "base/basictypes.h" | 9 #include "base/basictypes.h" |
10 #include "base/compiler_specific.h" | 10 #include "base/compiler_specific.h" |
(...skipping 258 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
269 if (!message.ReadInt(&iter, &request_id)) { | 269 if (!message.ReadInt(&iter, &request_id)) { |
270 NOTREACHED() << "malformed resource message"; | 270 NOTREACHED() << "malformed resource message"; |
271 return true; | 271 return true; |
272 } | 272 } |
273 | 273 |
274 PendingRequestList::iterator it = pending_requests_.find(request_id); | 274 PendingRequestList::iterator it = pending_requests_.find(request_id); |
275 if (it == pending_requests_.end()) { | 275 if (it == pending_requests_.end()) { |
276 // This might happen for kill()ed requests on the webkit end, so perhaps it | 276 // This might happen for kill()ed requests on the webkit end, so perhaps it |
277 // shouldn't be a warning... | 277 // shouldn't be a warning... |
278 DLOG(WARNING) << "Got response for a nonexistant or finished request"; | 278 DLOG(WARNING) << "Got response for a nonexistant or finished request"; |
| 279 // Release resources in the message if it is a data message. |
| 280 ReleaseResourcesInDataMessage(message); |
279 return true; | 281 return true; |
280 } | 282 } |
281 | 283 |
282 PendingRequestInfo& request_info = it->second; | 284 PendingRequestInfo& request_info = it->second; |
283 if (request_info.is_deferred) { | 285 if (request_info.is_deferred) { |
284 request_info.deferred_message_queue.push_back(new IPC::Message(message)); | 286 request_info.deferred_message_queue.push_back(new IPC::Message(message)); |
285 return true; | 287 return true; |
286 } | 288 } |
287 // Make sure any deferred messages are dispatched before we dispatch more. | 289 // Make sure any deferred messages are dispatched before we dispatch more. |
288 if (!request_info.deferred_message_queue.empty()) | 290 if (!request_info.deferred_message_queue.empty()) |
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
460 // Compute a unique request_id for this renderer process. | 462 // Compute a unique request_id for this renderer process. |
461 int id = MakeRequestID(); | 463 int id = MakeRequestID(); |
462 pending_requests_[id] = PendingRequestInfo(callback, resource_type); | 464 pending_requests_[id] = PendingRequestInfo(callback, resource_type); |
463 return id; | 465 return id; |
464 } | 466 } |
465 | 467 |
466 bool ResourceDispatcher::RemovePendingRequest(int request_id) { | 468 bool ResourceDispatcher::RemovePendingRequest(int request_id) { |
467 PendingRequestList::iterator it = pending_requests_.find(request_id); | 469 PendingRequestList::iterator it = pending_requests_.find(request_id); |
468 if (it == pending_requests_.end()) | 470 if (it == pending_requests_.end()) |
469 return false; | 471 return false; |
| 472 |
| 473 // Iterate through the deferred message queue and clean up the messages. |
| 474 PendingRequestInfo& request_info = it->second; |
| 475 MessageQueue& q = request_info.deferred_message_queue; |
| 476 while (!q.empty()) { |
| 477 IPC::Message* m = q.front(); |
| 478 ReleaseResourcesInDataMessage(*m); |
| 479 q.pop_front(); |
| 480 delete m; |
| 481 } |
| 482 |
470 pending_requests_.erase(it); | 483 pending_requests_.erase(it); |
471 return true; | 484 return true; |
472 } | 485 } |
473 | 486 |
474 void ResourceDispatcher::SetDefersLoading(int request_id, bool value) { | 487 void ResourceDispatcher::SetDefersLoading(int request_id, bool value) { |
475 PendingRequestList::iterator it = pending_requests_.find(request_id); | 488 PendingRequestList::iterator it = pending_requests_.find(request_id); |
476 if (it == pending_requests_.end()) { | 489 if (it == pending_requests_.end()) { |
477 NOTREACHED() << "unknown request"; | 490 NOTREACHED() << "unknown request"; |
478 return; | 491 return; |
479 } | 492 } |
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
552 case ViewMsg_Resource_DataReceived::ID: | 565 case ViewMsg_Resource_DataReceived::ID: |
553 case ViewMsg_Resource_RequestComplete::ID: | 566 case ViewMsg_Resource_RequestComplete::ID: |
554 return true; | 567 return true; |
555 | 568 |
556 default: | 569 default: |
557 break; | 570 break; |
558 } | 571 } |
559 | 572 |
560 return false; | 573 return false; |
561 } | 574 } |
| 575 |
| 576 void ResourceDispatcher::ReleaseResourcesInDataMessage( |
| 577 const IPC::Message& message) { |
| 578 void* iter = NULL; |
| 579 int request_id; |
| 580 if (!message.ReadInt(&iter, &request_id)) { |
| 581 NOTREACHED() << "malformed resource message"; |
| 582 return; |
| 583 } |
| 584 |
| 585 // If the message contains a shared memory handle, we should close the |
| 586 // handle or there will be a memory leak. |
| 587 if (message.type() == ViewMsg_Resource_DataReceived::ID) { |
| 588 base::SharedMemoryHandle shm_handle; |
| 589 if (IPC::ParamTraits<base::SharedMemoryHandle>::Read(&message, |
| 590 &iter, |
| 591 &shm_handle)) { |
| 592 base::SharedMemory::CloseHandle(shm_handle); |
| 593 } |
| 594 } |
| 595 } |
OLD | NEW |