Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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/spaces.h" | 5 #include "src/heap/spaces.h" |
| 6 | 6 |
| 7 #include "src/base/bits.h" | 7 #include "src/base/bits.h" |
| 8 #include "src/base/platform/platform.h" | 8 #include "src/base/platform/platform.h" |
| 9 #include "src/full-codegen/full-codegen.h" | 9 #include "src/full-codegen/full-codegen.h" |
| 10 #include "src/heap/slots-buffer.h" | 10 #include "src/heap/slots-buffer.h" |
| (...skipping 1294 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1305 to_space_.SetUp(chunk_base_, initial_semispace_capacity, | 1305 to_space_.SetUp(chunk_base_, initial_semispace_capacity, |
| 1306 maximum_semispace_capacity); | 1306 maximum_semispace_capacity); |
| 1307 from_space_.SetUp(chunk_base_ + reserved_semispace_capacity, | 1307 from_space_.SetUp(chunk_base_ + reserved_semispace_capacity, |
| 1308 initial_semispace_capacity, maximum_semispace_capacity); | 1308 initial_semispace_capacity, maximum_semispace_capacity); |
| 1309 if (!to_space_.Commit()) { | 1309 if (!to_space_.Commit()) { |
| 1310 return false; | 1310 return false; |
| 1311 } | 1311 } |
| 1312 DCHECK(!from_space_.is_committed()); // No need to use memory yet. | 1312 DCHECK(!from_space_.is_committed()); // No need to use memory yet. |
| 1313 | 1313 |
| 1314 start_ = chunk_base_; | 1314 start_ = chunk_base_; |
| 1315 address_mask_ = ~(2 * reserved_semispace_capacity - 1); | |
| 1316 object_mask_ = address_mask_ | kHeapObjectTagMask; | |
| 1317 object_expected_ = reinterpret_cast<uintptr_t>(start_) | kHeapObjectTag; | |
| 1318 | 1315 |
| 1319 ResetAllocationInfo(); | 1316 ResetAllocationInfo(); |
| 1320 | 1317 |
| 1321 return true; | 1318 return true; |
| 1322 } | 1319 } |
| 1323 | 1320 |
| 1324 | 1321 |
| 1325 void NewSpace::TearDown() { | 1322 void NewSpace::TearDown() { |
| 1326 if (allocated_histogram_) { | 1323 if (allocated_histogram_) { |
| 1327 DeleteArray(allocated_histogram_); | 1324 DeleteArray(allocated_histogram_); |
| (...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1668 // SemiSpace implementation | 1665 // SemiSpace implementation |
| 1669 | 1666 |
| 1670 void SemiSpace::SetUp(Address start, int initial_capacity, | 1667 void SemiSpace::SetUp(Address start, int initial_capacity, |
| 1671 int maximum_capacity) { | 1668 int maximum_capacity) { |
| 1672 DCHECK_GE(maximum_capacity, Page::kPageSize); | 1669 DCHECK_GE(maximum_capacity, Page::kPageSize); |
| 1673 minimum_capacity_ = RoundDown(initial_capacity, Page::kPageSize); | 1670 minimum_capacity_ = RoundDown(initial_capacity, Page::kPageSize); |
| 1674 current_capacity_ = minimum_capacity_; | 1671 current_capacity_ = minimum_capacity_; |
| 1675 maximum_capacity_ = RoundDown(maximum_capacity, Page::kPageSize); | 1672 maximum_capacity_ = RoundDown(maximum_capacity, Page::kPageSize); |
| 1676 committed_ = false; | 1673 committed_ = false; |
| 1677 start_ = start; | 1674 start_ = start; |
| 1678 address_mask_ = ~(maximum_capacity_ - 1); | |
| 1679 object_mask_ = address_mask_ | kHeapObjectTagMask; | |
| 1680 object_expected_ = reinterpret_cast<uintptr_t>(start) | kHeapObjectTag; | |
| 1681 age_mark_ = start_ + NewSpacePage::kObjectStartOffset; | 1675 age_mark_ = start_ + NewSpacePage::kObjectStartOffset; |
| 1682 } | 1676 } |
| 1683 | 1677 |
| 1684 | 1678 |
| 1685 void SemiSpace::TearDown() { | 1679 void SemiSpace::TearDown() { |
| 1686 start_ = nullptr; | 1680 start_ = nullptr; |
| 1687 current_capacity_ = 0; | 1681 current_capacity_ = 0; |
| 1688 } | 1682 } |
| 1689 | 1683 |
| 1690 | 1684 |
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1796 new_last_page->set_next_page(anchor()); | 1790 new_last_page->set_next_page(anchor()); |
| 1797 anchor()->set_prev_page(new_last_page); | 1791 anchor()->set_prev_page(new_last_page); |
| 1798 DCHECK((current_page_ >= first_page()) && (current_page_ <= new_last_page)); | 1792 DCHECK((current_page_ >= first_page()) && (current_page_ <= new_last_page)); |
| 1799 } | 1793 } |
| 1800 | 1794 |
| 1801 set_current_capacity(new_capacity); | 1795 set_current_capacity(new_capacity); |
| 1802 | 1796 |
| 1803 return true; | 1797 return true; |
| 1804 } | 1798 } |
| 1805 | 1799 |
| 1806 | 1800 void SemiSpace::FixPages(intptr_t flags, intptr_t mask) { |
|
Hannes Payer (out of office)
2016/02/08 16:05:40
FixPagesFlags?
Michael Lippautz
2016/02/08 18:00:38
Done.
| |
| 1807 void SemiSpace::FlipPages(intptr_t flags, intptr_t mask) { | |
| 1808 anchor_.set_owner(this); | 1801 anchor_.set_owner(this); |
| 1809 // Fixup back-pointers to anchor. Address of anchor changes when we swap. | 1802 // Fixup back-pointers to anchor. Address of anchor changes when we swap. |
| 1810 anchor_.prev_page()->set_next_page(&anchor_); | 1803 anchor_.prev_page()->set_next_page(&anchor_); |
| 1811 anchor_.next_page()->set_prev_page(&anchor_); | 1804 anchor_.next_page()->set_prev_page(&anchor_); |
| 1812 | 1805 |
| 1813 bool becomes_to_space = (id_ == kFromSpace); | |
| 1814 id_ = becomes_to_space ? kToSpace : kFromSpace; | |
| 1815 NewSpacePageIterator it(this); | 1806 NewSpacePageIterator it(this); |
| 1816 while (it.has_next()) { | 1807 while (it.has_next()) { |
| 1817 NewSpacePage* page = it.next(); | 1808 NewSpacePage* page = it.next(); |
| 1818 page->set_owner(this); | 1809 page->set_owner(this); |
| 1819 page->SetFlags(flags, mask); | 1810 page->SetFlags(flags, mask); |
| 1820 if (becomes_to_space) { | 1811 if (id_ == kToSpace) { |
| 1821 page->ClearFlag(MemoryChunk::IN_FROM_SPACE); | 1812 page->ClearFlag(MemoryChunk::IN_FROM_SPACE); |
| 1822 page->SetFlag(MemoryChunk::IN_TO_SPACE); | 1813 page->SetFlag(MemoryChunk::IN_TO_SPACE); |
| 1823 page->ClearFlag(MemoryChunk::NEW_SPACE_BELOW_AGE_MARK); | 1814 page->ClearFlag(MemoryChunk::NEW_SPACE_BELOW_AGE_MARK); |
| 1824 page->ResetLiveBytes(); | 1815 page->ResetLiveBytes(); |
| 1825 } else { | 1816 } else { |
| 1826 page->SetFlag(MemoryChunk::IN_FROM_SPACE); | 1817 page->SetFlag(MemoryChunk::IN_FROM_SPACE); |
| 1827 page->ClearFlag(MemoryChunk::IN_TO_SPACE); | 1818 page->ClearFlag(MemoryChunk::IN_TO_SPACE); |
| 1828 } | 1819 } |
| 1829 DCHECK(page->IsFlagSet(MemoryChunk::SCAN_ON_SCAVENGE)); | 1820 DCHECK(page->IsFlagSet(MemoryChunk::SCAN_ON_SCAVENGE)); |
| 1830 DCHECK(page->IsFlagSet(MemoryChunk::IN_TO_SPACE) || | 1821 DCHECK(page->IsFlagSet(MemoryChunk::IN_TO_SPACE) || |
| 1831 page->IsFlagSet(MemoryChunk::IN_FROM_SPACE)); | 1822 page->IsFlagSet(MemoryChunk::IN_FROM_SPACE)); |
| 1832 } | 1823 } |
| 1833 } | 1824 } |
| 1834 | 1825 |
| 1835 | 1826 |
| 1836 void SemiSpace::Reset() { | 1827 void SemiSpace::Reset() { |
| 1837 DCHECK_NE(anchor_.next_page(), &anchor_); | 1828 DCHECK_NE(anchor_.next_page(), &anchor_); |
| 1838 current_page_ = anchor_.next_page(); | 1829 current_page_ = anchor_.next_page(); |
| 1839 } | 1830 } |
| 1840 | 1831 |
| 1841 | 1832 |
| 1842 void SemiSpace::Swap(SemiSpace* from, SemiSpace* to) { | 1833 void SemiSpace::Swap(SemiSpace* from, SemiSpace* to) { |
| 1843 // We won't be swapping semispaces without data in them. | 1834 // We won't be swapping semispaces without data in them. |
| 1844 DCHECK_NE(from->anchor_.next_page(), &from->anchor_); | 1835 DCHECK_NE(from->anchor_.next_page(), &from->anchor_); |
| 1845 DCHECK_NE(to->anchor_.next_page(), &to->anchor_); | 1836 DCHECK_NE(to->anchor_.next_page(), &to->anchor_); |
| 1846 | 1837 |
| 1847 // Swap bits. | 1838 intptr_t saved_to_space_flags = to->current_page()->GetFlags(); |
| 1848 SemiSpace tmp = *from; | |
|
Michael Lippautz
2016/02/05 12:44:40
Let's move this to explicit code (std::swap), to a
| |
| 1849 *from = *to; | |
| 1850 *to = tmp; | |
| 1851 | 1839 |
| 1852 // Fixup back-pointers to the page list anchor now that its address | 1840 // We swap all properties but id_. |
| 1853 // has changed. | 1841 std::swap(from->current_capacity_, to->current_capacity_); |
|
ulan
2016/02/09 13:36:50
Let's extract it into separate function and put it
Michael Lippautz
2016/02/09 14:50:28
As discussed offline: This is already Swap(), and
| |
| 1854 // Swap to/from-space bits on pages. | 1842 std::swap(from->maximum_capacity_, to->maximum_capacity_); |
| 1855 // Copy GC flags from old active space (from-space) to new (to-space). | 1843 std::swap(from->minimum_capacity_, to->minimum_capacity_); |
| 1856 intptr_t flags = from->current_page()->GetFlags(); | 1844 std::swap(from->start_, to->start_); |
| 1857 to->FlipPages(flags, NewSpacePage::kCopyOnFlipFlagsMask); | 1845 std::swap(from->age_mark_, to->age_mark_); |
| 1846 std::swap(from->committed_, to->committed_); | |
| 1847 std::swap(from->anchor_, to->anchor_); | |
| 1848 std::swap(from->current_page_, to->current_page_); | |
| 1858 | 1849 |
| 1859 from->FlipPages(0, 0); | 1850 to->FixPages(saved_to_space_flags, NewSpacePage::kCopyOnFlipFlagsMask); |
| 1851 from->FixPages(0, 0); | |
| 1860 } | 1852 } |
| 1861 | 1853 |
| 1862 | 1854 |
| 1863 void SemiSpace::set_age_mark(Address mark) { | 1855 void SemiSpace::set_age_mark(Address mark) { |
| 1864 DCHECK_EQ(NewSpacePage::FromLimit(mark)->semi_space(), this); | 1856 DCHECK_EQ(NewSpacePage::FromLimit(mark)->semi_space(), this); |
| 1865 age_mark_ = mark; | 1857 age_mark_ = mark; |
| 1866 // Mark all pages up to the one containing mark. | 1858 // Mark all pages up to the one containing mark. |
| 1867 NewSpacePageIterator it(space_start(), mark); | 1859 NewSpacePageIterator it(space_start(), mark); |
| 1868 while (it.has_next()) { | 1860 while (it.has_next()) { |
| 1869 it.next()->SetFlag(MemoryChunk::NEW_SPACE_BELOW_AGE_MARK); | 1861 it.next()->SetFlag(MemoryChunk::NEW_SPACE_BELOW_AGE_MARK); |
| (...skipping 1368 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3238 object->ShortPrint(); | 3230 object->ShortPrint(); |
| 3239 PrintF("\n"); | 3231 PrintF("\n"); |
| 3240 } | 3232 } |
| 3241 printf(" --------------------------------------\n"); | 3233 printf(" --------------------------------------\n"); |
| 3242 printf(" Marked: %x, LiveCount: %x\n", mark_size, LiveBytes()); | 3234 printf(" Marked: %x, LiveCount: %x\n", mark_size, LiveBytes()); |
| 3243 } | 3235 } |
| 3244 | 3236 |
| 3245 #endif // DEBUG | 3237 #endif // DEBUG |
| 3246 } // namespace internal | 3238 } // namespace internal |
| 3247 } // namespace v8 | 3239 } // namespace v8 |
| OLD | NEW |