| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 #ifndef V8_TRANSITIONS_H_ | 5 #ifndef V8_TRANSITIONS_H_ |
| 6 #define V8_TRANSITIONS_H_ | 6 #define V8_TRANSITIONS_H_ |
| 7 | 7 |
| 8 #include "src/checks.h" | 8 #include "src/checks.h" |
| 9 #include "src/elements-kind.h" | 9 #include "src/elements-kind.h" |
| 10 #include "src/heap/heap.h" | 10 #include "src/heap/heap.h" |
| 11 #include "src/isolate.h" | 11 #include "src/isolate.h" |
| 12 #include "src/objects.h" | 12 #include "src/objects.h" |
| 13 | 13 |
| 14 namespace v8 { | 14 namespace v8 { |
| 15 namespace internal { | 15 namespace internal { |
| 16 | 16 |
| 17 | 17 |
| 18 // TransitionArrays are fixed arrays used to hold map transitions for property, | 18 // TransitionArrays are fixed arrays used to hold map transitions for property, |
| 19 // constant, and element changes. They can either be simple transition arrays | 19 // constant, and element changes. "Simple" transitions storing only a single |
| 20 // that store a single property transition, or a full transition array that has | 20 // property transition are stored inline (i.e. the target map is stored |
| 21 // directly); otherwise a full transition array is used that has |
| 21 // prototype transitions and multiple property transitons. The details related | 22 // prototype transitions and multiple property transitons. The details related |
| 22 // to property transitions are accessed in the descriptor array of the target | 23 // to property transitions are accessed in the descriptor array of the target |
| 23 // map. In the case of a simple transition, the key is also read from the | 24 // map. In the case of a simple transition, the key is also read from the |
| 24 // descriptor array of the target map. | 25 // descriptor array of the target map. |
| 25 // | 26 // |
| 26 // The simple format of the these objects is: | 27 // This class provides a static interface that operates directly on maps |
| 27 // [0] Undefined or back pointer map | 28 // and handles the distinction between simple and full transitions storage. |
| 28 // [1] Single transition | |
| 29 // | 29 // |
| 30 // The full format is: | 30 // The full format is: |
| 31 // [0] Undefined or back pointer map | 31 // [0] Smi(0) or fixed array of prototype transitions |
| 32 // [1] Smi(0) or fixed array of prototype transitions | 32 // [1] Number of transitions |
| 33 // [2] Number of transitions | 33 // [2] First transition |
| 34 // [3] First transition | 34 // [2 + number of transitions * kTransitionSize]: start of slack |
| 35 // [3 + number of transitions * kTransitionSize]: start of slack | |
| 36 class TransitionArray: public FixedArray { | 35 class TransitionArray: public FixedArray { |
| 37 public: | 36 public: |
| 38 // Accessors for fetching instance transition at transition number. | 37 // Insert a new transition into |map|'s transition array, extending it |
| 39 inline Name* GetKey(int transition_number); | 38 // as necessary. |
| 40 inline void SetKey(int transition_number, Name* value); | 39 static void Insert(Handle<Map> map, Handle<Name> name, Handle<Map> target, |
| 41 inline Object** GetKeySlot(int transition_number); | 40 SimpleTransitionFlag flag); |
| 42 int GetSortedKeyIndex(int transition_number) { return transition_number; } | |
| 43 | 41 |
| 44 Name* GetSortedKey(int transition_number) { | 42 static Map* SearchTransition(Map* map, PropertyKind kind, Name* name, |
| 45 return GetKey(transition_number); | 43 PropertyAttributes attributes); |
| 44 |
| 45 static Map* SearchSpecial(Map* map, Symbol* name); |
| 46 |
| 47 static Handle<Map> FindTransitionToField(Handle<Map> map, Handle<Name> name); |
| 48 |
| 49 static Handle<String> ExpectedTransitionKey(Handle<Map> map); |
| 50 |
| 51 static Handle<Map> ExpectedTransitionTarget(Handle<Map> map) { |
| 52 DCHECK(!ExpectedTransitionKey(map).is_null()); |
| 53 return Handle<Map>(GetSimpleTransition(map->raw_transitions())); |
| 54 } |
| 55 static inline bool IsEmpty(Object* raw_transition) { |
| 56 return raw_transition->IsSmi() || |
| 57 (raw_transition->IsWeakCell() && |
| 58 WeakCell::cast(raw_transition)->cleared()); |
| 59 } |
| 60 static inline bool IsSimpleTransition(Object* raw_transition) { |
| 61 DCHECK(!raw_transition->IsWeakCell() || |
| 62 WeakCell::cast(raw_transition)->cleared() || |
| 63 WeakCell::cast(raw_transition)->value()->IsMap()); |
| 64 return raw_transition->IsWeakCell() && |
| 65 !WeakCell::cast(raw_transition)->cleared(); |
| 66 } |
| 67 static inline Map* GetSimpleTransition(Object* raw_transition) { |
| 68 DCHECK(IsSimpleTransition(raw_transition)); |
| 69 return Map::cast(WeakCell::cast(raw_transition)->value()); |
| 70 } |
| 71 static inline bool IsFullTransitionArray(Object* raw_transitions) { |
| 72 return raw_transitions->IsTransitionArray(); |
| 46 } | 73 } |
| 47 | 74 |
| 48 inline Map* GetTarget(int transition_number); | 75 // The size of transition arrays are limited so they do not end up in large |
| 49 inline void SetTarget(int transition_number, Map* target); | 76 // object space. Otherwise ClearNonLiveReferences would leak memory while |
| 77 // applying in-place right trimming. |
| 78 static bool CanHaveMoreTransitions(Handle<Map> map); |
| 50 | 79 |
| 51 inline PropertyDetails GetTargetDetails(int transition_number); | 80 // ===== PROTOTYPE TRANSITIONS ===== |
| 52 inline Object* GetTargetValue(int transition_number); | 81 // When you set the prototype of an object using the __proto__ accessor you |
| 82 // need a new map for the object (the prototype is stored in the map). In |
| 83 // order not to multiply maps unnecessarily we store these as transitions in |
| 84 // the original map. That way we can transition to the same map if the same |
| 85 // prototype is set, rather than creating a new map every time. The |
| 86 // transitions are in the form of a map where the keys are prototype objects |
| 87 // and the values are the maps they transition to. |
| 88 // Cache format: |
| 89 // 0: finger - index of the first free cell in the cache |
| 90 // 1 + i: target map |
| 91 static const int kMaxCachedPrototypeTransitions = 256; |
| 92 static Handle<Map> PutPrototypeTransition(Handle<Map> map, |
| 93 Handle<Object> prototype, |
| 94 Handle<Map> target_map); |
| 53 | 95 |
| 54 inline bool HasElementsTransition(); | 96 static Handle<Map> GetPrototypeTransition(Handle<Map> map, |
| 97 Handle<Object> prototype); |
| 55 | 98 |
| 56 inline Object* back_pointer_storage(); | 99 static FixedArray* GetPrototypeTransitions(Map* map); |
| 57 inline void set_back_pointer_storage( | 100 |
| 58 Object* back_pointer, | 101 static int NumberOfPrototypeTransitions(FixedArray* proto_transitions) { |
| 59 WriteBarrierMode mode = UPDATE_WRITE_BARRIER); | 102 if (proto_transitions->length() == 0) return 0; |
| 103 Object* raw = proto_transitions->get(kProtoTransitionNumberOfEntriesOffset); |
| 104 return Smi::cast(raw)->value(); |
| 105 } |
| 106 |
| 107 static void SetNumberOfPrototypeTransitions(FixedArray* proto_transitions, |
| 108 int value); |
| 60 | 109 |
| 61 inline FixedArray* GetPrototypeTransitions(); | 110 inline FixedArray* GetPrototypeTransitions(); |
| 62 inline void SetPrototypeTransitions( | 111 inline void SetPrototypeTransitions( |
| 63 FixedArray* prototype_transitions, | 112 FixedArray* prototype_transitions, |
| 64 WriteBarrierMode mode = UPDATE_WRITE_BARRIER); | 113 WriteBarrierMode mode = UPDATE_WRITE_BARRIER); |
| 65 inline Object** GetPrototypeTransitionsSlot(); | 114 inline Object** GetPrototypeTransitionsSlot(); |
| 66 inline bool HasPrototypeTransitions(); | 115 inline bool HasPrototypeTransitions(); |
| 67 | 116 |
| 68 // Returns the number of transitions in the array. | 117 // ===== ITERATION ===== |
| 69 int number_of_transitions() { | 118 |
| 70 if (IsSimpleTransition()) return 1; | 119 typedef void (*TraverseCallback)(Map* map, void* data); |
| 71 if (length() <= kFirstIndex) return 0; | 120 |
| 72 return Smi::cast(get(kTransitionLengthIndex))->value(); | 121 // Traverse the transition tree in postorder. |
| 122 static void TraverseTransitionTree(Map* map, TraverseCallback callback, |
| 123 void* data) { |
| 124 // Make sure that we do not allocate in the callback. |
| 125 DisallowHeapAllocation no_allocation; |
| 126 TraverseTransitionTreeInternal(map, callback, data); |
| 73 } | 127 } |
| 74 | 128 |
| 75 int number_of_transitions_storage() { | 129 // ===== FINE-GRAINED ACCESSORS ===== |
| 76 if (IsSimpleTransition()) return 1; | 130 |
| 77 if (length() <= kFirstIndex) return 0; | 131 // Accessors for fetching instance transition at transition number. |
| 78 return (length() - kFirstIndex) / kTransitionSize; | 132 static inline Name* GetKey(Object* raw_transitions, int transition_number); |
| 133 inline Name* GetKey(int transition_number); |
| 134 inline void SetKey(int transition_number, Name* value); |
| 135 inline Object** GetKeySlot(int transition_number); |
| 136 int GetSortedKeyIndex(int transition_number) { return transition_number; } |
| 137 |
| 138 Name* GetSortedKey(int transition_number) { |
| 139 return GetKey(transition_number); |
| 79 } | 140 } |
| 80 | 141 |
| 81 int NumberOfSlackTransitions() { | 142 static inline Map* GetTarget(Object* raw_transitions, int transition_number); |
| 82 return number_of_transitions_storage() - number_of_transitions(); | 143 inline Map* GetTarget(int transition_number); |
| 83 } | 144 inline void SetTarget(int transition_number, Map* target); |
| 84 | |
| 85 inline void SetNumberOfTransitions(int number_of_transitions); | |
| 86 inline int number_of_entries() { return number_of_transitions(); } | |
| 87 | |
| 88 // Creates a FullTransitionArray from a SimpleTransitionArray in | |
| 89 // containing_map. | |
| 90 static Handle<TransitionArray> ExtendToFullTransitionArray( | |
| 91 Handle<Map> containing_map); | |
| 92 | |
| 93 // Return a transition array, using the array from the owning map if it | |
| 94 // already has one (copying into a larger array if necessary), otherwise | |
| 95 // creating a new one according to flag. | |
| 96 // TODO(verwaest): This should not cause an existing transition to be | |
| 97 // overwritten. | |
| 98 static Handle<TransitionArray> Insert(Handle<Map> map, Handle<Name> name, | |
| 99 Handle<Map> target, | |
| 100 SimpleTransitionFlag flag); | |
| 101 // Search a transition for a given kind, property name and attributes. | |
| 102 int Search(PropertyKind kind, Name* name, PropertyAttributes attributes, | |
| 103 int* out_insertion_index = NULL); | |
| 104 | |
| 105 // Search a non-property transition (like elements kind, observe or frozen | |
| 106 // transitions). | |
| 107 inline int SearchSpecial(Symbol* symbol, int* out_insertion_index = NULL) { | |
| 108 return SearchName(symbol, out_insertion_index); | |
| 109 } | |
| 110 | 145 |
| 111 static inline PropertyDetails GetTargetDetails(Name* name, Map* target); | 146 static inline PropertyDetails GetTargetDetails(Name* name, Map* target); |
| 112 | 147 |
| 113 // Allocates a TransitionArray. | 148 // Returns the number of transitions in the array. |
| 114 static Handle<TransitionArray> Allocate(Isolate* isolate, | 149 static int NumberOfTransitions(Object* raw_transitions); |
| 115 int number_of_transitions, | 150 // Required for templatized Search interface. |
| 116 int slack = 0); | 151 inline int number_of_entries() { return number_of_transitions(); } |
| 117 | 152 |
| 118 bool IsSimpleTransition() { | 153 inline void SetNumberOfTransitions(int number_of_transitions); |
| 119 return length() == kSimpleTransitionSize && | |
| 120 get(kSimpleTransitionTarget)->IsHeapObject() && | |
| 121 // The IntrusivePrototypeTransitionIterator may have set the map of the | |
| 122 // prototype transitions array to a smi. In that case, there are | |
| 123 // prototype transitions, hence this transition array is a full | |
| 124 // transition array. | |
| 125 HeapObject::cast(get(kSimpleTransitionTarget))->map()->IsMap() && | |
| 126 get(kSimpleTransitionTarget)->IsMap(); | |
| 127 } | |
| 128 | 154 |
| 129 bool IsFullTransitionArray() { | 155 static int Capacity(Object* raw_transitions); |
| 130 return length() > kFirstIndex || | |
| 131 (length() == kFirstIndex && !IsSimpleTransition()); | |
| 132 } | |
| 133 | 156 |
| 134 // Casting. | 157 // Casting. |
| 135 static inline TransitionArray* cast(Object* obj); | 158 static inline TransitionArray* cast(Object* obj); |
| 136 | 159 |
| 137 // Constant for denoting key was not found. | |
| 138 static const int kNotFound = -1; | |
| 139 | |
| 140 static const int kBackPointerStorageIndex = 0; | |
| 141 | |
| 142 // Layout for full transition arrays. | |
| 143 static const int kPrototypeTransitionsIndex = 1; | |
| 144 static const int kTransitionLengthIndex = 2; | |
| 145 static const int kFirstIndex = 3; | |
| 146 | |
| 147 // Layout for simple transition arrays. | |
| 148 static const int kSimpleTransitionTarget = 1; | |
| 149 static const int kSimpleTransitionSize = 2; | |
| 150 static const int kSimpleTransitionIndex = 0; | |
| 151 STATIC_ASSERT(kSimpleTransitionIndex != kNotFound); | |
| 152 | |
| 153 static const int kBackPointerStorageOffset = FixedArray::kHeaderSize; | |
| 154 | |
| 155 // Layout for the full transition array header. | |
| 156 static const int kPrototypeTransitionsOffset = kBackPointerStorageOffset + | |
| 157 kPointerSize; | |
| 158 static const int kTransitionLengthOffset = | |
| 159 kPrototypeTransitionsOffset + kPointerSize; | |
| 160 | |
| 161 // Layout of map transition entries in full transition arrays. | |
| 162 static const int kTransitionKey = 0; | |
| 163 static const int kTransitionTarget = 1; | |
| 164 static const int kTransitionSize = 2; | 160 static const int kTransitionSize = 2; |
| 161 static const int kProtoTransitionHeaderSize = 1; |
| 165 | 162 |
| 166 #if defined(DEBUG) || defined(OBJECT_PRINT) | 163 #if defined(DEBUG) || defined(OBJECT_PRINT) |
| 167 // For our gdb macros, we should perhaps change these in the future. | 164 // For our gdb macros, we should perhaps change these in the future. |
| 168 void Print(); | 165 void Print(); |
| 169 | 166 |
| 170 // Print all the transitions. | 167 // Print all the transitions. |
| 171 void PrintTransitions(std::ostream& os, bool print_header = true); // NOLINT | 168 static void PrintTransitions(std::ostream& os, Object* transitions, |
| 169 bool print_header = true); // NOLINT |
| 172 #endif | 170 #endif |
| 173 | 171 |
| 174 #ifdef DEBUG | 172 #ifdef DEBUG |
| 175 bool IsSortedNoDuplicates(int valid_entries = -1); | 173 bool IsSortedNoDuplicates(int valid_entries = -1); |
| 176 bool IsConsistentWithBackPointers(Map* current_map); | 174 static bool IsSortedNoDuplicates(Map* map); |
| 177 bool IsEqualTo(TransitionArray* other); | 175 static bool IsConsistentWithBackPointers(Map* map); |
| 178 | 176 |
| 179 // Returns true for a non-property transitions like elements kind, observed | 177 // Returns true for a non-property transitions like elements kind, observed |
| 180 // or frozen transitions. | 178 // or frozen transitions. |
| 181 static inline bool IsSpecialTransition(Name* name); | 179 static inline bool IsSpecialTransition(Name* name); |
| 182 #endif | 180 #endif |
| 183 | 181 |
| 182 // Constant for denoting key was not found. |
| 183 static const int kNotFound = -1; |
| 184 |
| 184 // The maximum number of transitions we want in a transition array (should | 185 // The maximum number of transitions we want in a transition array (should |
| 185 // fit in a page). | 186 // fit in a page). |
| 186 static const int kMaxNumberOfTransitions = 1024 + 512; | 187 static const int kMaxNumberOfTransitions = 1024 + 512; |
| 187 | 188 |
| 188 // Returns the fixed array length required to hold number_of_transitions | 189 private: |
| 189 // transitions. | 190 // Layout for full transition arrays. |
| 190 static int LengthFor(int number_of_transitions) { | 191 static const int kPrototypeTransitionsIndex = 0; |
| 191 return ToKeyIndex(number_of_transitions); | 192 static const int kTransitionLengthIndex = 1; |
| 192 } | 193 static const int kFirstIndex = 2; |
| 193 | 194 |
| 194 private: | 195 // Layout of map transition entries in full transition arrays. |
| 196 static const int kTransitionKey = 0; |
| 197 static const int kTransitionTarget = 1; |
| 198 STATIC_ASSERT(kTransitionSize == 2); |
| 199 |
| 200 static const int kProtoTransitionNumberOfEntriesOffset = 0; |
| 201 STATIC_ASSERT(kProtoTransitionHeaderSize == 1); |
| 202 |
| 195 // Conversion from transition number to array indices. | 203 // Conversion from transition number to array indices. |
| 196 static int ToKeyIndex(int transition_number) { | 204 static int ToKeyIndex(int transition_number) { |
| 197 return kFirstIndex + | 205 return kFirstIndex + |
| 198 (transition_number * kTransitionSize) + | 206 (transition_number * kTransitionSize) + |
| 199 kTransitionKey; | 207 kTransitionKey; |
| 200 } | 208 } |
| 201 | 209 |
| 202 static int ToTargetIndex(int transition_number) { | 210 static int ToTargetIndex(int transition_number) { |
| 203 return kFirstIndex + | 211 return kFirstIndex + |
| 204 (transition_number * kTransitionSize) + | 212 (transition_number * kTransitionSize) + |
| 205 kTransitionTarget; | 213 kTransitionTarget; |
| 206 } | 214 } |
| 207 | 215 |
| 208 static Handle<TransitionArray> AllocateSimple( | 216 // Returns the fixed array length required to hold number_of_transitions |
| 209 Isolate* isolate, Handle<Map> target); | 217 // transitions. |
| 218 static int LengthFor(int number_of_transitions) { |
| 219 return ToKeyIndex(number_of_transitions); |
| 220 } |
| 210 | 221 |
| 211 // Allocate a new transition array with a single entry. | 222 // Allocates a TransitionArray. |
| 212 static Handle<TransitionArray> NewWith(Handle<Map> map, | 223 static Handle<TransitionArray> Allocate(Isolate* isolate, |
| 213 Handle<Name> name, | 224 int number_of_transitions, |
| 214 Handle<Map> target, | 225 int slack = 0); |
| 215 SimpleTransitionFlag flag); | |
| 216 | 226 |
| 227 static void EnsureHasFullTransitionArray(Handle<Map> map); |
| 228 static void ReplaceTransitions(Handle<Map> map, Object* new_transitions); |
| 229 |
| 230 // Search a transition for a given kind, property name and attributes. |
| 231 int Search(PropertyKind kind, Name* name, PropertyAttributes attributes, |
| 232 int* out_insertion_index = NULL); |
| 233 |
| 234 // Search a non-property transition (like elements kind, observe or frozen |
| 235 // transitions). |
| 236 inline int SearchSpecial(Symbol* symbol, int* out_insertion_index = NULL) { |
| 237 return SearchName(symbol, out_insertion_index); |
| 238 } |
| 217 // Search a first transition for a given property name. | 239 // Search a first transition for a given property name. |
| 218 inline int SearchName(Name* name, int* out_insertion_index = NULL); | 240 inline int SearchName(Name* name, int* out_insertion_index = NULL); |
| 219 int SearchDetails(int transition, PropertyKind kind, | 241 int SearchDetails(int transition, PropertyKind kind, |
| 220 PropertyAttributes attributes, int* out_insertion_index); | 242 PropertyAttributes attributes, int* out_insertion_index); |
| 221 | 243 |
| 244 int number_of_transitions() { |
| 245 if (length() < kFirstIndex) return 0; |
| 246 return Smi::cast(get(kTransitionLengthIndex))->value(); |
| 247 } |
| 248 |
| 249 static inline PropertyDetails GetSimpleTargetDetails(Map* transition) { |
| 250 return transition->GetLastDescriptorDetails(); |
| 251 } |
| 252 |
| 253 static inline Name* GetSimpleTransitionKey(Map* transition) { |
| 254 int descriptor = transition->LastAdded(); |
| 255 return transition->instance_descriptors()->GetKey(descriptor); |
| 256 } |
| 257 |
| 258 static void TraverseTransitionTreeInternal(Map* map, |
| 259 TraverseCallback callback, |
| 260 void* data); |
| 261 |
| 262 static void SetPrototypeTransitions(Handle<Map> map, |
| 263 Handle<FixedArray> proto_transitions); |
| 264 |
| 222 // Compares two tuples <key, kind, attributes>, returns -1 if | 265 // Compares two tuples <key, kind, attributes>, returns -1 if |
| 223 // tuple1 is "less" than tuple2, 0 if tuple1 equal to tuple2 and 1 otherwise. | 266 // tuple1 is "less" than tuple2, 0 if tuple1 equal to tuple2 and 1 otherwise. |
| 224 static inline int CompareKeys(Name* key1, uint32_t hash1, PropertyKind kind1, | 267 static inline int CompareKeys(Name* key1, uint32_t hash1, PropertyKind kind1, |
| 225 PropertyAttributes attributes1, Name* key2, | 268 PropertyAttributes attributes1, Name* key2, |
| 226 uint32_t hash2, PropertyKind kind2, | 269 uint32_t hash2, PropertyKind kind2, |
| 227 PropertyAttributes attributes2); | 270 PropertyAttributes attributes2); |
| 228 | 271 |
| 229 // Compares keys, returns -1 if key1 is "less" than key2, | 272 // Compares keys, returns -1 if key1 is "less" than key2, |
| 230 // 0 if key1 equal to key2 and 1 otherwise. | 273 // 0 if key1 equal to key2 and 1 otherwise. |
| 231 static inline int CompareNames(Name* key1, uint32_t hash1, Name* key2, | 274 static inline int CompareNames(Name* key1, uint32_t hash1, Name* key2, |
| 232 uint32_t hash2); | 275 uint32_t hash2); |
| 233 | 276 |
| 234 // Compares two details, returns -1 if details1 is "less" than details2, | 277 // Compares two details, returns -1 if details1 is "less" than details2, |
| 235 // 0 if details1 equal to details2 and 1 otherwise. | 278 // 0 if details1 equal to details2 and 1 otherwise. |
| 236 static inline int CompareDetails(PropertyKind kind1, | 279 static inline int CompareDetails(PropertyKind kind1, |
| 237 PropertyAttributes attributes1, | 280 PropertyAttributes attributes1, |
| 238 PropertyKind kind2, | 281 PropertyKind kind2, |
| 239 PropertyAttributes attributes2); | 282 PropertyAttributes attributes2); |
| 240 | 283 |
| 241 inline void NoIncrementalWriteBarrierSet(int transition_number, | 284 inline void NoIncrementalWriteBarrierSet(int transition_number, |
| 242 Name* key, | 285 Name* key, |
| 243 Map* target); | 286 Map* target); |
| 244 | 287 |
| 245 // Copy a single transition from the origin array. | 288 // Copy a single transition from the origin array. |
| 246 inline void NoIncrementalWriteBarrierCopyFrom(TransitionArray* origin, | 289 inline void NoIncrementalWriteBarrierCopyFrom(TransitionArray* origin, |
| 247 int origin_transition, | 290 int origin_transition, |
| 248 int target_transition); | 291 int target_transition); |
| 249 | 292 |
| 293 #ifdef DEBUG |
| 294 static void CheckNewTransitionsAreConsistent(Handle<Map> map, |
| 295 TransitionArray* old_transitions, |
| 296 Object* transitions); |
| 297 #endif |
| 298 |
| 250 DISALLOW_IMPLICIT_CONSTRUCTORS(TransitionArray); | 299 DISALLOW_IMPLICIT_CONSTRUCTORS(TransitionArray); |
| 251 }; | 300 }; |
| 252 | 301 |
| 253 | 302 |
| 254 } } // namespace v8::internal | 303 } } // namespace v8::internal |
| 255 | 304 |
| 256 #endif // V8_TRANSITIONS_H_ | 305 #endif // V8_TRANSITIONS_H_ |
| OLD | NEW |