Chromium Code Reviews| Index: src/heap/heap.cc |
| diff --git a/src/heap/heap.cc b/src/heap/heap.cc |
| index 234bc9f563a14d148cc19967d902fb7cc1c4ff8e..0ee13ebaf4d814b5b83c7a7ac7c42a6085cc7b10 100644 |
| --- a/src/heap/heap.cc |
| +++ b/src/heap/heap.cc |
| @@ -135,6 +135,7 @@ Heap::Heap() |
| current_gc_flags_(Heap::kNoGCFlags), |
| external_string_table_(this), |
| chunks_queued_for_free_(NULL), |
| + pending_unmap_job_semaphore_(0), |
| gc_callbacks_depth_(0), |
| deserialization_complete_(false), |
| concurrent_sweeping_enabled_(false), |
| @@ -6654,6 +6655,34 @@ void ExternalStringTable::TearDown() { |
| } |
| +class Heap::UnmapFreeMemoryTask : public v8::Task { |
| + public: |
| + UnmapFreeMemoryTask(Heap* heap, MemoryChunk* head) |
| + : heap_(heap), head_(head) {} |
| + virtual ~UnmapFreeMemoryTask() {} |
| + |
| + |
|
Michael Lippautz
2015/08/21 12:28:58
-line
Hannes Payer (out of office)
2015/08/21 12:56:04
Done.
|
| + private: |
| + // v8::Task overrides. |
| + void Run() override { |
| + heap_->FreeQueuedChunks(head_); |
| + heap_->pending_unmap_job_semaphore_.Signal(); |
| + } |
| + |
| + Heap* heap_; |
| + MemoryChunk* head_; |
| + |
| + DISALLOW_COPY_AND_ASSIGN(UnmapFreeMemoryTask); |
| +}; |
| + |
| + |
| +void Heap::WaitUntilUnmappingOfFreeChunksCompleted() { |
| + // We start an unmap job after sweeping and after compaction. |
| + pending_unmap_job_semaphore_.Wait(); |
| + pending_unmap_job_semaphore_.Wait(); |
| +} |
| + |
| + |
| void Heap::QueueMemoryChunkForFree(MemoryChunk* chunk) { |
| chunk->set_next_chunk(chunks_queued_for_free_); |
| chunks_queued_for_free_ = chunk; |
| @@ -6668,19 +6697,32 @@ void Heap::FilterStoreBufferEntriesOnAboutToBeFreedPages() { |
| next = chunk->next_chunk(); |
| chunk->SetFlag(MemoryChunk::ABOUT_TO_BE_FREED); |
| } |
| - isolate_->heap()->store_buffer()->Compact(); |
| - isolate_->heap()->store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); |
| + store_buffer()->Compact(); |
| + store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); |
| } |
| void Heap::FreeQueuedChunks() { |
| + if (chunks_queued_for_free_ != NULL) { |
| + V8::GetCurrentPlatform()->CallOnBackgroundThread( |
| + new UnmapFreeMemoryTask(this, chunks_queued_for_free_), |
| + v8::Platform::kShortRunningTask); |
| + chunks_queued_for_free_ = NULL; |
| + } else { |
| + // If we do not have anything to unmap, we just signal the semaphore |
| + // that we are done. |
| + pending_unmap_job_semaphore_.Signal(); |
| + } |
| +} |
| + |
| + |
| +void Heap::FreeQueuedChunks(MemoryChunk* list_head) { |
| MemoryChunk* next; |
| MemoryChunk* chunk; |
| - for (chunk = chunks_queued_for_free_; chunk != NULL; chunk = next) { |
| + for (chunk = list_head; chunk != NULL; chunk = next) { |
| next = chunk->next_chunk(); |
| isolate_->memory_allocator()->Free(chunk); |
| } |
| - chunks_queued_for_free_ = NULL; |
| } |