Index: src/heap/heap.h |
diff --git a/src/heap/heap.h b/src/heap/heap.h |
index 89885782b4507b867248e46848d3bd9e5ce58964..1e6a90145522f77ef7cb9ad9fe8827f8012909ab 100644 |
--- a/src/heap/heap.h |
+++ b/src/heap/heap.h |
@@ -402,6 +402,9 @@ class StoreBufferRebuilder { |
// A queue of objects promoted during scavenge. Each object is accompanied |
// by it's size to avoid dereferencing a map pointer for scanning. |
+// The last page in to-space is used for the promotion queue. On conflict |
+// during scavenge, the promotion queue is allocated externally and all |
+// entries are copied to the external queue. |
class PromotionQueue { |
public: |
explicit PromotionQueue(Heap* heap) |
@@ -424,6 +427,12 @@ class PromotionQueue { |
} |
void SetNewLimit(Address limit) { |
+ // If we are already using an emergency stack, we can ignore it. |
+ if (emergency_stack_) return; |
+ |
+ // If the limit is not on the same page, we can ignore it. |
+ if (Page::FromAllocationTop(limit) != GetHeadPage()) return; |
+ |
limit_ = reinterpret_cast<intptr_t*>(limit); |
if (limit_ <= rear_) { |
@@ -434,6 +443,10 @@ class PromotionQueue { |
} |
bool IsBelowPromotionQueue(Address to_space_top) { |
+ // If an emergency stack is used, the to-space address cannot interfere |
+ // with the promotion queue. |
+ if (emergency_stack_) return true; |
+ |
// If the given to-space top pointer and the head of the promotion queue |
// are not on the same page, then the to-space objects are below the |
// promotion queue. |
@@ -461,12 +474,6 @@ class PromotionQueue { |
return; |
} |
- if (NewSpacePage::IsAtStart(reinterpret_cast<Address>(front_))) { |
- NewSpacePage* front_page = |
- NewSpacePage::FromAddress(reinterpret_cast<Address>(front_)); |
- DCHECK(!front_page->prev_page()->is_anchor()); |
- front_ = reinterpret_cast<intptr_t*>(front_page->prev_page()->area_end()); |
- } |
*target = reinterpret_cast<HeapObject*>(*(--front_)); |
*size = static_cast<int>(*(--front_)); |
// Assert no underflow. |