OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 1727 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1738 | 1738 |
1739 bool MarkCompactCollector::IsUnmarkedHeapObject(Object** p) { | 1739 bool MarkCompactCollector::IsUnmarkedHeapObject(Object** p) { |
1740 Object* o = *p; | 1740 Object* o = *p; |
1741 if (!o->IsHeapObject()) return false; | 1741 if (!o->IsHeapObject()) return false; |
1742 HeapObject* heap_object = HeapObject::cast(o); | 1742 HeapObject* heap_object = HeapObject::cast(o); |
1743 MarkBit mark = Marking::MarkBitFrom(heap_object); | 1743 MarkBit mark = Marking::MarkBitFrom(heap_object); |
1744 return !mark.Get(); | 1744 return !mark.Get(); |
1745 } | 1745 } |
1746 | 1746 |
1747 | 1747 |
| 1748 bool MarkCompactCollector::IsUnmarkedHeapObjectWithHeap(Heap* heap, |
| 1749 Object** p) { |
| 1750 Object* o = *p; |
| 1751 ASSERT(o->IsHeapObject()); |
| 1752 HeapObject* heap_object = HeapObject::cast(o); |
| 1753 MarkBit mark = Marking::MarkBitFrom(heap_object); |
| 1754 return !mark.Get(); |
| 1755 } |
| 1756 |
| 1757 |
1748 void MarkCompactCollector::MarkSymbolTable() { | 1758 void MarkCompactCollector::MarkSymbolTable() { |
1749 SymbolTable* symbol_table = heap()->symbol_table(); | 1759 SymbolTable* symbol_table = heap()->symbol_table(); |
1750 // Mark the symbol table itself. | 1760 // Mark the symbol table itself. |
1751 MarkBit symbol_table_mark = Marking::MarkBitFrom(symbol_table); | 1761 MarkBit symbol_table_mark = Marking::MarkBitFrom(symbol_table); |
1752 SetMark(symbol_table, symbol_table_mark); | 1762 SetMark(symbol_table, symbol_table_mark); |
1753 // Explicitly mark the prefix. | 1763 // Explicitly mark the prefix. |
1754 MarkingVisitor marker(heap()); | 1764 MarkingVisitor marker(heap()); |
1755 symbol_table->IteratePrefix(&marker); | 1765 symbol_table->IteratePrefix(&marker); |
1756 ProcessMarkingDeque(); | 1766 ProcessMarkingDeque(); |
1757 } | 1767 } |
1758 | 1768 |
1759 | 1769 |
1760 void MarkCompactCollector::MarkRoots(RootMarkingVisitor* visitor) { | 1770 void MarkCompactCollector::MarkRoots(RootMarkingVisitor* visitor) { |
1761 // Mark the heap roots including global variables, stack variables, | 1771 // Mark the heap roots including global variables, stack variables, |
1762 // etc., and all objects reachable from them. | 1772 // etc., and all objects reachable from them. |
1763 heap()->IterateStrongRoots(visitor, VISIT_ONLY_STRONG); | 1773 heap()->IterateStrongRoots(visitor, VISIT_ONLY_STRONG); |
1764 | 1774 |
1765 // Handle the symbol table specially. | 1775 // Handle the symbol table specially. |
1766 MarkSymbolTable(); | 1776 MarkSymbolTable(); |
1767 | 1777 |
1768 // There may be overflowed objects in the heap. Visit them now. | 1778 // There may be overflowed objects in the heap. Visit them now. |
1769 while (marking_deque_.overflowed()) { | 1779 while (marking_deque_.overflowed()) { |
1770 RefillMarkingDeque(); | 1780 RefillMarkingDeque(); |
1771 EmptyMarkingDeque(); | 1781 EmptyMarkingDeque(); |
1772 } | 1782 } |
1773 } | 1783 } |
1774 | 1784 |
1775 | 1785 |
1776 void MarkCompactCollector::MarkObjectGroups() { | |
1777 List<ObjectGroup*>* object_groups = | |
1778 heap()->isolate()->global_handles()->object_groups(); | |
1779 | |
1780 int last = 0; | |
1781 for (int i = 0; i < object_groups->length(); i++) { | |
1782 ObjectGroup* entry = object_groups->at(i); | |
1783 ASSERT(entry != NULL); | |
1784 | |
1785 Object*** objects = entry->objects_; | |
1786 bool group_marked = false; | |
1787 for (size_t j = 0; j < entry->length_; j++) { | |
1788 Object* object = *objects[j]; | |
1789 if (object->IsHeapObject()) { | |
1790 HeapObject* heap_object = HeapObject::cast(object); | |
1791 MarkBit mark = Marking::MarkBitFrom(heap_object); | |
1792 if (mark.Get()) { | |
1793 group_marked = true; | |
1794 break; | |
1795 } | |
1796 } | |
1797 } | |
1798 | |
1799 if (!group_marked) { | |
1800 (*object_groups)[last++] = entry; | |
1801 continue; | |
1802 } | |
1803 | |
1804 // An object in the group is marked, so mark as grey all white heap | |
1805 // objects in the group. | |
1806 for (size_t j = 0; j < entry->length_; ++j) { | |
1807 Object* object = *objects[j]; | |
1808 if (object->IsHeapObject()) { | |
1809 HeapObject* heap_object = HeapObject::cast(object); | |
1810 MarkBit mark = Marking::MarkBitFrom(heap_object); | |
1811 MarkObject(heap_object, mark); | |
1812 } | |
1813 } | |
1814 | |
1815 // Once the entire group has been colored grey, set the object group | |
1816 // to NULL so it won't be processed again. | |
1817 entry->Dispose(); | |
1818 object_groups->at(i) = NULL; | |
1819 } | |
1820 object_groups->Rewind(last); | |
1821 } | |
1822 | |
1823 | |
1824 void MarkCompactCollector::MarkImplicitRefGroups() { | 1786 void MarkCompactCollector::MarkImplicitRefGroups() { |
1825 List<ImplicitRefGroup*>* ref_groups = | 1787 List<ImplicitRefGroup*>* ref_groups = |
1826 heap()->isolate()->global_handles()->implicit_ref_groups(); | 1788 heap()->isolate()->global_handles()->implicit_ref_groups(); |
1827 | 1789 |
1828 int last = 0; | 1790 int last = 0; |
1829 for (int i = 0; i < ref_groups->length(); i++) { | 1791 for (int i = 0; i < ref_groups->length(); i++) { |
1830 ImplicitRefGroup* entry = ref_groups->at(i); | 1792 ImplicitRefGroup* entry = ref_groups->at(i); |
1831 ASSERT(entry != NULL); | 1793 ASSERT(entry != NULL); |
1832 | 1794 |
1833 if (!IsMarked(*entry->parent_)) { | 1795 if (!IsMarked(*entry->parent_)) { |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1932 // objects in the heap. | 1894 // objects in the heap. |
1933 void MarkCompactCollector::ProcessMarkingDeque() { | 1895 void MarkCompactCollector::ProcessMarkingDeque() { |
1934 EmptyMarkingDeque(); | 1896 EmptyMarkingDeque(); |
1935 while (marking_deque_.overflowed()) { | 1897 while (marking_deque_.overflowed()) { |
1936 RefillMarkingDeque(); | 1898 RefillMarkingDeque(); |
1937 EmptyMarkingDeque(); | 1899 EmptyMarkingDeque(); |
1938 } | 1900 } |
1939 } | 1901 } |
1940 | 1902 |
1941 | 1903 |
1942 void MarkCompactCollector::ProcessExternalMarking() { | 1904 void MarkCompactCollector::ProcessExternalMarking(RootMarkingVisitor* visitor) { |
1943 bool work_to_do = true; | 1905 bool work_to_do = true; |
1944 ASSERT(marking_deque_.IsEmpty()); | 1906 ASSERT(marking_deque_.IsEmpty()); |
1945 while (work_to_do) { | 1907 while (work_to_do) { |
1946 MarkObjectGroups(); | 1908 heap()->isolate()->global_handles()->IterateObjectGroups( |
| 1909 visitor, &IsUnmarkedHeapObjectWithHeap); |
1947 MarkImplicitRefGroups(); | 1910 MarkImplicitRefGroups(); |
1948 work_to_do = !marking_deque_.IsEmpty(); | 1911 work_to_do = !marking_deque_.IsEmpty(); |
1949 ProcessMarkingDeque(); | 1912 ProcessMarkingDeque(); |
1950 } | 1913 } |
1951 } | 1914 } |
1952 | 1915 |
1953 | 1916 |
1954 void MarkCompactCollector::MarkLiveObjects() { | 1917 void MarkCompactCollector::MarkLiveObjects() { |
1955 GCTracer::Scope gc_scope(tracer_, GCTracer::Scope::MC_MARK); | 1918 GCTracer::Scope gc_scope(tracer_, GCTracer::Scope::MC_MARK); |
1956 // The recursive GC marker detects when it is nearing stack overflow, | 1919 // The recursive GC marker detects when it is nearing stack overflow, |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2015 } | 1978 } |
2016 } | 1979 } |
2017 } | 1980 } |
2018 | 1981 |
2019 RootMarkingVisitor root_visitor(heap()); | 1982 RootMarkingVisitor root_visitor(heap()); |
2020 MarkRoots(&root_visitor); | 1983 MarkRoots(&root_visitor); |
2021 | 1984 |
2022 // The objects reachable from the roots are marked, yet unreachable | 1985 // The objects reachable from the roots are marked, yet unreachable |
2023 // objects are unmarked. Mark objects reachable due to host | 1986 // objects are unmarked. Mark objects reachable due to host |
2024 // application specific logic. | 1987 // application specific logic. |
2025 ProcessExternalMarking(); | 1988 ProcessExternalMarking(&root_visitor); |
2026 | 1989 |
2027 // The objects reachable from the roots or object groups are marked, | 1990 // The objects reachable from the roots or object groups are marked, |
2028 // yet unreachable objects are unmarked. Mark objects reachable | 1991 // yet unreachable objects are unmarked. Mark objects reachable |
2029 // only from weak global handles. | 1992 // only from weak global handles. |
2030 // | 1993 // |
2031 // First we identify nonlive weak handles and mark them as pending | 1994 // First we identify nonlive weak handles and mark them as pending |
2032 // destruction. | 1995 // destruction. |
2033 heap()->isolate()->global_handles()->IdentifyWeakHandles( | 1996 heap()->isolate()->global_handles()->IdentifyWeakHandles( |
2034 &IsUnmarkedHeapObject); | 1997 &IsUnmarkedHeapObject); |
2035 // Then we mark the objects and process the transitive closure. | 1998 // Then we mark the objects and process the transitive closure. |
2036 heap()->isolate()->global_handles()->IterateWeakRoots(&root_visitor); | 1999 heap()->isolate()->global_handles()->IterateWeakRoots(&root_visitor); |
2037 while (marking_deque_.overflowed()) { | 2000 while (marking_deque_.overflowed()) { |
2038 RefillMarkingDeque(); | 2001 RefillMarkingDeque(); |
2039 EmptyMarkingDeque(); | 2002 EmptyMarkingDeque(); |
2040 } | 2003 } |
2041 | 2004 |
2042 // Repeat host application specific marking to mark unmarked objects | 2005 // Repeat host application specific marking to mark unmarked objects |
2043 // reachable from the weak roots. | 2006 // reachable from the weak roots. |
2044 ProcessExternalMarking(); | 2007 ProcessExternalMarking(&root_visitor); |
2045 | 2008 |
2046 AfterMarking(); | 2009 AfterMarking(); |
2047 } | 2010 } |
2048 | 2011 |
2049 | 2012 |
2050 void MarkCompactCollector::AfterMarking() { | 2013 void MarkCompactCollector::AfterMarking() { |
2051 // Object literal map caches reference symbols (cache keys) and maps | 2014 // Object literal map caches reference symbols (cache keys) and maps |
2052 // (cache values). At this point still useful maps have already been | 2015 // (cache values). At this point still useful maps have already been |
2053 // marked. Mark the keys for the alive values before we process the | 2016 // marked. Mark the keys for the alive values before we process the |
2054 // symbol table. | 2017 // symbol table. |
(...skipping 1790 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3845 while (buffer != NULL) { | 3808 while (buffer != NULL) { |
3846 SlotsBuffer* next_buffer = buffer->next(); | 3809 SlotsBuffer* next_buffer = buffer->next(); |
3847 DeallocateBuffer(buffer); | 3810 DeallocateBuffer(buffer); |
3848 buffer = next_buffer; | 3811 buffer = next_buffer; |
3849 } | 3812 } |
3850 *buffer_address = NULL; | 3813 *buffer_address = NULL; |
3851 } | 3814 } |
3852 | 3815 |
3853 | 3816 |
3854 } } // namespace v8::internal | 3817 } } // namespace v8::internal |
OLD | NEW |