| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project 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 "src/heap/mark-compact.h" | 5 #include "src/heap/mark-compact.h" |
| 6 | 6 |
| 7 #include "src/base/atomicops.h" | 7 #include "src/base/atomicops.h" |
| 8 #include "src/base/bits.h" | 8 #include "src/base/bits.h" |
| 9 #include "src/base/sys-info.h" | 9 #include "src/base/sys-info.h" |
| 10 #include "src/code-stubs.h" | 10 #include "src/code-stubs.h" |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 54 public: | 54 public: |
| 55 virtual void Run() = 0; | 55 virtual void Run() = 0; |
| 56 | 56 |
| 57 protected: | 57 protected: |
| 58 explicit MarkingVerifier(Heap* heap) : heap_(heap) {} | 58 explicit MarkingVerifier(Heap* heap) : heap_(heap) {} |
| 59 | 59 |
| 60 virtual MarkingState marking_state(MemoryChunk* chunk) = 0; | 60 virtual MarkingState marking_state(MemoryChunk* chunk) = 0; |
| 61 | 61 |
| 62 virtual void VerifyPointers(Object** start, Object** end) = 0; | 62 virtual void VerifyPointers(Object** start, Object** end) = 0; |
| 63 | 63 |
| 64 void VisitPointers(Object** start, Object** end) override { | 64 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 65 VerifyPointers(start, end); | 65 VerifyPointers(start, end); |
| 66 } | 66 } |
| 67 | 67 |
| 68 void VisitRootPointers(Root root, Object** start, Object** end) override { | 68 void VisitRootPointers(Root root, Object** start, Object** end) override { |
| 69 VerifyPointers(start, end); | 69 VerifyPointers(start, end); |
| 70 } | 70 } |
| 71 | 71 |
| 72 void VerifyRoots(VisitMode mode); | 72 void VerifyRoots(VisitMode mode); |
| 73 void VerifyMarkingOnPage(const Page& page, const MarkingState& state, | 73 void VerifyMarkingOnPage(const Page& page, const MarkingState& state, |
| 74 Address start, Address end); | 74 Address start, Address end); |
| (...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 163 | 163 |
| 164 void VerifyPointers(Object** start, Object** end) override { | 164 void VerifyPointers(Object** start, Object** end) override { |
| 165 for (Object** current = start; current < end; current++) { | 165 for (Object** current = start; current < end; current++) { |
| 166 if ((*current)->IsHeapObject()) { | 166 if ((*current)->IsHeapObject()) { |
| 167 HeapObject* object = HeapObject::cast(*current); | 167 HeapObject* object = HeapObject::cast(*current); |
| 168 CHECK(ObjectMarking::IsBlackOrGrey(object, marking_state(object))); | 168 CHECK(ObjectMarking::IsBlackOrGrey(object, marking_state(object))); |
| 169 } | 169 } |
| 170 } | 170 } |
| 171 } | 171 } |
| 172 | 172 |
| 173 void VisitEmbeddedPointer(RelocInfo* rinfo) override { | 173 void VisitEmbeddedPointer(Code* host, RelocInfo* rinfo) override { |
| 174 DCHECK(rinfo->rmode() == RelocInfo::EMBEDDED_OBJECT); | 174 DCHECK(rinfo->rmode() == RelocInfo::EMBEDDED_OBJECT); |
| 175 if (!rinfo->host()->IsWeakObject(rinfo->target_object())) { | 175 if (!host->IsWeakObject(rinfo->target_object())) { |
| 176 Object* p = rinfo->target_object(); | 176 Object* p = rinfo->target_object(); |
| 177 VisitPointer(&p); | 177 VisitPointer(host, &p); |
| 178 } | 178 } |
| 179 } | 179 } |
| 180 | 180 |
| 181 void VisitCell(RelocInfo* rinfo) override { | 181 void VisitCell(Code* host, RelocInfo* rinfo) override { |
| 182 Code* code = rinfo->host(); | |
| 183 DCHECK(rinfo->rmode() == RelocInfo::CELL); | 182 DCHECK(rinfo->rmode() == RelocInfo::CELL); |
| 184 if (!code->IsWeakObject(rinfo->target_cell())) { | 183 if (!host->IsWeakObject(rinfo->target_cell())) { |
| 185 ObjectVisitor::VisitCell(rinfo); | 184 ObjectVisitor::VisitCell(host, rinfo); |
| 186 } | 185 } |
| 187 } | 186 } |
| 188 }; | 187 }; |
| 189 | 188 |
| 190 class YoungGenerationMarkingVerifier : public MarkingVerifier { | 189 class YoungGenerationMarkingVerifier : public MarkingVerifier { |
| 191 public: | 190 public: |
| 192 explicit YoungGenerationMarkingVerifier(Heap* heap) : MarkingVerifier(heap) {} | 191 explicit YoungGenerationMarkingVerifier(Heap* heap) : MarkingVerifier(heap) {} |
| 193 | 192 |
| 194 MarkingState marking_state(MemoryChunk* chunk) override { | 193 MarkingState marking_state(MemoryChunk* chunk) override { |
| 195 return MarkingState::External(chunk); | 194 return MarkingState::External(chunk); |
| (...skipping 16 matching lines...) Expand all Loading... |
| 212 CHECK(ObjectMarking::IsBlackOrGrey(object, marking_state(object))); | 211 CHECK(ObjectMarking::IsBlackOrGrey(object, marking_state(object))); |
| 213 } | 212 } |
| 214 } | 213 } |
| 215 } | 214 } |
| 216 }; | 215 }; |
| 217 | 216 |
| 218 class EvacuationVerifier : public ObjectVisitor, public RootVisitor { | 217 class EvacuationVerifier : public ObjectVisitor, public RootVisitor { |
| 219 public: | 218 public: |
| 220 virtual void Run() = 0; | 219 virtual void Run() = 0; |
| 221 | 220 |
| 222 void VisitPointers(Object** start, Object** end) override { | 221 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 223 VerifyPointers(start, end); | 222 VerifyPointers(start, end); |
| 224 } | 223 } |
| 225 | 224 |
| 226 void VisitRootPointers(Root root, Object** start, Object** end) override { | 225 void VisitRootPointers(Root root, Object** start, Object** end) override { |
| 227 VerifyPointers(start, end); | 226 VerifyPointers(start, end); |
| 228 } | 227 } |
| 229 | 228 |
| 230 protected: | 229 protected: |
| 231 explicit EvacuationVerifier(Heap* heap) : heap_(heap) {} | 230 explicit EvacuationVerifier(Heap* heap) : heap_(heap) {} |
| 232 | 231 |
| (...skipping 897 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1130 ClearNextCandidate(function, undefined); | 1129 ClearNextCandidate(function, undefined); |
| 1131 break; | 1130 break; |
| 1132 } | 1131 } |
| 1133 | 1132 |
| 1134 candidate = next_candidate; | 1133 candidate = next_candidate; |
| 1135 } | 1134 } |
| 1136 } | 1135 } |
| 1137 } | 1136 } |
| 1138 | 1137 |
| 1139 | 1138 |
| 1140 void CodeFlusher::IteratePointersToFromSpace(ObjectVisitor* v) { | |
| 1141 Heap* heap = isolate_->heap(); | |
| 1142 | |
| 1143 JSFunction** slot = &jsfunction_candidates_head_; | |
| 1144 JSFunction* candidate = jsfunction_candidates_head_; | |
| 1145 while (candidate != NULL) { | |
| 1146 if (heap->InFromSpace(candidate)) { | |
| 1147 v->VisitPointer(reinterpret_cast<Object**>(slot)); | |
| 1148 } | |
| 1149 candidate = GetNextCandidate(*slot); | |
| 1150 slot = GetNextCandidateSlot(*slot); | |
| 1151 } | |
| 1152 } | |
| 1153 | |
| 1154 class StaticYoungGenerationMarkingVisitor | 1139 class StaticYoungGenerationMarkingVisitor |
| 1155 : public StaticNewSpaceVisitor<StaticYoungGenerationMarkingVisitor> { | 1140 : public StaticNewSpaceVisitor<StaticYoungGenerationMarkingVisitor> { |
| 1156 public: | 1141 public: |
| 1157 static void Initialize(Heap* heap) { | 1142 static void Initialize(Heap* heap) { |
| 1158 StaticNewSpaceVisitor<StaticYoungGenerationMarkingVisitor>::Initialize(); | 1143 StaticNewSpaceVisitor<StaticYoungGenerationMarkingVisitor>::Initialize(); |
| 1159 } | 1144 } |
| 1160 | 1145 |
| 1161 inline static void VisitPointer(Heap* heap, HeapObject* object, Object** p) { | 1146 inline static void VisitPointer(Heap* heap, HeapObject* object, Object** p) { |
| 1162 Object* target = *p; | 1147 Object* target = *p; |
| 1163 if (heap->InNewSpace(target)) { | 1148 if (heap->InNewSpace(target)) { |
| (...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1363 private: | 1348 private: |
| 1364 MarkCompactCollector* collector_; | 1349 MarkCompactCollector* collector_; |
| 1365 }; | 1350 }; |
| 1366 | 1351 |
| 1367 class SharedFunctionInfoMarkingVisitor : public ObjectVisitor, | 1352 class SharedFunctionInfoMarkingVisitor : public ObjectVisitor, |
| 1368 public RootVisitor { | 1353 public RootVisitor { |
| 1369 public: | 1354 public: |
| 1370 explicit SharedFunctionInfoMarkingVisitor(MarkCompactCollector* collector) | 1355 explicit SharedFunctionInfoMarkingVisitor(MarkCompactCollector* collector) |
| 1371 : collector_(collector) {} | 1356 : collector_(collector) {} |
| 1372 | 1357 |
| 1373 void VisitPointers(Object** start, Object** end) override { | 1358 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 1374 for (Object** p = start; p < end; p++) MarkObject(p); | 1359 for (Object** p = start; p < end; p++) MarkObject(p); |
| 1375 } | 1360 } |
| 1376 | 1361 |
| 1377 void VisitPointer(Object** slot) override { MarkObject(slot); } | 1362 void VisitPointer(HeapObject* host, Object** slot) override { |
| 1363 MarkObject(slot); |
| 1364 } |
| 1378 | 1365 |
| 1379 void VisitRootPointers(Root root, Object** start, Object** end) override { | 1366 void VisitRootPointers(Root root, Object** start, Object** end) override { |
| 1380 for (Object** p = start; p < end; p++) MarkObject(p); | 1367 for (Object** p = start; p < end; p++) MarkObject(p); |
| 1381 } | 1368 } |
| 1382 | 1369 |
| 1383 void VisitRootPointer(Root root, Object** slot) override { MarkObject(slot); } | 1370 void VisitRootPointer(Root root, Object** slot) override { MarkObject(slot); } |
| 1384 | 1371 |
| 1385 private: | 1372 private: |
| 1386 void MarkObject(Object** slot) { | 1373 void MarkObject(Object** slot) { |
| 1387 Object* obj = *slot; | 1374 Object* obj = *slot; |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1473 | 1460 |
| 1474 // Visitor class for marking heap roots. | 1461 // Visitor class for marking heap roots. |
| 1475 // TODO(ulan): Remove ObjectVisitor base class after fixing marking of | 1462 // TODO(ulan): Remove ObjectVisitor base class after fixing marking of |
| 1476 // the string table and the top optimized code. | 1463 // the string table and the top optimized code. |
| 1477 class MarkCompactCollector::RootMarkingVisitor : public ObjectVisitor, | 1464 class MarkCompactCollector::RootMarkingVisitor : public ObjectVisitor, |
| 1478 public RootVisitor { | 1465 public RootVisitor { |
| 1479 public: | 1466 public: |
| 1480 explicit RootMarkingVisitor(Heap* heap) | 1467 explicit RootMarkingVisitor(Heap* heap) |
| 1481 : collector_(heap->mark_compact_collector()) {} | 1468 : collector_(heap->mark_compact_collector()) {} |
| 1482 | 1469 |
| 1483 void VisitPointer(Object** p) override { MarkObjectByPointer(p); } | 1470 void VisitPointer(HeapObject* host, Object** p) override { |
| 1471 MarkObjectByPointer(p); |
| 1472 } |
| 1484 | 1473 |
| 1485 void VisitPointers(Object** start, Object** end) override { | 1474 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 1486 for (Object** p = start; p < end; p++) MarkObjectByPointer(p); | 1475 for (Object** p = start; p < end; p++) MarkObjectByPointer(p); |
| 1487 } | 1476 } |
| 1488 | 1477 |
| 1489 void VisitRootPointer(Root root, Object** p) override { | 1478 void VisitRootPointer(Root root, Object** p) override { |
| 1490 MarkObjectByPointer(p); | 1479 MarkObjectByPointer(p); |
| 1491 } | 1480 } |
| 1492 | 1481 |
| 1493 void VisitRootPointers(Root root, Object** start, Object** end) override { | 1482 void VisitRootPointers(Root root, Object** start, Object** end) override { |
| 1494 for (Object** p = start; p < end; p++) MarkObjectByPointer(p); | 1483 for (Object** p = start; p < end; p++) MarkObjectByPointer(p); |
| 1495 } | 1484 } |
| 1496 | 1485 |
| 1497 // Skip the weak next code link in a code object, which is visited in | 1486 // Skip the weak next code link in a code object, which is visited in |
| 1498 // ProcessTopOptimizedFrame. | 1487 // ProcessTopOptimizedFrame. |
| 1499 void VisitNextCodeLink(Object** p) override {} | 1488 void VisitNextCodeLink(Code* host, Object** p) override {} |
| 1500 | 1489 |
| 1501 private: | 1490 private: |
| 1502 void MarkObjectByPointer(Object** p) { | 1491 void MarkObjectByPointer(Object** p) { |
| 1503 if (!(*p)->IsHeapObject()) return; | 1492 if (!(*p)->IsHeapObject()) return; |
| 1504 | 1493 |
| 1505 HeapObject* object = HeapObject::cast(*p); | 1494 HeapObject* object = HeapObject::cast(*p); |
| 1506 | 1495 |
| 1507 if (ObjectMarking::IsBlackOrGrey<MarkBit::NON_ATOMIC>( | 1496 if (ObjectMarking::IsBlackOrGrey<MarkBit::NON_ATOMIC>( |
| 1508 object, MarkingState::Internal(object))) | 1497 object, MarkingState::Internal(object))) |
| 1509 return; | 1498 return; |
| (...skipping 13 matching lines...) Expand all Loading... |
| 1523 } | 1512 } |
| 1524 | 1513 |
| 1525 MarkCompactCollector* collector_; | 1514 MarkCompactCollector* collector_; |
| 1526 }; | 1515 }; |
| 1527 | 1516 |
| 1528 class InternalizedStringTableCleaner : public ObjectVisitor { | 1517 class InternalizedStringTableCleaner : public ObjectVisitor { |
| 1529 public: | 1518 public: |
| 1530 InternalizedStringTableCleaner(Heap* heap, HeapObject* table) | 1519 InternalizedStringTableCleaner(Heap* heap, HeapObject* table) |
| 1531 : heap_(heap), pointers_removed_(0), table_(table) {} | 1520 : heap_(heap), pointers_removed_(0), table_(table) {} |
| 1532 | 1521 |
| 1533 void VisitPointers(Object** start, Object** end) override { | 1522 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 1534 // Visit all HeapObject pointers in [start, end). | 1523 // Visit all HeapObject pointers in [start, end). |
| 1535 MarkCompactCollector* collector = heap_->mark_compact_collector(); | 1524 MarkCompactCollector* collector = heap_->mark_compact_collector(); |
| 1536 Object* the_hole = heap_->the_hole_value(); | 1525 Object* the_hole = heap_->the_hole_value(); |
| 1537 for (Object** p = start; p < end; p++) { | 1526 for (Object** p = start; p < end; p++) { |
| 1538 Object* o = *p; | 1527 Object* o = *p; |
| 1539 if (o->IsHeapObject()) { | 1528 if (o->IsHeapObject()) { |
| 1540 HeapObject* heap_object = HeapObject::cast(o); | 1529 HeapObject* heap_object = HeapObject::cast(o); |
| 1541 if (ObjectMarking::IsWhite(heap_object, | 1530 if (ObjectMarking::IsWhite(heap_object, |
| 1542 MarkingState::Internal(heap_object))) { | 1531 MarkingState::Internal(heap_object))) { |
| 1543 pointers_removed_++; | 1532 pointers_removed_++; |
| (...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1648 PushBlack(object); | 1637 PushBlack(object); |
| 1649 if (marking_deque()->IsFull()) return; | 1638 if (marking_deque()->IsFull()) return; |
| 1650 } | 1639 } |
| 1651 } | 1640 } |
| 1652 | 1641 |
| 1653 class RecordMigratedSlotVisitor final : public ObjectVisitor { | 1642 class RecordMigratedSlotVisitor final : public ObjectVisitor { |
| 1654 public: | 1643 public: |
| 1655 explicit RecordMigratedSlotVisitor(MarkCompactCollector* collector) | 1644 explicit RecordMigratedSlotVisitor(MarkCompactCollector* collector) |
| 1656 : collector_(collector) {} | 1645 : collector_(collector) {} |
| 1657 | 1646 |
| 1658 inline void VisitPointer(Object** p) final { | 1647 inline void VisitPointer(HeapObject* host, Object** p) final { |
| 1659 RecordMigratedSlot(*p, reinterpret_cast<Address>(p)); | 1648 RecordMigratedSlot(*p, reinterpret_cast<Address>(p)); |
| 1660 } | 1649 } |
| 1661 | 1650 |
| 1662 inline void VisitPointers(Object** start, Object** end) final { | 1651 inline void VisitPointers(HeapObject* host, Object** start, |
| 1652 Object** end) final { |
| 1663 while (start < end) { | 1653 while (start < end) { |
| 1664 RecordMigratedSlot(*start, reinterpret_cast<Address>(start)); | 1654 RecordMigratedSlot(*start, reinterpret_cast<Address>(start)); |
| 1665 ++start; | 1655 ++start; |
| 1666 } | 1656 } |
| 1667 } | 1657 } |
| 1668 | 1658 |
| 1669 inline void VisitCodeEntry(Address code_entry_slot) final { | 1659 inline void VisitCodeEntry(JSFunction* host, Address code_entry_slot) final { |
| 1670 Address code_entry = Memory::Address_at(code_entry_slot); | 1660 Address code_entry = Memory::Address_at(code_entry_slot); |
| 1671 if (Page::FromAddress(code_entry)->IsEvacuationCandidate()) { | 1661 if (Page::FromAddress(code_entry)->IsEvacuationCandidate()) { |
| 1672 RememberedSet<OLD_TO_OLD>::InsertTyped(Page::FromAddress(code_entry_slot), | 1662 RememberedSet<OLD_TO_OLD>::InsertTyped(Page::FromAddress(code_entry_slot), |
| 1673 nullptr, CODE_ENTRY_SLOT, | 1663 nullptr, CODE_ENTRY_SLOT, |
| 1674 code_entry_slot); | 1664 code_entry_slot); |
| 1675 } | 1665 } |
| 1676 } | 1666 } |
| 1677 | 1667 |
| 1678 inline void VisitCodeTarget(RelocInfo* rinfo) final { | 1668 inline void VisitCodeTarget(Code* host, RelocInfo* rinfo) final { |
| 1669 DCHECK_EQ(host, rinfo->host()); |
| 1679 DCHECK(RelocInfo::IsCodeTarget(rinfo->rmode())); | 1670 DCHECK(RelocInfo::IsCodeTarget(rinfo->rmode())); |
| 1680 Code* target = Code::GetCodeFromTargetAddress(rinfo->target_address()); | 1671 Code* target = Code::GetCodeFromTargetAddress(rinfo->target_address()); |
| 1681 Code* host = rinfo->host(); | |
| 1682 // The target is always in old space, we don't have to record the slot in | 1672 // The target is always in old space, we don't have to record the slot in |
| 1683 // the old-to-new remembered set. | 1673 // the old-to-new remembered set. |
| 1684 DCHECK(!collector_->heap()->InNewSpace(target)); | 1674 DCHECK(!collector_->heap()->InNewSpace(target)); |
| 1685 collector_->RecordRelocSlot(host, rinfo, target); | 1675 collector_->RecordRelocSlot(host, rinfo, target); |
| 1686 } | 1676 } |
| 1687 | 1677 |
| 1688 inline void VisitDebugTarget(RelocInfo* rinfo) final { | 1678 inline void VisitDebugTarget(Code* host, RelocInfo* rinfo) final { |
| 1679 DCHECK_EQ(host, rinfo->host()); |
| 1689 DCHECK(RelocInfo::IsDebugBreakSlot(rinfo->rmode()) && | 1680 DCHECK(RelocInfo::IsDebugBreakSlot(rinfo->rmode()) && |
| 1690 rinfo->IsPatchedDebugBreakSlotSequence()); | 1681 rinfo->IsPatchedDebugBreakSlotSequence()); |
| 1691 Code* target = Code::GetCodeFromTargetAddress(rinfo->debug_call_address()); | 1682 Code* target = Code::GetCodeFromTargetAddress(rinfo->debug_call_address()); |
| 1692 Code* host = rinfo->host(); | |
| 1693 // The target is always in old space, we don't have to record the slot in | 1683 // The target is always in old space, we don't have to record the slot in |
| 1694 // the old-to-new remembered set. | 1684 // the old-to-new remembered set. |
| 1695 DCHECK(!collector_->heap()->InNewSpace(target)); | 1685 DCHECK(!collector_->heap()->InNewSpace(target)); |
| 1696 collector_->RecordRelocSlot(host, rinfo, target); | 1686 collector_->RecordRelocSlot(host, rinfo, target); |
| 1697 } | 1687 } |
| 1698 | 1688 |
| 1699 inline void VisitEmbeddedPointer(RelocInfo* rinfo) final { | 1689 inline void VisitEmbeddedPointer(Code* host, RelocInfo* rinfo) final { |
| 1690 DCHECK_EQ(host, rinfo->host()); |
| 1700 DCHECK(rinfo->rmode() == RelocInfo::EMBEDDED_OBJECT); | 1691 DCHECK(rinfo->rmode() == RelocInfo::EMBEDDED_OBJECT); |
| 1701 HeapObject* object = HeapObject::cast(rinfo->target_object()); | 1692 HeapObject* object = HeapObject::cast(rinfo->target_object()); |
| 1702 Code* host = rinfo->host(); | |
| 1703 collector_->heap()->RecordWriteIntoCode(host, rinfo, object); | 1693 collector_->heap()->RecordWriteIntoCode(host, rinfo, object); |
| 1704 collector_->RecordRelocSlot(host, rinfo, object); | 1694 collector_->RecordRelocSlot(host, rinfo, object); |
| 1705 } | 1695 } |
| 1706 | 1696 |
| 1707 inline void VisitCell(RelocInfo* rinfo) final { | 1697 inline void VisitCell(Code* host, RelocInfo* rinfo) final { |
| 1698 DCHECK_EQ(host, rinfo->host()); |
| 1708 DCHECK(rinfo->rmode() == RelocInfo::CELL); | 1699 DCHECK(rinfo->rmode() == RelocInfo::CELL); |
| 1709 Cell* cell = rinfo->target_cell(); | 1700 Cell* cell = rinfo->target_cell(); |
| 1710 Code* host = rinfo->host(); | |
| 1711 // The cell is always in old space, we don't have to record the slot in | 1701 // The cell is always in old space, we don't have to record the slot in |
| 1712 // the old-to-new remembered set. | 1702 // the old-to-new remembered set. |
| 1713 DCHECK(!collector_->heap()->InNewSpace(cell)); | 1703 DCHECK(!collector_->heap()->InNewSpace(cell)); |
| 1714 collector_->RecordRelocSlot(host, rinfo, cell); | 1704 collector_->RecordRelocSlot(host, rinfo, cell); |
| 1715 } | 1705 } |
| 1716 | 1706 |
| 1717 // Entries that will never move. | 1707 // Entries that will never move. |
| 1718 inline void VisitCodeAgeSequence(RelocInfo* rinfo) final { | 1708 inline void VisitCodeAgeSequence(Code* host, RelocInfo* rinfo) final { |
| 1709 DCHECK_EQ(host, rinfo->host()); |
| 1719 DCHECK(RelocInfo::IsCodeAgeSequence(rinfo->rmode())); | 1710 DCHECK(RelocInfo::IsCodeAgeSequence(rinfo->rmode())); |
| 1720 Code* stub = rinfo->code_age_stub(); | 1711 Code* stub = rinfo->code_age_stub(); |
| 1721 USE(stub); | 1712 USE(stub); |
| 1722 DCHECK(!Page::FromAddress(stub->address())->IsEvacuationCandidate()); | 1713 DCHECK(!Page::FromAddress(stub->address())->IsEvacuationCandidate()); |
| 1723 } | 1714 } |
| 1724 | 1715 |
| 1725 // Entries that are skipped for recording. | 1716 // Entries that are skipped for recording. |
| 1726 inline void VisitExternalReference(RelocInfo* rinfo) final {} | 1717 inline void VisitExternalReference(Code* host, RelocInfo* rinfo) final {} |
| 1727 inline void VisitExternalReference(Address* p) final {} | 1718 inline void VisitExternalReference(Foreign* host, Address* p) final {} |
| 1728 inline void VisitRuntimeEntry(RelocInfo* rinfo) final {} | 1719 inline void VisitRuntimeEntry(Code* host, RelocInfo* rinfo) final {} |
| 1729 inline void VisitInternalReference(RelocInfo* rinfo) final {} | 1720 inline void VisitInternalReference(Code* host, RelocInfo* rinfo) final {} |
| 1730 | 1721 |
| 1731 private: | 1722 private: |
| 1732 inline void RecordMigratedSlot(Object* value, Address slot) { | 1723 inline void RecordMigratedSlot(Object* value, Address slot) { |
| 1733 if (value->IsHeapObject()) { | 1724 if (value->IsHeapObject()) { |
| 1734 Page* p = Page::FromAddress(reinterpret_cast<Address>(value)); | 1725 Page* p = Page::FromAddress(reinterpret_cast<Address>(value)); |
| 1735 if (p->InNewSpace()) { | 1726 if (p->InNewSpace()) { |
| 1736 RememberedSet<OLD_TO_NEW>::Insert(Page::FromAddress(slot), slot); | 1727 RememberedSet<OLD_TO_NEW>::Insert(Page::FromAddress(slot), slot); |
| 1737 } else if (p->IsEvacuationCandidate()) { | 1728 } else if (p->IsEvacuationCandidate()) { |
| 1738 RememberedSet<OLD_TO_OLD>::Insert(Page::FromAddress(slot), slot); | 1729 RememberedSet<OLD_TO_OLD>::Insert(Page::FromAddress(slot), slot); |
| 1739 } | 1730 } |
| (...skipping 1333 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3073 } | 3064 } |
| 3074 return REMOVE_SLOT; | 3065 return REMOVE_SLOT; |
| 3075 } | 3066 } |
| 3076 | 3067 |
| 3077 // Visitor for updating root pointers and to-space pointers. | 3068 // Visitor for updating root pointers and to-space pointers. |
| 3078 // It does not expect to encounter pointers to dead objects. | 3069 // It does not expect to encounter pointers to dead objects. |
| 3079 // TODO(ulan): Remove code object specific functions. This visitor | 3070 // TODO(ulan): Remove code object specific functions. This visitor |
| 3080 // nevers visits code objects. | 3071 // nevers visits code objects. |
| 3081 class PointersUpdatingVisitor : public ObjectVisitor, public RootVisitor { | 3072 class PointersUpdatingVisitor : public ObjectVisitor, public RootVisitor { |
| 3082 public: | 3073 public: |
| 3083 void VisitPointer(Object** p) override { UpdateSlot(p); } | 3074 void VisitPointer(HeapObject* host, Object** p) override { UpdateSlot(p); } |
| 3084 | 3075 |
| 3085 void VisitPointers(Object** start, Object** end) override { | 3076 void VisitPointers(HeapObject* host, Object** start, Object** end) override { |
| 3086 for (Object** p = start; p < end; p++) UpdateSlot(p); | 3077 for (Object** p = start; p < end; p++) UpdateSlot(p); |
| 3087 } | 3078 } |
| 3088 | 3079 |
| 3089 void VisitRootPointer(Root root, Object** p) override { UpdateSlot(p); } | 3080 void VisitRootPointer(Root root, Object** p) override { UpdateSlot(p); } |
| 3090 | 3081 |
| 3091 void VisitRootPointers(Root root, Object** start, Object** end) override { | 3082 void VisitRootPointers(Root root, Object** start, Object** end) override { |
| 3092 for (Object** p = start; p < end; p++) UpdateSlot(p); | 3083 for (Object** p = start; p < end; p++) UpdateSlot(p); |
| 3093 } | 3084 } |
| 3094 | 3085 |
| 3095 void VisitCell(RelocInfo* rinfo) override { | 3086 void VisitCell(Code* host, RelocInfo* rinfo) override { |
| 3096 UpdateTypedSlotHelper::UpdateCell(rinfo, UpdateSlot); | 3087 UpdateTypedSlotHelper::UpdateCell(rinfo, UpdateSlot); |
| 3097 } | 3088 } |
| 3098 | 3089 |
| 3099 void VisitEmbeddedPointer(RelocInfo* rinfo) override { | 3090 void VisitEmbeddedPointer(Code* host, RelocInfo* rinfo) override { |
| 3100 UpdateTypedSlotHelper::UpdateEmbeddedPointer(rinfo, UpdateSlot); | 3091 UpdateTypedSlotHelper::UpdateEmbeddedPointer(rinfo, UpdateSlot); |
| 3101 } | 3092 } |
| 3102 | 3093 |
| 3103 void VisitCodeTarget(RelocInfo* rinfo) override { | 3094 void VisitCodeTarget(Code* host, RelocInfo* rinfo) override { |
| 3104 UpdateTypedSlotHelper::UpdateCodeTarget(rinfo, UpdateSlot); | 3095 UpdateTypedSlotHelper::UpdateCodeTarget(rinfo, UpdateSlot); |
| 3105 } | 3096 } |
| 3106 | 3097 |
| 3107 void VisitCodeEntry(Address entry_address) override { | 3098 void VisitCodeEntry(JSFunction* host, Address entry_address) override { |
| 3108 UpdateTypedSlotHelper::UpdateCodeEntry(entry_address, UpdateSlot); | 3099 UpdateTypedSlotHelper::UpdateCodeEntry(entry_address, UpdateSlot); |
| 3109 } | 3100 } |
| 3110 | 3101 |
| 3111 void VisitDebugTarget(RelocInfo* rinfo) override { | 3102 void VisitDebugTarget(Code* host, RelocInfo* rinfo) override { |
| 3112 UpdateTypedSlotHelper::UpdateDebugTarget(rinfo, UpdateSlot); | 3103 UpdateTypedSlotHelper::UpdateDebugTarget(rinfo, UpdateSlot); |
| 3113 } | 3104 } |
| 3114 }; | 3105 }; |
| 3115 | 3106 |
| 3116 static String* UpdateReferenceInExternalStringTableEntry(Heap* heap, | 3107 static String* UpdateReferenceInExternalStringTableEntry(Heap* heap, |
| 3117 Object** p) { | 3108 Object** p) { |
| 3118 MapWord map_word = HeapObject::cast(*p)->map_word(); | 3109 MapWord map_word = HeapObject::cast(*p)->map_word(); |
| 3119 | 3110 |
| 3120 if (map_word.IsForwardingAddress()) { | 3111 if (map_word.IsForwardingAddress()) { |
| 3121 return String::cast(map_word.ToForwardingAddress()); | 3112 return String::cast(map_word.ToForwardingAddress()); |
| (...skipping 1099 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4221 // The target is always in old space, we don't have to record the slot in | 4212 // The target is always in old space, we don't have to record the slot in |
| 4222 // the old-to-new remembered set. | 4213 // the old-to-new remembered set. |
| 4223 DCHECK(!heap()->InNewSpace(target)); | 4214 DCHECK(!heap()->InNewSpace(target)); |
| 4224 RecordRelocSlot(host, &rinfo, target); | 4215 RecordRelocSlot(host, &rinfo, target); |
| 4225 } | 4216 } |
| 4226 } | 4217 } |
| 4227 } | 4218 } |
| 4228 | 4219 |
| 4229 } // namespace internal | 4220 } // namespace internal |
| 4230 } // namespace v8 | 4221 } // namespace v8 |
| OLD | NEW |