OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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/type-feedback-vector.h" | 5 #include "src/type-feedback-vector.h" |
6 | 6 |
7 #include "src/code-stubs.h" | 7 #include "src/code-stubs.h" |
8 #include "src/ic/ic.h" | 8 #include "src/ic/ic.h" |
9 #include "src/ic/ic-state.h" | 9 #include "src/ic/ic-state.h" |
10 #include "src/objects.h" | 10 #include "src/objects.h" |
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
76 // Fill the bit-vector part with zeros. | 76 // Fill the bit-vector part with zeros. |
77 for (int i = 0; i < slot_kinds_length; i++) { | 77 for (int i = 0; i < slot_kinds_length; i++) { |
78 array->set(kReservedIndexCount + i, Smi::FromInt(0)); | 78 array->set(kReservedIndexCount + i, Smi::FromInt(0)); |
79 } | 79 } |
80 | 80 |
81 Handle<TypeFeedbackMetadata> metadata = | 81 Handle<TypeFeedbackMetadata> metadata = |
82 Handle<TypeFeedbackMetadata>::cast(array); | 82 Handle<TypeFeedbackMetadata>::cast(array); |
83 for (int i = 0; i < slot_count; i++) { | 83 for (int i = 0; i < slot_count; i++) { |
84 metadata->SetKind(FeedbackVectorSlot(i), spec->GetKind(i)); | 84 metadata->SetKind(FeedbackVectorSlot(i), spec->GetKind(i)); |
85 } | 85 } |
86 | |
87 // It's important that the TypeFeedbackMetadata have a COW map, since it's | |
88 // pointed to by both a SharedFunctionInfo and indirectly by closures through | |
89 // the TypeFeedbackVector. The serializer uses the COW map type to decide | |
90 // this object belongs in the startup snapshot and not the partial | |
91 // snapshot(s). | |
92 metadata->set_map(isolate->heap()->fixed_cow_array_map()); | |
93 | |
94 return metadata; | 86 return metadata; |
95 } | 87 } |
96 | 88 |
97 | 89 |
98 bool TypeFeedbackMetadata::SpecDiffersFrom( | 90 bool TypeFeedbackMetadata::SpecDiffersFrom( |
99 const FeedbackVectorSpec* other_spec) const { | 91 const FeedbackVectorSpec* other_spec) const { |
100 if (other_spec->slots() != slot_count()) { | 92 if (other_spec->slots() != slot_count()) { |
101 return true; | 93 return true; |
102 } | 94 } |
103 | 95 |
104 int slots = slot_count(); | 96 int slots = slot_count(); |
105 for (int i = 0; i < slots; i++) { | 97 for (int i = 0; i < slots; i++) { |
106 if (GetKind(FeedbackVectorSlot(i)) != other_spec->GetKind(i)) { | 98 if (GetKind(FeedbackVectorSlot(i)) != other_spec->GetKind(i)) { |
107 return true; | 99 return true; |
108 } | 100 } |
109 } | 101 } |
110 return false; | 102 return false; |
111 } | 103 } |
112 | 104 |
113 bool TypeFeedbackMetadata::DiffersFrom( | |
114 const TypeFeedbackMetadata* other_metadata) const { | |
115 if (other_metadata->slot_count() != slot_count()) { | |
116 return true; | |
117 } | |
118 | |
119 int slots = slot_count(); | |
120 for (int i = 0; i < slots; i++) { | |
121 FeedbackVectorSlot slot(i); | |
122 if (GetKind(slot) != other_metadata->GetKind(slot)) { | |
123 return true; | |
124 } | |
125 } | |
126 return false; | |
127 } | |
128 | 105 |
129 const char* TypeFeedbackMetadata::Kind2String(FeedbackVectorSlotKind kind) { | 106 const char* TypeFeedbackMetadata::Kind2String(FeedbackVectorSlotKind kind) { |
130 switch (kind) { | 107 switch (kind) { |
131 case FeedbackVectorSlotKind::INVALID: | 108 case FeedbackVectorSlotKind::INVALID: |
132 return "INVALID"; | 109 return "INVALID"; |
133 case FeedbackVectorSlotKind::CALL_IC: | 110 case FeedbackVectorSlotKind::CALL_IC: |
134 return "CALL_IC"; | 111 return "CALL_IC"; |
135 case FeedbackVectorSlotKind::LOAD_IC: | 112 case FeedbackVectorSlotKind::LOAD_IC: |
136 return "LOAD_IC"; | 113 return "LOAD_IC"; |
137 case FeedbackVectorSlotKind::KEYED_LOAD_IC: | 114 case FeedbackVectorSlotKind::KEYED_LOAD_IC: |
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
262 } | 239 } |
263 } | 240 } |
264 } | 241 } |
265 | 242 |
266 | 243 |
267 // static | 244 // static |
268 void TypeFeedbackVector::ClearAllKeyedStoreICs(Isolate* isolate) { | 245 void TypeFeedbackVector::ClearAllKeyedStoreICs(Isolate* isolate) { |
269 SharedFunctionInfo::Iterator iterator(isolate); | 246 SharedFunctionInfo::Iterator iterator(isolate); |
270 SharedFunctionInfo* shared; | 247 SharedFunctionInfo* shared; |
271 while ((shared = iterator.Next())) { | 248 while ((shared = iterator.Next())) { |
272 if (!shared->OptimizedCodeMapIsCleared()) { | 249 TypeFeedbackVector* vector = shared->feedback_vector(); |
273 FixedArray* optimized_code_map = shared->optimized_code_map(); | 250 vector->ClearKeyedStoreICs(shared); |
274 int length = optimized_code_map->length(); | |
275 for (int i = SharedFunctionInfo::kEntriesStart; i < length; | |
276 i += SharedFunctionInfo::kEntryLength) { | |
277 WeakCell* cell = WeakCell::cast( | |
278 optimized_code_map->get(i + SharedFunctionInfo::kLiteralsOffset)); | |
279 if (cell->value()->IsLiteralsArray()) { | |
280 TypeFeedbackVector* vector = | |
281 LiteralsArray::cast(cell->value())->feedback_vector(); | |
282 vector->ClearKeyedStoreICs(shared); | |
283 } | |
284 } | |
285 } | |
286 } | 251 } |
287 } | 252 } |
288 | 253 |
289 | 254 |
290 void TypeFeedbackVector::ClearKeyedStoreICs(SharedFunctionInfo* shared) { | 255 void TypeFeedbackVector::ClearKeyedStoreICs(SharedFunctionInfo* shared) { |
291 Isolate* isolate = GetIsolate(); | 256 Isolate* isolate = GetIsolate(); |
| 257 |
292 Code* host = shared->code(); | 258 Code* host = shared->code(); |
293 Object* uninitialized_sentinel = | 259 Object* uninitialized_sentinel = |
294 TypeFeedbackVector::RawUninitializedSentinel(isolate); | 260 TypeFeedbackVector::RawUninitializedSentinel(isolate); |
295 | 261 |
296 TypeFeedbackMetadataIterator iter(metadata()); | 262 TypeFeedbackMetadataIterator iter(metadata()); |
297 while (iter.HasNext()) { | 263 while (iter.HasNext()) { |
298 FeedbackVectorSlot slot = iter.Next(); | 264 FeedbackVectorSlot slot = iter.Next(); |
299 FeedbackVectorSlotKind kind = iter.kind(); | 265 FeedbackVectorSlotKind kind = iter.kind(); |
300 if (kind != FeedbackVectorSlotKind::KEYED_STORE_IC) continue; | 266 if (kind != FeedbackVectorSlotKind::KEYED_STORE_IC) continue; |
301 Object* obj = Get(slot); | 267 Object* obj = Get(slot); |
(...skipping 551 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
853 return mode; | 819 return mode; |
854 } | 820 } |
855 | 821 |
856 | 822 |
857 IcCheckType KeyedStoreICNexus::GetKeyType() const { | 823 IcCheckType KeyedStoreICNexus::GetKeyType() const { |
858 // The structure of the vector slots tells us the type. | 824 // The structure of the vector slots tells us the type. |
859 return GetFeedback()->IsName() ? PROPERTY : ELEMENT; | 825 return GetFeedback()->IsName() ? PROPERTY : ELEMENT; |
860 } | 826 } |
861 } // namespace internal | 827 } // namespace internal |
862 } // namespace v8 | 828 } // namespace v8 |
OLD | NEW |