Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(394)

Side by Side Diff: src/global-handles.cc

Issue 1358703003: Changed scavenge GC to collect unmodified references (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Updated to use a new unmodified flag instead of partially dependent flag Created 5 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2009 the V8 project authors. All rights reserved. 1 // Copyright 2009 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/global-handles.h" 5 #include "src/global-handles.h"
6 6
7 #include "src/api.h" 7 #include "src/api.h"
8 #include "src/v8.h" 8 #include "src/v8.h"
9 #include "src/vm-state-inl.h" 9 #include "src/vm-state-inl.h"
10 10
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
59 #ifdef ENABLE_HANDLE_ZAPPING 59 #ifdef ENABLE_HANDLE_ZAPPING
60 ~Node() { 60 ~Node() {
61 // TODO(1428): if it's a weak handle we should have invoked its callback. 61 // TODO(1428): if it's a weak handle we should have invoked its callback.
62 // Zap the values for eager trapping. 62 // Zap the values for eager trapping.
63 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue); 63 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue);
64 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId; 64 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId;
65 index_ = 0; 65 index_ = 0;
66 set_independent(false); 66 set_independent(false);
67 set_partially_dependent(false); 67 set_partially_dependent(false);
68 set_in_new_space_list(false); 68 set_in_new_space_list(false);
69 set_unmodified(false);
69 parameter_or_next_free_.next_free = NULL; 70 parameter_or_next_free_.next_free = NULL;
70 weak_callback_ = NULL; 71 weak_callback_ = NULL;
71 } 72 }
72 #endif 73 #endif
73 74
74 void Initialize(int index, Node** first_free) { 75 void Initialize(int index, Node** first_free) {
75 index_ = static_cast<uint8_t>(index); 76 index_ = static_cast<uint8_t>(index);
76 DCHECK(static_cast<int>(index_) == index); 77 DCHECK(static_cast<int>(index_) == index);
77 set_state(FREE); 78 set_state(FREE);
78 set_weakness_type(NORMAL_WEAK); 79 set_weakness_type(NORMAL_WEAK);
79 set_in_new_space_list(false); 80 set_in_new_space_list(false);
81 set_unmodified(false);
80 parameter_or_next_free_.next_free = *first_free; 82 parameter_or_next_free_.next_free = *first_free;
81 *first_free = this; 83 *first_free = this;
82 } 84 }
83 85
84 void Acquire(Object* object) { 86 void Acquire(Object* object) {
85 DCHECK(state() == FREE); 87 DCHECK(state() == FREE);
86 object_ = object; 88 object_ = object;
87 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId; 89 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId;
88 set_independent(false); 90 set_independent(false);
89 set_partially_dependent(false); 91 set_partially_dependent(false);
92 set_unmodified(false);
90 set_state(NORMAL); 93 set_state(NORMAL);
91 parameter_or_next_free_.parameter = NULL; 94 parameter_or_next_free_.parameter = NULL;
92 weak_callback_ = NULL; 95 weak_callback_ = NULL;
93 IncreaseBlockUses(); 96 IncreaseBlockUses();
94 } 97 }
95 98
96 void Zap() { 99 void Zap() {
97 DCHECK(IsInUse()); 100 DCHECK(IsInUse());
98 // Zap the values for eager trapping. 101 // Zap the values for eager trapping.
99 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue); 102 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue);
100 } 103 }
101 104
102 void Release() { 105 void Release() {
103 DCHECK(IsInUse()); 106 DCHECK(IsInUse());
104 set_state(FREE); 107 set_state(FREE);
105 // Zap the values for eager trapping. 108 // Zap the values for eager trapping.
106 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue); 109 object_ = reinterpret_cast<Object*>(kGlobalHandleZapValue);
107 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId; 110 class_id_ = v8::HeapProfiler::kPersistentHandleNoClassId;
108 set_independent(false); 111 set_independent(false);
109 set_partially_dependent(false); 112 set_partially_dependent(false);
113 set_unmodified(false);
110 weak_callback_ = NULL; 114 weak_callback_ = NULL;
111 DecreaseBlockUses(); 115 DecreaseBlockUses();
112 } 116 }
113 117
114 // Object slot accessors. 118 // Object slot accessors.
115 Object* object() const { return object_; } 119 Object* object() const { return object_; }
116 Object** location() { return &object_; } 120 Object** location() { return &object_; }
117 Handle<Object> handle() { return Handle<Object>(location()); } 121 Handle<Object> handle() { return Handle<Object>(location()); }
118 122
119 // Wrapper class ID accessors. 123 // Wrapper class ID accessors.
(...skipping 26 matching lines...) Expand all
146 flags_ = IsPartiallyDependent::update(flags_, v); 150 flags_ = IsPartiallyDependent::update(flags_, v);
147 } 151 }
148 152
149 bool is_in_new_space_list() { 153 bool is_in_new_space_list() {
150 return IsInNewSpaceList::decode(flags_); 154 return IsInNewSpaceList::decode(flags_);
151 } 155 }
152 void set_in_new_space_list(bool v) { 156 void set_in_new_space_list(bool v) {
153 flags_ = IsInNewSpaceList::update(flags_, v); 157 flags_ = IsInNewSpaceList::update(flags_, v);
154 } 158 }
155 159
160 bool is_unmodified() { return flag_unmodified_; }
161
162 void set_unmodified(bool v) { flag_unmodified_ = v; }
163
156 WeaknessType weakness_type() const { 164 WeaknessType weakness_type() const {
157 return NodeWeaknessType::decode(flags_); 165 return NodeWeaknessType::decode(flags_);
158 } 166 }
159 void set_weakness_type(WeaknessType weakness_type) { 167 void set_weakness_type(WeaknessType weakness_type) {
160 flags_ = NodeWeaknessType::update(flags_, weakness_type); 168 flags_ = NodeWeaknessType::update(flags_, weakness_type);
161 } 169 }
162 170
163 bool IsNearDeath() const { 171 bool IsNearDeath() const {
164 // Check for PENDING to ensure correct answer when processing callbacks. 172 // Check for PENDING to ensure correct answer when processing callbacks.
165 return state() == PENDING || state() == NEAR_DEATH; 173 return state() == PENDING || state() == NEAR_DEATH;
(...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after
347 355
348 // This stores three flags (independent, partially_dependent and 356 // This stores three flags (independent, partially_dependent and
349 // in_new_space_list) and a State. 357 // in_new_space_list) and a State.
350 class NodeState : public BitField<State, 0, 3> {}; 358 class NodeState : public BitField<State, 0, 3> {};
351 class IsIndependent : public BitField<bool, 3, 1> {}; 359 class IsIndependent : public BitField<bool, 3, 1> {};
352 class IsPartiallyDependent : public BitField<bool, 4, 1> {}; 360 class IsPartiallyDependent : public BitField<bool, 4, 1> {};
353 class IsInNewSpaceList : public BitField<bool, 5, 1> {}; 361 class IsInNewSpaceList : public BitField<bool, 5, 1> {};
354 class NodeWeaknessType : public BitField<WeaknessType, 6, 2> {}; 362 class NodeWeaknessType : public BitField<WeaknessType, 6, 2> {};
355 363
356 uint8_t flags_; 364 uint8_t flags_;
365 // Merge this with flags_ later on. May be we need to extend flags_
mythria 2015/09/28 15:20:08 I added a new field for the unmodified check.flags
jochen (gone - plz use gerrit) 2015/09/28 15:56:19 if the performance tests are looking good, we'll j
366 bool flag_unmodified_;
357 367
358 // Handle specific callback - might be a weak reference in disguise. 368 // Handle specific callback - might be a weak reference in disguise.
359 WeakCallback weak_callback_; 369 WeakCallback weak_callback_;
360 370
361 // Provided data for callback. In FREE state, this is used for 371 // Provided data for callback. In FREE state, this is used for
362 // the free list link. 372 // the free list link.
363 union { 373 union {
364 void* parameter; 374 void* parameter;
365 Node* next_free; 375 Node* next_free;
366 } parameter_or_next_free_; 376 } parameter_or_next_free_;
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after
641 } 651 }
642 } 652 }
643 } 653 }
644 654
645 655
646 void GlobalHandles::IterateNewSpaceStrongAndDependentRoots(ObjectVisitor* v) { 656 void GlobalHandles::IterateNewSpaceStrongAndDependentRoots(ObjectVisitor* v) {
647 for (int i = 0; i < new_space_nodes_.length(); ++i) { 657 for (int i = 0; i < new_space_nodes_.length(); ++i) {
648 Node* node = new_space_nodes_[i]; 658 Node* node = new_space_nodes_[i];
649 if (node->IsStrongRetainer() || 659 if (node->IsStrongRetainer() ||
650 (node->IsWeakRetainer() && !node->is_independent() && 660 (node->IsWeakRetainer() && !node->is_independent() &&
651 !node->is_partially_dependent())) { 661 !node->is_partially_dependent() && !node->is_unmodified())) {
652 v->VisitPointer(node->location()); 662 v->VisitPointer(node->location());
653 } 663 }
654 } 664 }
655 } 665 }
656 666
657 667
658 void GlobalHandles::IdentifyNewSpaceWeakIndependentHandles( 668 void GlobalHandles::IdentifyNewSpaceWeakIndependentHandles(
659 WeakSlotCallbackWithHeap f) { 669 WeakSlotCallbackWithHeap f) {
660 for (int i = 0; i < new_space_nodes_.length(); ++i) { 670 for (int i = 0; i < new_space_nodes_.length(); ++i) {
661 Node* node = new_space_nodes_[i]; 671 Node* node = new_space_nodes_[i];
(...skipping 18 matching lines...) Expand all
680 node->CollectPhantomCallbackData(isolate(), 690 node->CollectPhantomCallbackData(isolate(),
681 &pending_phantom_callbacks_); 691 &pending_phantom_callbacks_);
682 } else { 692 } else {
683 v->VisitPointer(node->location()); 693 v->VisitPointer(node->location());
684 } 694 }
685 } 695 }
686 } 696 }
687 } 697 }
688 698
689 699
700 void GlobalHandles::IdentifyWeakUnmodifiedObjects(WeakSlotCallback f) {
jochen (gone - plz use gerrit) 2015/09/28 15:56:19 nit. f -> is_unmodified()
mythria 2015/10/02 15:29:16 Done.
701 for (int i = 0; i < new_space_nodes_.length(); ++i) {
702 Node* node = new_space_nodes_[i];
703 if (node->IsWeak() && f(node->location())) {
704 node->set_partially_dependent(true);
rmcilroy 2015/09/28 17:32:46 fix to set_unmodified(true);
mythria 2015/10/02 15:29:15 Done.
705 }
706 }
707 }
708
709
710 void GlobalHandles::IdentifyNewSpaceWeakUnModifiedHandles(
711 WeakSlotCallbackWithHeap f) {
jochen (gone - plz use gerrit) 2015/09/28 15:56:19 f -> is_unscavenged
mythria 2015/10/02 15:29:15 Done.
712 for (int i = 0; i < new_space_nodes_.length(); ++i) {
713 Node* node = new_space_nodes_[i];
714 DCHECK(node->is_in_new_space_list());
715 if ((node->is_independent() || node->is_unmodified()) && node->IsWeak() &&
716 f(isolate_->heap(), node->location())) {
717 node->MarkPending();
718 }
719 }
720 }
721
722
723 void GlobalHandles::IterateNewSpaceWeakUnModifiedRoots(ObjectVisitor* v) {
724 for (int i = 0; i < new_space_nodes_.length(); ++i) {
725 Node* node = new_space_nodes_[i];
726 DCHECK(node->is_in_new_space_list());
727 if ((node->is_independent() || node->is_unmodified()) &&
728 node->IsWeakRetainer()) {
729 // Pending weak phantom handles die immediately. Everything else survives.
730 if (node->state() == Node::PENDING &&
731 node->weakness_type() != NORMAL_WEAK) {
732 node->CollectPhantomCallbackData(isolate(),
733 &pending_phantom_callbacks_);
734 } else {
735 v->VisitPointer(node->location());
736 }
737 }
738 }
739 }
740
741
690 bool GlobalHandles::IterateObjectGroups(ObjectVisitor* v, 742 bool GlobalHandles::IterateObjectGroups(ObjectVisitor* v,
691 WeakSlotCallbackWithHeap can_skip) { 743 WeakSlotCallbackWithHeap can_skip) {
692 ComputeObjectGroupsAndImplicitReferences(); 744 ComputeObjectGroupsAndImplicitReferences();
693 int last = 0; 745 int last = 0;
694 bool any_group_was_visited = false; 746 bool any_group_was_visited = false;
695 for (int i = 0; i < object_groups_.length(); i++) { 747 for (int i = 0; i < object_groups_.length(); i++) {
696 ObjectGroup* entry = object_groups_.at(i); 748 ObjectGroup* entry = object_groups_.at(i);
697 DCHECK(entry != NULL); 749 DCHECK(entry != NULL);
698 750
699 Object*** objects = entry->objects; 751 Object*** objects = entry->objects;
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
753 Node* node = new_space_nodes_[i]; 805 Node* node = new_space_nodes_[i];
754 DCHECK(node->is_in_new_space_list()); 806 DCHECK(node->is_in_new_space_list());
755 if (!node->IsRetainer()) { 807 if (!node->IsRetainer()) {
756 // Free nodes do not have weak callbacks. Do not use them to compute 808 // Free nodes do not have weak callbacks. Do not use them to compute
757 // the freed_nodes. 809 // the freed_nodes.
758 continue; 810 continue;
759 } 811 }
760 // Skip dependent handles. Their weak callbacks might expect to be 812 // Skip dependent handles. Their weak callbacks might expect to be
761 // called between two global garbage collection callbacks which 813 // called between two global garbage collection callbacks which
762 // are not called for minor collections. 814 // are not called for minor collections.
763 if (!node->is_independent() && !node->is_partially_dependent()) { 815 if (!node->is_independent() && !node->is_partially_dependent() &&
816 !node->is_unmodified()) {
764 continue; 817 continue;
765 } 818 }
766 node->clear_partially_dependent(); 819 node->clear_partially_dependent();
767 if (node->PostGarbageCollectionProcessing(isolate_)) { 820 if (node->PostGarbageCollectionProcessing(isolate_)) {
768 if (initial_post_gc_processing_count != post_gc_processing_count_) { 821 if (initial_post_gc_processing_count != post_gc_processing_count_) {
769 // Weak callback triggered another GC and another round of 822 // Weak callback triggered another GC and another round of
770 // PostGarbageCollection processing. The current node might 823 // PostGarbageCollection processing. The current node might
771 // have been deleted in that round, so we need to bail out (or 824 // have been deleted in that round, so we need to bail out (or
772 // restart the processing). 825 // restart the processing).
773 return freed_nodes; 826 return freed_nodes;
(...skipping 500 matching lines...) Expand 10 before | Expand all | Expand 10 after
1274 blocks_[block][offset] = object; 1327 blocks_[block][offset] = object;
1275 if (isolate->heap()->InNewSpace(object)) { 1328 if (isolate->heap()->InNewSpace(object)) {
1276 new_space_indices_.Add(size_); 1329 new_space_indices_.Add(size_);
1277 } 1330 }
1278 *index = size_++; 1331 *index = size_++;
1279 } 1332 }
1280 1333
1281 1334
1282 } // namespace internal 1335 } // namespace internal
1283 } // namespace v8 1336 } // namespace v8
OLDNEW
« src/global-handles.h ('K') | « src/global-handles.h ('k') | src/heap/heap.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698