Index: src/heap.h |
diff --git a/src/heap.h b/src/heap.h |
index f488b8cda276316df11e6df8b3e645a533c8b111..fcdd65c7b9ce6ae93455a3532191c355436af0cd 100644 |
--- a/src/heap.h |
+++ b/src/heap.h |
@@ -282,24 +282,42 @@ class HeapDebugUtils; |
// by it's size to avoid dereferencing a map pointer for scanning. |
class PromotionQueue { |
public: |
- PromotionQueue() : front_(NULL), rear_(NULL) { } |
+ PromotionQueue() |
+ : front_(NULL), rear_(NULL), limit_(NULL), emergency_stack_(0) { } |
- void Initialize(Address start_address) { |
+ void Initialize(NewSpace* new_space) { |
// Assumes that a NewSpacePage exactly fits a number of promotion queue |
// entries (where each is a pair of intptr_t). This allows us to simplify |
// the test fpr when to switch pages. |
ASSERT((Page::kPageSize - MemoryChunk::kBodyOffset) % (2 * kPointerSize) |
== 0); |
- ASSERT(NewSpacePage::IsAtEnd(start_address)); |
- front_ = rear_ = reinterpret_cast<intptr_t*>(start_address); |
+ limit_ = reinterpret_cast<intptr_t*>(new_space->ToSpaceStart()); |
+ front_ = rear_ = reinterpret_cast<intptr_t*>(new_space->ToSpaceEnd()); |
+ emergency_stack_ = NULL; |
} |
- bool is_empty() { return front_ == rear_; } |
+ void Destroy() { |
+ delete emergency_stack_; |
Erik Corry
2011/11/07 16:35:25
I would be more comfortable if you also nulled it.
|
+ } |
+ |
+ void SetNewLimit(Address limit); |
+ |
+ bool is_empty() { |
+ return (front_ == rear_) && |
+ (emergency_stack_ == NULL || emergency_stack_->length() == 0); |
+ } |
inline void insert(HeapObject* target, int size); |
void remove(HeapObject** target, int* size) { |
ASSERT(!is_empty()); |
+ if (front_ == rear_) { |
+ Entry e = emergency_stack_->RemoveLast(); |
+ *target = e.obj_; |
+ *size = e.size_; |
+ return; |
+ } |
+ |
if (NewSpacePage::IsAtStart(reinterpret_cast<Address>(front_))) { |
NewSpacePage* front_page = |
NewSpacePage::FromAddress(reinterpret_cast<Address>(front_)); |
@@ -318,6 +336,19 @@ class PromotionQueue { |
// The front of the queue is higher in the memory page chain than the rear. |
intptr_t* front_; |
intptr_t* rear_; |
+ intptr_t* limit_; |
+ |
+ static const int kEntrySizeInWords = 2; |
+ |
+ struct Entry { |
+ Entry(HeapObject* obj, int size) : obj_(obj), size_(size) { } |
+ |
+ HeapObject* obj_; |
+ int size_; |
+ }; |
+ List<Entry>* emergency_stack_; |
+ |
+ void RelocateQueueHead(); |
DISALLOW_COPY_AND_ASSIGN(PromotionQueue); |
}; |