| 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 1137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1148 | 1148 |
| 1149 MarkCompactCollector::~MarkCompactCollector() { | 1149 MarkCompactCollector::~MarkCompactCollector() { |
| 1150 if (code_flusher_ != NULL) { | 1150 if (code_flusher_ != NULL) { |
| 1151 delete code_flusher_; | 1151 delete code_flusher_; |
| 1152 code_flusher_ = NULL; | 1152 code_flusher_ = NULL; |
| 1153 } | 1153 } |
| 1154 } | 1154 } |
| 1155 | 1155 |
| 1156 | 1156 |
| 1157 static inline HeapObject* ShortCircuitConsString(Object** p) { | 1157 static inline HeapObject* ShortCircuitConsString(Object** p) { |
| 1158 // Optimization: If the heap object pointed to by p is a non-symbol | 1158 // Optimization: If the heap object pointed to by p is a non-internalized |
| 1159 // cons string whose right substring is HEAP->empty_string, update | 1159 // cons string whose right substring is HEAP->empty_string, update |
| 1160 // it in place to its left substring. Return the updated value. | 1160 // it in place to its left substring. Return the updated value. |
| 1161 // | 1161 // |
| 1162 // Here we assume that if we change *p, we replace it with a heap object | 1162 // Here we assume that if we change *p, we replace it with a heap object |
| 1163 // (i.e., the left substring of a cons string is always a heap object). | 1163 // (i.e., the left substring of a cons string is always a heap object). |
| 1164 // | 1164 // |
| 1165 // The check performed is: | 1165 // The check performed is: |
| 1166 // object->IsConsString() && !object->IsSymbol() && | 1166 // object->IsConsString() && !object->IsInternalizedString() && |
| 1167 // (ConsString::cast(object)->second() == HEAP->empty_string()) | 1167 // (ConsString::cast(object)->second() == HEAP->empty_string()) |
| 1168 // except the maps for the object and its possible substrings might be | 1168 // except the maps for the object and its possible substrings might be |
| 1169 // marked. | 1169 // marked. |
| 1170 HeapObject* object = HeapObject::cast(*p); | 1170 HeapObject* object = HeapObject::cast(*p); |
| 1171 if (!FLAG_clever_optimizations) return object; | 1171 if (!FLAG_clever_optimizations) return object; |
| 1172 Map* map = object->map(); | 1172 Map* map = object->map(); |
| 1173 InstanceType type = map->instance_type(); | 1173 InstanceType type = map->instance_type(); |
| 1174 if ((type & kShortcutTypeMask) != kShortcutTypeTag) return object; | 1174 if ((type & kShortcutTypeMask) != kShortcutTypeTag) return object; |
| 1175 | 1175 |
| 1176 Object* second = reinterpret_cast<ConsString*>(object)->unchecked_second(); | 1176 Object* second = reinterpret_cast<ConsString*>(object)->unchecked_second(); |
| (...skipping 356 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1533 }; | 1533 }; |
| 1534 | 1534 |
| 1535 | 1535 |
| 1536 template<> | 1536 template<> |
| 1537 class MarkCompactMarkingVisitor::ObjectStatsTracker< | 1537 class MarkCompactMarkingVisitor::ObjectStatsTracker< |
| 1538 MarkCompactMarkingVisitor::kVisitFixedArray> { | 1538 MarkCompactMarkingVisitor::kVisitFixedArray> { |
| 1539 public: | 1539 public: |
| 1540 static inline void Visit(Map* map, HeapObject* obj) { | 1540 static inline void Visit(Map* map, HeapObject* obj) { |
| 1541 Heap* heap = map->GetHeap(); | 1541 Heap* heap = map->GetHeap(); |
| 1542 FixedArray* fixed_array = FixedArray::cast(obj); | 1542 FixedArray* fixed_array = FixedArray::cast(obj); |
| 1543 if (fixed_array == heap->symbol_table()) { | 1543 if (fixed_array == heap->string_table()) { |
| 1544 heap->RecordObjectStats( | 1544 heap->RecordObjectStats( |
| 1545 FIXED_ARRAY_TYPE, | 1545 FIXED_ARRAY_TYPE, |
| 1546 SYMBOL_TABLE_SUB_TYPE, | 1546 STRING_TABLE_SUB_TYPE, |
| 1547 fixed_array->Size()); | 1547 fixed_array->Size()); |
| 1548 } | 1548 } |
| 1549 ObjectStatsVisitBase(kVisitFixedArray, map, obj); | 1549 ObjectStatsVisitBase(kVisitFixedArray, map, obj); |
| 1550 } | 1550 } |
| 1551 }; | 1551 }; |
| 1552 | 1552 |
| 1553 | 1553 |
| 1554 void MarkCompactMarkingVisitor::Initialize() { | 1554 void MarkCompactMarkingVisitor::Initialize() { |
| 1555 StaticMarkingVisitor<MarkCompactMarkingVisitor>::Initialize(); | 1555 StaticMarkingVisitor<MarkCompactMarkingVisitor>::Initialize(); |
| 1556 | 1556 |
| (...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1717 | 1717 |
| 1718 // Mark all the objects reachable from the map and body. May leave | 1718 // Mark all the objects reachable from the map and body. May leave |
| 1719 // overflowed objects in the heap. | 1719 // overflowed objects in the heap. |
| 1720 collector_->EmptyMarkingDeque(); | 1720 collector_->EmptyMarkingDeque(); |
| 1721 } | 1721 } |
| 1722 | 1722 |
| 1723 MarkCompactCollector* collector_; | 1723 MarkCompactCollector* collector_; |
| 1724 }; | 1724 }; |
| 1725 | 1725 |
| 1726 | 1726 |
| 1727 // Helper class for pruning the symbol table. | 1727 // Helper class for pruning the string table. |
| 1728 class SymbolTableCleaner : public ObjectVisitor { | 1728 class StringTableCleaner : public ObjectVisitor { |
| 1729 public: | 1729 public: |
| 1730 explicit SymbolTableCleaner(Heap* heap) | 1730 explicit StringTableCleaner(Heap* heap) |
| 1731 : heap_(heap), pointers_removed_(0) { } | 1731 : heap_(heap), pointers_removed_(0) { } |
| 1732 | 1732 |
| 1733 virtual void VisitPointers(Object** start, Object** end) { | 1733 virtual void VisitPointers(Object** start, Object** end) { |
| 1734 // Visit all HeapObject pointers in [start, end). | 1734 // Visit all HeapObject pointers in [start, end). |
| 1735 for (Object** p = start; p < end; p++) { | 1735 for (Object** p = start; p < end; p++) { |
| 1736 Object* o = *p; | 1736 Object* o = *p; |
| 1737 if (o->IsHeapObject() && | 1737 if (o->IsHeapObject() && |
| 1738 !Marking::MarkBitFrom(HeapObject::cast(o)).Get()) { | 1738 !Marking::MarkBitFrom(HeapObject::cast(o)).Get()) { |
| 1739 // Check if the symbol being pruned is an external symbol. We need to | 1739 // Check if the internalized string being pruned is external. We need to |
| 1740 // delete the associated external data as this symbol is going away. | 1740 // delete the associated external data as this string is going away. |
| 1741 | 1741 |
| 1742 // Since no objects have yet been moved we can safely access the map of | 1742 // Since no objects have yet been moved we can safely access the map of |
| 1743 // the object. | 1743 // the object. |
| 1744 if (o->IsExternalString()) { | 1744 if (o->IsExternalString()) { |
| 1745 heap_->FinalizeExternalString(String::cast(*p)); | 1745 heap_->FinalizeExternalString(String::cast(*p)); |
| 1746 } | 1746 } |
| 1747 // Set the entry to the_hole_value (as deleted). | 1747 // Set the entry to the_hole_value (as deleted). |
| 1748 *p = heap_->the_hole_value(); | 1748 *p = heap_->the_hole_value(); |
| 1749 pointers_removed_++; | 1749 pointers_removed_++; |
| 1750 } | 1750 } |
| (...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1890 bool MarkCompactCollector::IsUnmarkedHeapObjectWithHeap(Heap* heap, | 1890 bool MarkCompactCollector::IsUnmarkedHeapObjectWithHeap(Heap* heap, |
| 1891 Object** p) { | 1891 Object** p) { |
| 1892 Object* o = *p; | 1892 Object* o = *p; |
| 1893 ASSERT(o->IsHeapObject()); | 1893 ASSERT(o->IsHeapObject()); |
| 1894 HeapObject* heap_object = HeapObject::cast(o); | 1894 HeapObject* heap_object = HeapObject::cast(o); |
| 1895 MarkBit mark = Marking::MarkBitFrom(heap_object); | 1895 MarkBit mark = Marking::MarkBitFrom(heap_object); |
| 1896 return !mark.Get(); | 1896 return !mark.Get(); |
| 1897 } | 1897 } |
| 1898 | 1898 |
| 1899 | 1899 |
| 1900 void MarkCompactCollector::MarkSymbolTable() { | 1900 void MarkCompactCollector::MarkStringTable() { |
| 1901 SymbolTable* symbol_table = heap()->symbol_table(); | 1901 StringTable* string_table = heap()->string_table(); |
| 1902 // Mark the symbol table itself. | 1902 // Mark the string table itself. |
| 1903 MarkBit symbol_table_mark = Marking::MarkBitFrom(symbol_table); | 1903 MarkBit string_table_mark = Marking::MarkBitFrom(string_table); |
| 1904 SetMark(symbol_table, symbol_table_mark); | 1904 SetMark(string_table, string_table_mark); |
| 1905 // Explicitly mark the prefix. | 1905 // Explicitly mark the prefix. |
| 1906 MarkingVisitor marker(heap()); | 1906 MarkingVisitor marker(heap()); |
| 1907 symbol_table->IteratePrefix(&marker); | 1907 string_table->IteratePrefix(&marker); |
| 1908 ProcessMarkingDeque(); | 1908 ProcessMarkingDeque(); |
| 1909 } | 1909 } |
| 1910 | 1910 |
| 1911 | 1911 |
| 1912 void MarkCompactCollector::MarkRoots(RootMarkingVisitor* visitor) { | 1912 void MarkCompactCollector::MarkRoots(RootMarkingVisitor* visitor) { |
| 1913 // Mark the heap roots including global variables, stack variables, | 1913 // Mark the heap roots including global variables, stack variables, |
| 1914 // etc., and all objects reachable from them. | 1914 // etc., and all objects reachable from them. |
| 1915 heap()->IterateStrongRoots(visitor, VISIT_ONLY_STRONG); | 1915 heap()->IterateStrongRoots(visitor, VISIT_ONLY_STRONG); |
| 1916 | 1916 |
| 1917 // Handle the symbol table specially. | 1917 // Handle the string table specially. |
| 1918 MarkSymbolTable(); | 1918 MarkStringTable(); |
| 1919 | 1919 |
| 1920 // There may be overflowed objects in the heap. Visit them now. | 1920 // There may be overflowed objects in the heap. Visit them now. |
| 1921 while (marking_deque_.overflowed()) { | 1921 while (marking_deque_.overflowed()) { |
| 1922 RefillMarkingDeque(); | 1922 RefillMarkingDeque(); |
| 1923 EmptyMarkingDeque(); | 1923 EmptyMarkingDeque(); |
| 1924 } | 1924 } |
| 1925 } | 1925 } |
| 1926 | 1926 |
| 1927 | 1927 |
| 1928 void MarkCompactCollector::MarkImplicitRefGroups() { | 1928 void MarkCompactCollector::MarkImplicitRefGroups() { |
| (...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2146 | 2146 |
| 2147 // Repeat host application specific marking to mark unmarked objects | 2147 // Repeat host application specific marking to mark unmarked objects |
| 2148 // reachable from the weak roots. | 2148 // reachable from the weak roots. |
| 2149 ProcessExternalMarking(&root_visitor); | 2149 ProcessExternalMarking(&root_visitor); |
| 2150 | 2150 |
| 2151 AfterMarking(); | 2151 AfterMarking(); |
| 2152 } | 2152 } |
| 2153 | 2153 |
| 2154 | 2154 |
| 2155 void MarkCompactCollector::AfterMarking() { | 2155 void MarkCompactCollector::AfterMarking() { |
| 2156 // Object literal map caches reference symbols (cache keys) and maps | 2156 // Object literal map caches reference strings (cache keys) and maps |
| 2157 // (cache values). At this point still useful maps have already been | 2157 // (cache values). At this point still useful maps have already been |
| 2158 // marked. Mark the keys for the alive values before we process the | 2158 // marked. Mark the keys for the alive values before we process the |
| 2159 // symbol table. | 2159 // string table. |
| 2160 ProcessMapCaches(); | 2160 ProcessMapCaches(); |
| 2161 | 2161 |
| 2162 // Prune the symbol table removing all symbols only pointed to by the | 2162 // Prune the string table removing all strings only pointed to by the |
| 2163 // symbol table. Cannot use symbol_table() here because the symbol | 2163 // string table. Cannot use string_table() here because the string |
| 2164 // table is marked. | 2164 // table is marked. |
| 2165 SymbolTable* symbol_table = heap()->symbol_table(); | 2165 StringTable* string_table = heap()->string_table(); |
| 2166 SymbolTableCleaner v(heap()); | 2166 StringTableCleaner v(heap()); |
| 2167 symbol_table->IterateElements(&v); | 2167 string_table->IterateElements(&v); |
| 2168 symbol_table->ElementsRemoved(v.PointersRemoved()); | 2168 string_table->ElementsRemoved(v.PointersRemoved()); |
| 2169 heap()->external_string_table_.Iterate(&v); | 2169 heap()->external_string_table_.Iterate(&v); |
| 2170 heap()->external_string_table_.CleanUp(); | 2170 heap()->external_string_table_.CleanUp(); |
| 2171 heap()->error_object_list_.RemoveUnmarked(heap()); | 2171 heap()->error_object_list_.RemoveUnmarked(heap()); |
| 2172 | 2172 |
| 2173 // Process the weak references. | 2173 // Process the weak references. |
| 2174 MarkCompactWeakObjectRetainer mark_compact_object_retainer; | 2174 MarkCompactWeakObjectRetainer mark_compact_object_retainer; |
| 2175 heap()->ProcessWeakReferences(&mark_compact_object_retainer); | 2175 heap()->ProcessWeakReferences(&mark_compact_object_retainer); |
| 2176 | 2176 |
| 2177 // Remove object groups after marking phase. | 2177 // Remove object groups after marking phase. |
| 2178 heap()->isolate()->global_handles()->RemoveObjectGroups(); | 2178 heap()->isolate()->global_handles()->RemoveObjectGroups(); |
| (...skipping 1064 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3243 Address value_address = | 3243 Address value_address = |
| 3244 reinterpret_cast<Address>(cell) + | 3244 reinterpret_cast<Address>(cell) + |
| 3245 (JSGlobalPropertyCell::kValueOffset - kHeapObjectTag); | 3245 (JSGlobalPropertyCell::kValueOffset - kHeapObjectTag); |
| 3246 updating_visitor.VisitPointer(reinterpret_cast<Object**>(value_address)); | 3246 updating_visitor.VisitPointer(reinterpret_cast<Object**>(value_address)); |
| 3247 } | 3247 } |
| 3248 } | 3248 } |
| 3249 | 3249 |
| 3250 // Update pointer from the native contexts list. | 3250 // Update pointer from the native contexts list. |
| 3251 updating_visitor.VisitPointer(heap_->native_contexts_list_address()); | 3251 updating_visitor.VisitPointer(heap_->native_contexts_list_address()); |
| 3252 | 3252 |
| 3253 heap_->symbol_table()->Iterate(&updating_visitor); | 3253 heap_->string_table()->Iterate(&updating_visitor); |
| 3254 | 3254 |
| 3255 // Update pointers from external string table. | 3255 // Update pointers from external string table. |
| 3256 heap_->UpdateReferencesInExternalStringTable( | 3256 heap_->UpdateReferencesInExternalStringTable( |
| 3257 &UpdateReferenceInExternalStringTableEntry); | 3257 &UpdateReferenceInExternalStringTableEntry); |
| 3258 | 3258 |
| 3259 // Update pointers in the new error object list. | 3259 // Update pointers in the new error object list. |
| 3260 heap_->error_object_list()->UpdateReferences(); | 3260 heap_->error_object_list()->UpdateReferences(); |
| 3261 | 3261 |
| 3262 if (!FLAG_watch_ic_patching) { | 3262 if (!FLAG_watch_ic_patching) { |
| 3263 // Update JSFunction pointers from the runtime profiler. | 3263 // Update JSFunction pointers from the runtime profiler. |
| (...skipping 808 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4072 while (buffer != NULL) { | 4072 while (buffer != NULL) { |
| 4073 SlotsBuffer* next_buffer = buffer->next(); | 4073 SlotsBuffer* next_buffer = buffer->next(); |
| 4074 DeallocateBuffer(buffer); | 4074 DeallocateBuffer(buffer); |
| 4075 buffer = next_buffer; | 4075 buffer = next_buffer; |
| 4076 } | 4076 } |
| 4077 *buffer_address = NULL; | 4077 *buffer_address = NULL; |
| 4078 } | 4078 } |
| 4079 | 4079 |
| 4080 | 4080 |
| 4081 } } // namespace v8::internal | 4081 } } // namespace v8::internal |
| OLD | NEW |