Removed transitions from the accessor pair descriptors.
authorverwaest@chromium.org <verwaest@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Mon, 16 Jul 2012 14:02:50 +0000 (14:02 +0000)
committerverwaest@chromium.org <verwaest@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Mon, 16 Jul 2012 14:02:50 +0000 (14:02 +0000)
AccessorPair related transitions are now also stored as single map links, simplifying the code that handles transitions. AccessorPairs can now be shared between descriptor arrays, since they can only be mutated after another transition anyway; during which the pair is copied before writing.

Review URL: https://chromiumcodereview.appspot.com/10784014

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@12097 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

15 files changed:
src/bootstrapper.cc
src/factory.cc
src/heap.cc
src/heap.h
src/ic.cc
src/mark-compact.cc
src/objects-debug.cc
src/objects-inl.h
src/objects.cc
src/objects.h
src/property.h
src/runtime.cc
src/transitions-inl.h
src/transitions.cc
src/transitions.h

index 996721a5797b2f651483531c7ec789c454737ab6..349c540d7f667367c46481a2c1fb6edba20249cf 100644 (file)
@@ -1740,9 +1740,7 @@ bool Genesis::InstallNatives() {
     Handle<DescriptorArray> array_descriptors(
         array_function->initial_map()->instance_descriptors());
     int old = array_descriptors->SearchWithCache(heap()->length_symbol());
-    MaybeObject* copy_result =
-        reresult_descriptors->CopyFrom(0, *array_descriptors, old, witness);
-    if (copy_result->IsFailure()) return false;
+    reresult_descriptors->CopyFrom(0, *array_descriptors, old, witness);
 
     reresult_descriptors->SetLastAdded(0);
 
index f56db70f14f895d310dc8ebb033ef7e64c3a2d8f..679bb443b012d81c95b24d88befccbc6491f9600 100644 (file)
@@ -933,7 +933,7 @@ Handle<DescriptorArray> Factory::CopyAppendCallbackDescriptors(
   if (0 < descriptor_count) {
     result->SetLastAdded(array->LastAdded());
     for (int i = 0; i < descriptor_count; i++) {
-      DescriptorArray::CopyFrom(result, i, array, i, witness);
+      result->CopyFrom(i, *array, i, witness);
     }
   }
 
@@ -967,7 +967,7 @@ Handle<DescriptorArray> Factory::CopyAppendCallbackDescriptors(
     Handle<DescriptorArray> new_result =
         NewDescriptorArray(new_number_of_descriptors);
     for (int i = 0; i < new_number_of_descriptors; i++) {
-      DescriptorArray::CopyFrom(new_result, i, result, i, witness);
+      new_result->CopyFrom(i, *result, i, witness);
     }
     result = new_result;
   }
index 9e38f513703521d30a3ee8fedfe56c3e774f062b..bfc4620bcbd09da464bfec0278edbe3faa4720bd 100644 (file)
@@ -5329,37 +5329,9 @@ void Heap::Verify() {
   cell_space_->Verify(&no_dirty_regions_visitor);
 
   lo_space_->Verify();
-
-  VerifyNoAccessorPairSharing();
-}
-
-
-void Heap::VerifyNoAccessorPairSharing() {
-  // Verification is done in 2 phases: First we mark all AccessorPairs, checking
-  // that we mark only unmarked pairs, then we clear all marks, restoring the
-  // initial state. We use the Smi tag of the AccessorPair's getter as the
-  // marking bit, because we can never see a Smi as the getter.
-  for (int phase = 0; phase < 2; phase++) {
-    HeapObjectIterator iter(map_space());
-    for (HeapObject* obj = iter.Next(); obj != NULL; obj = iter.Next()) {
-      if (obj->IsMap()) {
-        DescriptorArray* descs = Map::cast(obj)->instance_descriptors();
-        for (int i = 0; i < descs->number_of_descriptors(); i++) {
-          if (descs->GetType(i) == CALLBACKS &&
-              descs->GetValue(i)->IsAccessorPair()) {
-            AccessorPair* accessors = AccessorPair::cast(descs->GetValue(i));
-            uintptr_t before = reinterpret_cast<intptr_t>(accessors->getter());
-            uintptr_t after = (phase == 0) ?
-                ((before & ~kSmiTagMask) | kSmiTag) :
-                ((before & ~kHeapObjectTag) | kHeapObjectTag);
-            CHECK(before != after);
-            accessors->set_getter(reinterpret_cast<Object*>(after));
-          }
-        }
-      }
-    }
-  }
 }
+
+
 #endif  // DEBUG
 
 
index 08c91a41d2a755e41f4ad33c8025ec34c0235380..bae01d6e3267017e90da14dfaf0a222d881567d6 100644 (file)
@@ -1237,10 +1237,6 @@ class Heap {
   // Verify the heap is in its normal state before or after a GC.
   void Verify();
 
-  // Verify that AccessorPairs are not shared, i.e. make sure that they have
-  // exactly one pointer to them.
-  void VerifyNoAccessorPairSharing();
-
   void OldPointerSpaceCheckStoreBuffer();
   void MapSpaceCheckStoreBuffer();
   void LargeObjectSpaceCheckStoreBuffer();
index 69a3f2a65f2e9a459a01c33f9fac488c9151c4f6..2f74eee69c3ef59c1ae04cf71c365e1c1857da88 100644 (file)
--- a/src/ic.cc
+++ b/src/ic.cc
@@ -1322,7 +1322,7 @@ static bool LookupForWrite(Handle<JSObject> receiver,
     // that we explicitly exclude native accessors for now, because the stubs
     // are not yet prepared for this scenario.
     receiver->Lookup(*name, lookup);
-    if (!lookup->IsCallbacks()) return false;
+    if (!lookup->IsPropertyCallbacks()) return false;
     Handle<Object> callback(lookup->GetCallbackObject());
     return callback->IsAccessorPair() && StoreICableLookup(lookup);
   }
@@ -1513,10 +1513,7 @@ void StoreIC::UpdateCaches(LookupResult* lookup,
     case CONSTANT_FUNCTION:
       return;
     case TRANSITION: {
-      Object* value = lookup->GetTransitionValue();
-      // Callbacks.
-      if (value->IsAccessorPair()) return;
-
+      Map* value = lookup->GetTransitionTarget();
       Handle<Map> transition(Map::cast(value));
       DescriptorArray* target_descriptors = transition->instance_descriptors();
       int descriptor = target_descriptors->LastAdded();
@@ -1979,16 +1976,8 @@ void KeyedStoreIC::UpdateCaches(LookupResult* lookup,
           Handle<Map>::null(), strict_mode);
       break;
     case TRANSITION: {
-      Object* value = lookup->GetTransitionValue();
-      // Callbacks transition.
-      if (value->IsAccessorPair()) {
-        code = (strict_mode == kStrictMode)
-            ? generic_stub_strict()
-            : generic_stub();
-        break;
-      }
+      Handle<Map> transition(lookup->GetTransitionTarget());
 
-      Handle<Map> transition(Map::cast(value));
       DescriptorArray* target_descriptors = transition->instance_descriptors();
       int descriptor = target_descriptors->LastAdded();
       PropertyDetails details = target_descriptors->GetDetails(descriptor);
@@ -2147,7 +2136,7 @@ RUNTIME_FUNCTION(MaybeObject*, StoreIC_ArrayLength) {
   // The length property has to be a writable callback property.
   LookupResult debug_lookup(isolate);
   receiver->LocalLookup(isolate->heap()->length_symbol(), &debug_lookup);
-  ASSERT(debug_lookup.IsCallbacks() && !debug_lookup.IsReadOnly());
+  ASSERT(debug_lookup.IsPropertyCallbacks() && !debug_lookup.IsReadOnly());
 #endif
 
   Object* result;
index 024b7ef4072ca162ebe9ca8750a1a6d3e885f42d..32f08d924e0646cc0647f1d9d8f38e4278e76a18 100644 (file)
@@ -1934,16 +1934,8 @@ void Marker<T>::MarkDescriptorArray(DescriptorArray* descriptors) {
       case CONSTANT_FUNCTION:
       case HANDLER:
       case INTERCEPTOR:
-        base_marker()->MarkObjectAndPush(value);
-        break;
       case CALLBACKS:
-        if (!value->IsAccessorPair()) {
-          base_marker()->MarkObjectAndPush(value);
-        } else if (base_marker()->MarkObjectWithoutPush(value)) {
-          AccessorPair* accessors = AccessorPair::cast(value);
-          MarkAccessorPairSlot(accessors, AccessorPair::kGetterOffset);
-          MarkAccessorPairSlot(accessors, AccessorPair::kSetterOffset);
-        }
+        base_marker()->MarkObjectAndPush(value);
         break;
       case TRANSITION:
       case NONEXISTENT:
@@ -1983,21 +1975,6 @@ void Marker<T>::MarkTransitionArray(TransitionArray* transitions) {
       base_marker()->MarkObjectAndPush(HeapObject::cast(key));
       mark_compact_collector()->RecordSlot(transitions_start, key_slot, key);
     }
-
-    Object** value_slot = transitions->GetValueSlot(i);
-    if (!(*value_slot)->IsHeapObject()) continue;
-    HeapObject* value = HeapObject::cast(*value_slot);
-
-    if (value->IsAccessorPair()) {
-      mark_compact_collector()->RecordSlot(transitions_start,
-                                           value_slot,
-                                           value);
-
-      base_marker()->MarkObjectWithoutPush(value);
-      AccessorPair* accessors = AccessorPair::cast(value);
-      MarkAccessorPairSlot(accessors, AccessorPair::kGetterOffset);
-      MarkAccessorPairSlot(accessors, AccessorPair::kSetterOffset);
-    }
   }
 }
 
index e40fe513a5c9a778c018591a8964c8ccae121af6..3047326e2ab195789d438c7e7efc15802cdebbe7 100644 (file)
@@ -949,15 +949,7 @@ bool TransitionArray::IsConsistentWithBackPointers(Map* current_map) {
     return false;
   }
   for (int i = 0; i < number_of_transitions(); ++i) {
-    Object* value = GetValue(i);
-    if (value->IsAccessorPair()) {
-      AccessorPair* accessors = AccessorPair::cast(value);
-      if (!CheckOneBackPointer(current_map, accessors->getter())) return false;
-      if (!CheckOneBackPointer(current_map, accessors->setter())) return false;
-    } else {
-      ASSERT(value->IsMap());
-      if (!CheckOneBackPointer(current_map, value)) return false;
-    }
+    if (!CheckOneBackPointer(current_map, GetTarget(i))) return false;
   }
   return true;
 }
index 23fb2133468afb020bff452f4e9163c6e904bd58..6dd2a99518753b694a64e44b9848d0c9713a4935 100644 (file)
@@ -3534,13 +3534,14 @@ Map* Map::elements_transition_map() {
 }
 
 
-MaybeObject* Map::AddTransition(String* key, Object* value) {
-  if (HasTransitionArray()) return transitions()->CopyInsert(key, value);
-  return TransitionArray::NewWith(key, value);
+MaybeObject* Map::AddTransition(String* key, Map* target) {
+  if (HasTransitionArray()) return transitions()->CopyInsert(key, target);
+  return TransitionArray::NewWith(key, target);
 }
 
-void Map::SetTransition(int transition_index, Object* value) {
-  transitions()->SetValue(transition_index, value);
+
+void Map::SetTransition(int transition_index, Map* target) {
+  transitions()->SetTarget(transition_index, target);
 }
 
 
index de41ce1eb99781b7a1ad8a9745e03d393e0c37b0..1a3500c3abd7801b981117f2f9dea976263cd7d1 100644 (file)
@@ -2859,18 +2859,11 @@ MaybeObject* JSObject::SetPropertyForResult(LookupResult* result,
                                               attributes,
                                               strict_mode);
     case TRANSITION: {
-      Object* transition = result->GetTransitionValue();
+      Map* transition_map = result->GetTransitionTarget();
 
-      if (transition->IsAccessorPair()) {
-        ASSERT(!AccessorPair::cast(transition)->ContainsAccessor());
-        return ConvertDescriptorToField(*name, *value, attributes);
-      }
-
-      Map* transition_map = Map::cast(transition);
       DescriptorArray* descriptors = transition_map->instance_descriptors();
       int descriptor = descriptors->LastAdded();
       PropertyDetails details = descriptors->GetDetails(descriptor);
-      ASSERT(details.type() == FIELD || details.type() == CONSTANT_FUNCTION);
 
       if (details.type() == FIELD) {
         if (attributes == details.attributes()) {
@@ -2881,9 +2874,12 @@ MaybeObject* JSObject::SetPropertyForResult(LookupResult* result,
                                                field_index);
         }
         return self->ConvertDescriptorToField(*name, *value, attributes);
+      } else if (details.type() == CALLBACKS) {
+        return ConvertDescriptorToField(*name, *value, attributes);
       }
 
-      // Is transition to CONSTANT_FUNCTION.
+      ASSERT(details.type() == CONSTANT_FUNCTION);
+
       Object* constant_function = descriptors->GetValue(descriptor);
       // If the same constant function is being added we can simply
       // transition to the target map.
@@ -2983,18 +2979,11 @@ MaybeObject* JSObject::SetLocalPropertyIgnoreAttributes(
       // Override callback in clone
       return ConvertDescriptorToField(name, value, attributes);
     case TRANSITION: {
-      Object* transition = result.GetTransitionValue();
-
-      if (transition->IsAccessorPair()) {
-        ASSERT(!AccessorPair::cast(transition)->ContainsAccessor());
-        return ConvertDescriptorToField(name, value, attributes);
-      }
+      Map* transition_map = result.GetTransitionTarget();
 
-      Map* transition_map = Map::cast(transition);
       DescriptorArray* descriptors = transition_map->instance_descriptors();
       int descriptor = descriptors->LastAdded();
       PropertyDetails details = descriptors->GetDetails(descriptor);
-      ASSERT(details.type() == FIELD || details.type() == CONSTANT_FUNCTION);
 
       if (details.type() == FIELD) {
         if (attributes == details.attributes()) {
@@ -3005,10 +2994,14 @@ MaybeObject* JSObject::SetLocalPropertyIgnoreAttributes(
                                          field_index);
         }
         return ConvertDescriptorToField(name, value, attributes);
+      } else if (details.type() == CALLBACKS) {
+        return ConvertDescriptorToField(name, value, attributes);
       }
 
-      // Was transition to CONSTANT_FUNCTION. Replace with a map transition to a
-      // new map with a FIELD, even if the value is a function.
+      ASSERT(details.type() == CONSTANT_FUNCTION);
+
+      // Replace transition to CONSTANT FUNCTION with a map transition to a new
+      // map with a FIELD, even if the value is a function.
       return ConvertTransitionToMapTransition(
           result.GetTransitionIndex(), name, value, attributes);
     }
@@ -3294,11 +3287,6 @@ MaybeObject* JSObject::NormalizeProperties(PropertyNormalizationMode mode,
       }
       case CALLBACKS: {
         Object* value = descs->GetCallbacksObject(i);
-        if (value->IsAccessorPair()) {
-          MaybeObject* maybe_copy =
-              AccessorPair::cast(value)->CopyWithoutTransitions();
-          if (!maybe_copy->To(&value)) return maybe_copy;
-        }
         MaybeObject* maybe_dictionary =
             dictionary->Add(descs->GetKey(i), value, details);
         if (!maybe_dictionary->To(&dictionary)) return maybe_dictionary;
@@ -4231,7 +4219,7 @@ void JSObject::LookupCallback(String* name, LookupResult* result) {
        current != heap->null_value() && current->IsJSObject();
        current = JSObject::cast(current)->GetPrototype()) {
     JSObject::cast(current)->LocalLookupRealNamedProperty(name, result);
-    if (result->IsCallbacks()) return;
+    if (result->IsPropertyCallbacks()) return;
   }
   result->NotFound();
 }
@@ -4343,7 +4331,7 @@ MaybeObject* JSObject::CreateAccessorPairFor(String* name) {
     // DefinePropertyAccessor below.
     Object* obj = result.GetCallbackObject();
     if (obj->IsAccessorPair()) {
-      return AccessorPair::cast(obj)->CopyWithoutTransitions();
+      return AccessorPair::cast(obj)->Copy();
     }
   }
   return GetHeap()->AllocateAccessorPair();
@@ -4377,9 +4365,9 @@ MaybeObject* JSObject::DefinePropertyAccessor(String* name,
   }
 
   AccessorPair* accessors;
-  MaybeObject* maybe_accessors = CreateAccessorPairFor(name);
-    if (!maybe_accessors->To(&accessors)) return maybe_accessors;
-  }
+  MaybeObject* maybe_accessors = CreateAccessorPairFor(name);
+  if (!maybe_accessors->To(&accessors)) return maybe_accessors;
+
   accessors->SetComponents(getter, setter);
   return SetPropertyCallback(name, accessors, attributes);
 }
@@ -4451,17 +4439,16 @@ MaybeObject* JSObject::SetPropertyCallback(String* name,
                                            Object* structure,
                                            PropertyAttributes attributes) {
   // Normalize object to make this operation simple.
-  { MaybeObject* maybe_ok = NormalizeProperties(CLEAR_INOBJECT_PROPERTIES, 0);
-    if (maybe_ok->IsFailure()) return maybe_ok;
-  }
+  MaybeObject* maybe_ok = NormalizeProperties(CLEAR_INOBJECT_PROPERTIES, 0);
+  if (maybe_ok->IsFailure()) return maybe_ok;
 
   // For the global object allocate a new map to invalidate the global inline
   // caches which have a global property cell reference directly in the code.
   if (IsGlobalObject()) {
     Map* new_map;
-    MaybeObject* maybe_new_map = map()->CopyDropDescriptors();
-      if (!maybe_new_map->To(&new_map)) return maybe_new_map;
-    }
+    MaybeObject* maybe_new_map = map()->CopyDropDescriptors();
+    if (!maybe_new_map->To(&new_map)) return maybe_new_map;
+
     set_map(new_map);
     // When running crankshaft, changing the map is not enough. We
     // need to deoptimize all functions that rely on this global
@@ -4471,9 +4458,8 @@ MaybeObject* JSObject::SetPropertyCallback(String* name,
 
   // Update the dictionary with the new CALLBACKS property.
   PropertyDetails details = PropertyDetails(attributes, CALLBACKS);
-  { MaybeObject* maybe_ok = SetNormalizedProperty(name, structure, details);
-    if (maybe_ok->IsFailure()) return maybe_ok;
-  }
+  maybe_ok = SetNormalizedProperty(name, structure, details);
+  if (maybe_ok->IsFailure()) return maybe_ok;
 
   return GetHeap()->undefined_value();
 }
@@ -4525,73 +4511,32 @@ MaybeObject* JSObject::DefineAccessor(String* name,
 }
 
 
-static MaybeObject* CreateFreshAccessor(JSObject* obj,
-                                        String* name,
-                                        AccessorComponent component,
-                                        Object* accessor,
-                                        PropertyAttributes attributes) {
-  // step 1: create a new getter/setter pair with only the accessor in it
-  Heap* heap = obj->GetHeap();
-  AccessorPair* accessors2;
-  { MaybeObject* maybe_accessors2 = heap->AllocateAccessorPair();
-    if (!maybe_accessors2->To(&accessors2)) return maybe_accessors2;
-  }
-  accessors2->set(component, accessor);
-
-  // step 2: create a copy of the descriptors, incl. the new getter/setter pair
-  Map* map1 = obj->map();
-  CallbacksDescriptor callbacks_descr2(name, accessors2, attributes, 0);
-  DescriptorArray* descriptors2;
-  { MaybeObject* maybe_descriptors2 =
-        map1->instance_descriptors()->CopyAdd(&callbacks_descr2);
-    if (!maybe_descriptors2->To(&descriptors2)) return maybe_descriptors2;
-  }
-
-  // step 3: create a new map with the new descriptors
-  Map* map2;
-  { MaybeObject* maybe_map2 = map1->CopyReplaceDescriptors(descriptors2);
-    if (!maybe_map2->To(&map2)) return maybe_map2;
-  }
+static MaybeObject* TryAccessorTransition(JSObject* self,
+                                          Map* transitioned_map,
+                                          String* name,
+                                          AccessorComponent component,
+                                          Object* accessor,
+                                          PropertyAttributes attributes) {
+  DescriptorArray* descs = transitioned_map->instance_descriptors();
+  int number = descs->LastAdded();
+  PropertyDetails details = descs->GetDetails(number);
 
-  // step 4: create a new getter/setter pair with a transition to the new map
-  AccessorPair* accessors1;
-  { MaybeObject* maybe_accessors1 = heap->AllocateAccessorPair();
-    if (!maybe_accessors1->To(&accessors1)) return maybe_accessors1;
-  }
-  accessors1->set(component, map2);
+  // If the transition target was not callbacks, fall back to the slow case.
+  if (details.type() != CALLBACKS) return self->GetHeap()->null_value();
 
-  // step 5: create a copy of the descriptors, incl. the new getter/setter pair
-  // with the transition
-  TransitionArray* new_transitions;
-  { MaybeObject* maybe_new_transitions = map1->AddTransition(name, accessors1);
-    if (!maybe_new_transitions->To(&new_transitions)) {
-      return maybe_new_transitions;
-    }
-  }
+  Object* target_accessor =
+      AccessorPair::cast(descs->GetCallbacksObject(number))->get(component);
+  PropertyAttributes target_attributes = details.attributes();
 
-  // step 6: everything went well so far, so we make our changes visible
-  { MaybeObject* transition_added = map1->set_transitions(new_transitions);
-    if (transition_added->IsFailure()) return transition_added;
+  // Reuse transition if adding same accessor with same attributes.
+  if (target_accessor == accessor && target_attributes == attributes) {
+    self->set_map(transitioned_map);
+    return self;
   }
 
-  map2->SetBackPointer(map1);
-  obj->set_map(map2);
-  return obj;
-}
-
-
-static bool TransitionToSameAccessor(Object* map,
-                                     String* name,
-                                     AccessorComponent component,
-                                     Object* accessor,
-                                     PropertyAttributes attributes ) {
-  Map* transitioned_map = Map::cast(map);
-  DescriptorArray* descs = transitioned_map->instance_descriptors();
-  int number = descs->LastAdded();
-  Object* target_accessor =
-      AccessorPair::cast(descs->GetCallbacksObject(number))->get(component);
-  PropertyAttributes target_attributes = descs->GetDetails(number).attributes();
-  return target_accessor == accessor && target_attributes == attributes;
+  // If either not the same accessor, or not the same attributes, fall back to
+  // the slow case.
+  return self->GetHeap()->null_value();
 }
 
 
@@ -4600,43 +4545,31 @@ static MaybeObject* NewCallbackTransition(JSObject* obj,
                                           AccessorComponent component,
                                           Object* accessor,
                                           PropertyAttributes attributes,
-                                          AccessorPair* accessors2) {
-  // step 1: copy the old getter/setter pair and set the new accessor
-  AccessorPair* accessors3;
-  { MaybeObject* maybe_accessors3 = accessors2->CopyWithoutTransitions();
-    if (!maybe_accessors3->To(&accessors3)) return maybe_accessors3;
-  }
-  accessors3->set(component, accessor);
-
-  // step 2: create a copy of the descriptors, incl. the new getter/setter pair
-  Map* map2 = obj->map();
-  CallbacksDescriptor callbacks_descr3(name, accessors3, attributes, 0);
-  DescriptorArray* descriptors3;
-  { MaybeObject* maybe_descriptors3 =
-        map2->instance_descriptors()->CopyInsert(&callbacks_descr3);
-    if (!maybe_descriptors3->To(&descriptors3)) return maybe_descriptors3;
-  }
+                                          AccessorPair* new_accessors) {
+  // step 1: create a copy of the descriptors, incl. the new getter/setter pair
+  Map* old_map = obj->map();
+  CallbacksDescriptor new_accessors_desc(name, new_accessors, attributes);
+  DescriptorArray* descriptors;
+  MaybeObject* maybe_descriptors =
+      old_map->instance_descriptors()->CopyInsert(&new_accessors_desc);
+  if (!maybe_descriptors->To(&descriptors)) return maybe_descriptors;
 
-  // step 3: create a new map with the new descriptors
-  Map* map3;
-  { MaybeObject* maybe_map3 = map2->CopyReplaceDescriptors(descriptors3);
-    if (!maybe_map3->To(&map3)) return maybe_map3;
-  }
+  // step 2: create a new map with the new descriptors
+  Map* new_map;
+  MaybeObject* maybe_new_map = old_map->CopyReplaceDescriptors(descriptors);
+  if (!maybe_new_map->To(&new_map)) return maybe_new_map;
 
-  // step 4: add a new transition to the new map
-  TransitionArray* new_transitions;
-  { MaybeObject* maybe_transitions = map2->AddTransition(name, accessors2);
-    if (!maybe_transitions->To(&new_transitions)) return maybe_transitions;
-  }
+  // step 3: add a new transition to the new map
+  TransitionArray* transitions;
+  MaybeObject* maybe_transitions = old_map->AddTransition(name, new_map);
+  if (!maybe_transitions->To(&transitions)) return maybe_transitions;
 
-  // step 5: everything went well so far, so we make our changes visible
-  { MaybeObject* transition_added = map2->set_transitions(new_transitions);
-    if (transition_added->IsFailure()) return transition_added;
-  }
+  // step 4: everything went well so far, so we make our changes visible
+  MaybeObject* transition_added = old_map->set_transitions(transitions);
+  if (transition_added->IsFailure()) return transition_added;
 
-  map3->SetBackPointer(map2);
-  obj->set_map(map3);
-  accessors2->set(component, map3);
+  new_map->SetBackPointer(old_map);
+  obj->set_map(new_map);
   return obj;
 }
 
@@ -4649,40 +4582,54 @@ MaybeObject* JSObject::DefineFastAccessor(String* name,
   LookupResult result(GetIsolate());
   LocalLookup(name, &result);
 
-  // If we have a new property, create a fresh accessor plus a transition to it.
-  if (!result.IsFound()) {
-    return CreateFreshAccessor(this, name, component, accessor, attributes);
-  }
+  if (result.IsFound()
+      && !result.IsPropertyCallbacks()
+      && !result.IsTransition()) return GetHeap()->null_value();
 
-  // If the property is not a JavaScript accessor, fall back to the slow case.
-  if (!result.IsCallbacks()) return GetHeap()->null_value();
+  // Return success if the same accessor with the same attributes already exist.
+  AccessorPair* source_accessors = NULL;
+  if (result.IsPropertyCallbacks()) {
+    Object* callback_value = result.GetCallbackObject();
+    if (callback_value->IsAccessorPair()) {
+      source_accessors = AccessorPair::cast(callback_value);
+      Object* entry = source_accessors->get(component);
+      if (entry == accessor && result.GetAttributes() == attributes) {
+        return this;
+      }
+    }
+  }
 
-  Object* callback_value = result.GetCallbackObject();
-  if (!callback_value->IsAccessorPair()) return GetHeap()->null_value();
-  AccessorPair* accessors = AccessorPair::cast(callback_value);
+  // If not, lookup a transition.
+  map()->LookupTransition(this, name, &result);
 
-  // Follow a callback transition, if there is a fitting one.
-  Object* entry = accessors->get(component);
-  if (entry->IsMap() &&
-      TransitionToSameAccessor(entry, name, component, accessor, attributes)) {
-    set_map(Map::cast(entry));
-    return this;
+  // If there is a transition, try to follow it.
+  if (result.IsFound()) {
+    Map* target = result.GetTransitionTarget();
+    return TryAccessorTransition(
+        this, target, name, component, accessor, attributes);
   }
 
-  if (entry == accessor && result.GetAttributes() == attributes) return this;
+  // If there is no transition yet, add a transition to the a new accessor pair
+  // containing the accessor.
+  AccessorPair* accessors;
+  MaybeObject* maybe_accessors;
 
-  // Only the other accessor has been set so far, create a new transition.
-  if (entry->IsTheHole()) {
-    return NewCallbackTransition(this,
-                                 name,
-                                 component,
-                                 accessor,
-                                 attributes,
-                                 accessors);
+  // Allocate a new pair if there were no source accessors. Otherwise, copy the
+  // pair and modify the accessor.
+  if (source_accessors != NULL) {
+    maybe_accessors = source_accessors->Copy();
+  } else {
+    maybe_accessors = GetHeap()->AllocateAccessorPair();
   }
+  if (!maybe_accessors->To(&accessors)) return maybe_accessors;
+  accessors->set(component, accessor);
 
-  // Nothing from the above worked, so we have to fall back to the slow case.
-  return GetHeap()->null_value();
+  return NewCallbackTransition(this,
+                               name,
+                               component,
+                               accessor,
+                               attributes,
+                               accessors);
 }
 
 
@@ -5012,44 +4959,17 @@ class IntrusiveMapTransitionIterator {
 
   Map* Next() {
     ASSERT(IsIterating());
-    // Attention, tricky index manipulation ahead: Two consecutive indices are
-    // assigned to each descriptor. Most descriptors directly advance to the
-    // next descriptor by adding 2 to the index. The exceptions are the
-    // CALLBACKS entries: An even index means we look at its getter, and an odd
-    // index means we look at its setter.
-    int raw_index = Smi::cast(*TransitionArrayHeader())->value();
-    int index = raw_index / 2;
+    int index = Smi::cast(*TransitionArrayHeader())->value();
     int number_of_transitions = transition_array_->number_of_transitions();
     while (index < number_of_transitions) {
-      Object* value = transition_array_->GetValue(index);
-
-      if (value->IsMap()) {
-        *TransitionArrayHeader() = Smi::FromInt(raw_index + 2);
-        return static_cast<Map*>(value);
-      }
-
-      ASSERT(value->IsAccessorPair());
-
-      // We might have a map transition in a getter or in a setter.
-      AccessorPair* accessors = static_cast<AccessorPair*>(value);
-      Object* accessor;
-      if ((raw_index & 1) == 0) {
-        accessor = accessors->setter();
-      } else {
-        ++index;
-        accessor = accessors->getter();
-      }
-      ++raw_index;
-      if (accessor->IsMap()) {
-        *TransitionArrayHeader() = Smi::FromInt(raw_index);
-        return static_cast<Map*>(accessor);
-      }
+      *TransitionArrayHeader() = Smi::FromInt(index + 1);
+      return transition_array_->GetTarget(index);
     }
 
-    if (index == transition_array_->number_of_transitions() &&
+    if (index == number_of_transitions &&
         transition_array_->HasElementsTransition()) {
       Map* elements_transition = transition_array_->elements_transition();
-      *TransitionArrayHeader() = Smi::FromInt(raw_index + 2);
+      *TransitionArrayHeader() = Smi::FromInt(index + 1);
       return elements_transition;
     }
     *TransitionArrayHeader() = transition_array_->GetHeap()->fixed_array_map();
@@ -5786,30 +5706,14 @@ static bool InsertionPointFound(String* key1, String* key2) {
 }
 
 
-void DescriptorArray::CopyFrom(Handle<DescriptorArray> dst,
-                               int dst_index,
-                               Handle<DescriptorArray> src,
+void DescriptorArray::CopyFrom(int dst_index,
+                               DescriptorArray* src,
                                int src_index,
                                const WhitenessWitness& witness) {
-  CALL_HEAP_FUNCTION_VOID(dst->GetIsolate(),
-                          dst->CopyFrom(dst_index, *src, src_index, witness));
-}
-
-
-MaybeObject* DescriptorArray::CopyFrom(int dst_index,
-                                       DescriptorArray* src,
-                                       int src_index,
-                                       const WhitenessWitness& witness) {
   Object* value = src->GetValue(src_index);
   PropertyDetails details = src->GetDetails(src_index);
-  if (details.type() == CALLBACKS && value->IsAccessorPair()) {
-    MaybeObject* maybe_copy =
-        AccessorPair::cast(value)->CopyWithoutTransitions();
-    if (!maybe_copy->To(&value)) return maybe_copy;
-  }
   Descriptor desc(src->GetKey(src_index), value, details);
   Set(dst_index, &desc, witness);
-  return this;
 }
 
 MaybeObject* DescriptorArray::CopyReplace(Descriptor* descriptor,
@@ -5833,9 +5737,7 @@ MaybeObject* DescriptorArray::CopyReplace(Descriptor* descriptor,
   // Copy the descriptors, replacing a descriptor.
   for (int index = 0; index < size; ++index) {
     if (index == insertion_index) continue;
-    MaybeObject* copy_result =
-        new_descriptors->CopyFrom(index, this, index, witness);
-    if (copy_result->IsFailure()) return copy_result;
+    new_descriptors->CopyFrom(index, this, index, witness);
   }
 
   descriptor->SetEnumerationIndex(GetDetails(insertion_index).index());
@@ -5850,9 +5752,8 @@ MaybeObject* DescriptorArray::CopyReplace(Descriptor* descriptor,
 
 MaybeObject* DescriptorArray::CopyInsert(Descriptor* descriptor) {
   // Ensure the key is a symbol.
-  { MaybeObject* maybe_result = descriptor->KeyToSymbol();
-    if (maybe_result->IsFailure()) return maybe_result;
-  }
+  MaybeObject* maybe_result = descriptor->KeyToSymbol();
+  if (maybe_result->IsFailure()) return maybe_result;
 
   // We replace the key if it is already present.
   int index = SearchWithCache(descriptor->GetKey());
@@ -5863,9 +5764,8 @@ MaybeObject* DescriptorArray::CopyInsert(Descriptor* descriptor) {
 
 MaybeObject* DescriptorArray::CopyAdd(Descriptor* descriptor) {
   // Ensure the key is a symbol.
-  { MaybeObject* maybe_result = descriptor->KeyToSymbol();
-    if (maybe_result->IsFailure()) return maybe_result;
-  }
+  MaybeObject* maybe_result = descriptor->KeyToSymbol();
+  if (maybe_result->IsFailure()) return maybe_result;
 
   String* key = descriptor->GetKey();
   ASSERT(Search(key) == kNotFound);
@@ -5873,9 +5773,8 @@ MaybeObject* DescriptorArray::CopyAdd(Descriptor* descriptor) {
   int new_size = number_of_descriptors() + 1;
 
   DescriptorArray* new_descriptors;
-  { MaybeObject* maybe_result = Allocate(new_size, MAY_BE_SHARED);
-    if (!maybe_result->To(&new_descriptors)) return maybe_result;
-  }
+  MaybeObject* maybe_descriptors = Allocate(new_size, MAY_BE_SHARED);
+  if (!maybe_descriptors->To(&new_descriptors)) return maybe_descriptors;
 
   FixedArray::WhitenessWitness witness(new_descriptors);
 
@@ -5886,9 +5785,7 @@ MaybeObject* DescriptorArray::CopyAdd(Descriptor* descriptor) {
     if (insertion_index < 0 && InsertionPointFound(GetKey(from), key)) {
       insertion_index = to++;
     }
-    MaybeObject* copy_result =
-        new_descriptors->CopyFrom(to++, this, from, witness);
-    if (copy_result->IsFailure()) return copy_result;
+    new_descriptors->CopyFrom(to++, this, from, witness);
   }
   if (insertion_index < 0) insertion_index = to++;
 
@@ -5909,18 +5806,14 @@ MaybeObject* DescriptorArray::Copy(SharedMode shared_mode) {
   // Allocate the new descriptor array.
   int number_of_descriptors = this->number_of_descriptors();
   DescriptorArray* new_descriptors;
-  { MaybeObject* maybe_result = Allocate(number_of_descriptors,
-                                         shared_mode);
-    if (!maybe_result->To(&new_descriptors)) return maybe_result;
-  }
+  MaybeObject* maybe_result = Allocate(number_of_descriptors, shared_mode);
+  if (!maybe_result->To(&new_descriptors)) return maybe_result;
 
   // Copy the content.
   if (number_of_descriptors > 0) {
     FixedArray::WhitenessWitness witness(new_descriptors);
     for (int i = 0; i < number_of_descriptors; i++) {
-      MaybeObject* copy_result =
-          new_descriptors->CopyFrom(i, this, i, witness);
-      if (copy_result->IsFailure()) return copy_result;
+      new_descriptors->CopyFrom(i, this, i, witness);
     }
     new_descriptors->SetLastAdded(LastAdded());
   }
@@ -6020,14 +5913,14 @@ void DescriptorArray::Sort(const WhitenessWitness& witness) {
 }
 
 
-MaybeObject* AccessorPair::CopyWithoutTransitions() {
+MaybeObject* AccessorPair::Copy() {
   Heap* heap = GetHeap();
   AccessorPair* copy;
-  MaybeObject* maybe_copy = heap->AllocateAccessorPair();
-    if (!maybe_copy->To(&copy)) return maybe_copy;
-  }
-  copy->set_getter(getter()->IsMap() ? heap->the_hole_value() : getter());
-  copy->set_setter(setter()->IsMap() ? heap->the_hole_value() : setter());
+  MaybeObject* maybe_copy = heap->AllocateAccessorPair();
+  if (!maybe_copy->To(&copy)) return maybe_copy;
+
+  copy->set_getter(getter());
+  copy->set_setter(setter());
   return copy;
 }
 
@@ -7313,40 +7206,6 @@ static bool ClearBackPointer(Heap* heap, Object* target) {
 }
 
 
-static bool ClearAccessorComponent(Heap* heap,
-                                   AccessorPair* accessors,
-                                   AccessorComponent component) {
-  Object* component_value = accessors->get(component);
-  if (!component_value->IsMap()) return true;
-  if (ClearBackPointer(heap, component_value)) {
-    accessors->set(component, heap->the_hole_value());
-    return true;
-  }
-  return false;
-}
-
-
-static bool ClearNonLiveTransition(Heap* heap,
-                                   TransitionArray* t,
-                                   int transition_index) {
-  // If the value is a map, check if the target is live. If not, clear the
-  // transition. Also drop the back pointer for that map transition, so that
-  // this map is not reached again by following a back pointer from that
-  // non-live map.
-  Object* value = t->GetValue(transition_index);
-  if (value->IsMap()) {
-    return ClearBackPointer(heap, t->GetValue(transition_index));
-  }
-
-  ASSERT(value->IsAccessorPair());
-
-  AccessorPair* accessors = AccessorPair::cast(value);
-  bool getter = ClearAccessorComponent(heap, accessors, ACCESSOR_GETTER);
-  bool setter = ClearAccessorComponent(heap, accessors, ACCESSOR_SETTER);
-  return getter && setter;
-}
-
-
 // TODO(mstarzinger): This method should be moved into MarkCompactCollector,
 // because it cannot be called from outside the GC and we already have methods
 // depending on the transitions layout in the GC anyways.
@@ -7362,17 +7221,17 @@ void Map::ClearNonLiveTransitions(Heap* heap) {
 
   // Compact all live descriptors to the left.
   for (int i = 0; i < t->number_of_transitions(); ++i) {
-    if (!ClearNonLiveTransition(heap, t, i)) {
+    if (!ClearBackPointer(heap, t->GetTarget(i))) {
       if (i != transition_index) {
         String* key = t->GetKey(i);
-        Object* value = t->GetValue(i);
+        Map* target = t->GetTarget(i);
         t->SetKey(transition_index, key);
-        t->SetValue(transition_index, value);
+        t->SetTarget(transition_index, target);
         MarkCompactCollector* collector = heap->mark_compact_collector();
         Object** key_slot = t->GetKeySlot(transition_index);
         collector->RecordSlot(key_slot, key_slot, key);
-        Object** value_slot = t->GetValueSlot(transition_index);
-        collector->RecordSlot(value_slot, value_slot, value);
+        Object** target_slot = t->GetTargetSlot(transition_index);
+        collector->RecordSlot(target_slot, target_slot, target);
       }
       transition_index++;
     }
@@ -10472,7 +10331,7 @@ bool JSObject::HasRealNamedCallbackProperty(String* key) {
 
   LookupResult result(isolate);
   LocalLookupRealNamedProperty(key, &result);
-  return result.IsCallbacks();
+  return result.IsPropertyCallbacks();
 }
 
 
@@ -12696,15 +12555,15 @@ MaybeObject* StringDictionary::TransformPropertiesToFastFor(
     if (IsKey(k)) {
       Object* value = ValueAt(i);
       // Ensure the key is a symbol before writing into the instance descriptor.
-      Object* key;
-      MaybeObject* maybe_key = heap->LookupSymbol(String::cast(k));
-        if (!maybe_key->ToObject(&key)) return maybe_key;
-      }
+      String* key;
+      MaybeObject* maybe_key = heap->LookupSymbol(String::cast(k));
+      if (!maybe_key->To(&key)) return maybe_key;
+
       PropertyDetails details = DetailsAt(i);
       PropertyType type = details.type();
 
       if (value->IsJSFunction() && !heap->InNewSpace(value)) {
-        ConstantFunctionDescriptor d(String::cast(key),
+        ConstantFunctionDescriptor d(key,
                                      JSFunction::cast(value),
                                      details.attributes(),
                                      details.index());
@@ -12718,18 +12577,13 @@ MaybeObject* StringDictionary::TransformPropertiesToFastFor(
           int offset = current_offset - inobject_props;
           FixedArray::cast(fields)->set(offset, value);
         }
-        FieldDescriptor d(String::cast(key),
+        FieldDescriptor d(key,
                           current_offset++,
                           details.attributes(),
                           details.index());
         descriptors->Set(next_descriptor, &d, witness);
       } else if (type == CALLBACKS) {
-        if (value->IsAccessorPair()) {
-          MaybeObject* maybe_copy =
-              AccessorPair::cast(value)->CopyWithoutTransitions();
-          if (!maybe_copy->To(&value)) return maybe_copy;
-        }
-        CallbacksDescriptor d(String::cast(key),
+        CallbacksDescriptor d(key,
                               value,
                               details.attributes(),
                               details.index());
@@ -12745,10 +12599,8 @@ MaybeObject* StringDictionary::TransformPropertiesToFastFor(
   descriptors->Sort(witness);
   // Allocate new map.
   Map* new_map;
-  { MaybeObject* maybe_new_map =
-        obj->map()->CopyReplaceDescriptors(descriptors);
-    if (!maybe_new_map->To(&new_map)) return maybe_new_map;
-  }
+  MaybeObject* maybe_new_map = obj->map()->CopyReplaceDescriptors(descriptors);
+  if (!maybe_new_map->To(&new_map)) return maybe_new_map;
 
   new_map->set_unused_property_fields(unused_property_fields);
 
index 01bd0c1a53bd94be743f20cc48b640b456727b00..fcffd253d6a89b4daf6b56b39d4d71f3b163ba15 100644 (file)
@@ -2548,20 +2548,12 @@ class DescriptorArray: public FixedArray {
   inline void Append(Descriptor* desc,
                      const WhitenessWitness&);
 
-  // Transfer a complete descriptor from the src descriptor array to the dst
-  // one, dropping map transitions in CALLBACKS.
-  static void CopyFrom(Handle<DescriptorArray> dst,
-                       int dst_index,
-                       Handle<DescriptorArray> src,
-                       int src_index,
-                       const WhitenessWitness& witness);
-
   // Transfer a complete descriptor from the src descriptor array to this
-  // descriptor array, dropping map transitions in CALLBACKS.
-  MUST_USE_RESULT MaybeObject* CopyFrom(int dst_index,
-                                        DescriptorArray* src,
-                                        int src_index,
-                                        const WhitenessWitness&);
+  // descriptor array.
+  void CopyFrom(int dst_index,
+                DescriptorArray* src,
+                int src_index,
+                const WhitenessWitness&);
 
   // Copy the descriptor array, insert a new descriptor and optionally
   // remove map transitions.  If the descriptor is already present, it is
@@ -4815,8 +4807,8 @@ class Map: public HeapObject {
   MUST_USE_RESULT inline MaybeObject* set_elements_transition_map(
       Map* transitioned_map);
   inline TransitionArray* transitions();
-  inline void SetTransition(int index, Object* value);
-  MUST_USE_RESULT inline MaybeObject* AddTransition(String* key, Object* value);
+  inline void SetTransition(int index, Map* target);
+  MUST_USE_RESULT inline MaybeObject* AddTransition(String* key, Map* target);
   MUST_USE_RESULT inline MaybeObject* set_transitions(
       TransitionArray* transitions);
   inline void ClearTransitions(Heap* heap,
@@ -8347,7 +8339,7 @@ class AccessorPair: public Struct {
 
   static inline AccessorPair* cast(Object* obj);
 
-  MUST_USE_RESULT MaybeObject* CopyWithoutTransitions();
+  MUST_USE_RESULT MaybeObject* Copy();
 
   Object* get(AccessorComponent component) {
     return component == ACCESSOR_GETTER ? getter() : setter();
index 6ec826c1406bef800b804a1557416d5d8881f89f..a94754061a2ec6bbf0f8cb38e1f06af3a3cfab9f 100644 (file)
@@ -236,12 +236,6 @@ class LookupResult BASE_EMBEDDED {
     return details_.type() == CALLBACKS;
   }
 
-  // Is callbacks contains both property callbacks and transitions to callbacks.
-  bool IsCallbacks() {
-    return IsPropertyCallbacks() ||
-           (IsTransition() && GetTransitionValue()->IsAccessorPair());
-  }
-
   bool IsReadOnly() {
     ASSERT(IsFound());
     ASSERT(!IsTransition());
@@ -299,11 +293,10 @@ class LookupResult BASE_EMBEDDED {
     }
   }
 
-  Object* GetTransitionValue() {
+  Map* GetTransitionTarget() {
     ASSERT(IsTransition());
     TransitionArray* transitions = holder()->map()->transitions();
-    Object* value = transitions->GetValue(number_);
-    return value;
+    return transitions->GetTarget(number_);
   }
 
   PropertyDetails GetTransitionDetails(Map* map) {
@@ -327,7 +320,7 @@ class LookupResult BASE_EMBEDDED {
 
   Map* GetTransitionMapFromMap(Map* map) {
     ASSERT(IsTransition());
-    return Map::cast(map->transitions()->GetValue(number_));
+    return map->transitions()->GetTarget(number_);
   }
 
   int GetTransitionIndex() {
@@ -363,14 +356,11 @@ class LookupResult BASE_EMBEDDED {
   }
 
   Object* GetCallbackObject() {
-    switch (lookup_type_) {
-      case CONSTANT_TYPE:
-        return HEAP->prototype_accessors();
-      case TRANSITION_TYPE:
-        return GetTransitionValue();
-      default:
-        return GetValue();
+    if (lookup_type_ == CONSTANT_TYPE) {
+      return HEAP->prototype_accessors();
     }
+    ASSERT(!IsTransition());
+    return GetValue();
   }
 
 #ifdef OBJECT_PRINT
index ddbee6d12537e5be4420a8f261a7fa52e62a5c74..fc0cce115cf84267b91da9790f6a14314ea72b28 100644 (file)
@@ -1530,7 +1530,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareContextSlot) {
         !object->IsJSContextExtensionObject()) {
       LookupResult lookup(isolate);
       object->Lookup(*name, &lookup);
-      if (lookup.IsCallbacks()) {
+      if (lookup.IsPropertyCallbacks()) {
         return ThrowRedeclarationError(isolate, "const", name);
       }
     }
@@ -4531,7 +4531,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DefineOrRedefineDataProperty) {
   js_object->LocalLookupRealNamedProperty(*name, &result);
 
   // Special case for callback properties.
-  if (result.IsCallbacks()) {
+  if (result.IsPropertyCallbacks()) {
     Object* callback = result.GetCallbackObject();
     // To be compatible with Safari we do not change the value on API objects
     // in Object.defineProperty(). Firefox disagrees here, and actually changes
index 16496ddd2d7e76a31167dfc91562771bc65823ad..0de98541526ef4936525863ed03bf4aa7d34b3d7 100644 (file)
@@ -138,44 +138,28 @@ void TransitionArray::SetKey(int transition_number, String* key) {
 }
 
 
-Object* TransitionArray::GetValue(int transition_number) {
+Map* TransitionArray::GetTarget(int transition_number) {
   ASSERT(transition_number < number_of_transitions());
-  return get(ToValueIndex(transition_number));
+  return Map::cast(get(ToTargetIndex(transition_number)));
 }
 
 
-Object** TransitionArray::GetValueSlot(int transition_number) {
+Object** TransitionArray::GetTargetSlot(int transition_number) {
   ASSERT(transition_number < number_of_transitions());
   return HeapObject::RawField(
       reinterpret_cast<HeapObject*>(this),
-      OffsetOfElementAt(ToValueIndex(transition_number)));
+      OffsetOfElementAt(ToTargetIndex(transition_number)));
 }
 
 
-void TransitionArray::SetValue(int transition_number, Object* value) {
+void TransitionArray::SetTarget(int transition_number, Map* value) {
   ASSERT(transition_number < number_of_transitions());
-  set(ToValueIndex(transition_number), value);
-}
-
-
-Map* TransitionArray::GetTargetMap(int transition_number) {
-  Object* value = GetValue(transition_number);
-  if (value->IsAccessorPair()) {
-    // TODO(verwaest): Currently details are always taken from the getter if it
-    // is a transition, otherwise from the setter which in that case has to be a
-    // transition. Details should be dependent on which component is requested.
-    AccessorPair* accessors = AccessorPair::cast(value);
-    if (accessors->getter()->IsMap()) {
-      return Map::cast(accessors->getter());
-    }
-    return Map::cast(accessors->setter());
-  }
-  return Map::cast(value);
+  set(ToTargetIndex(transition_number), value);
 }
 
 
 PropertyDetails TransitionArray::GetTargetDetails(int transition_number) {
-  Map* map = GetTargetMap(transition_number);
+  Map* map = GetTarget(transition_number);
   DescriptorArray* descriptors = map->instance_descriptors();
   int descriptor = descriptors->LastAdded();
   ASSERT(descriptor != DescriptorArray::kNotFound);
@@ -196,14 +180,14 @@ int TransitionArray::Search(String* name) {
 
 void TransitionArray::Set(int transition_number,
                           String* key,
-                          Object* value,
+                          Map* target,
                           const WhitenessWitness&) {
   NoIncrementalWriteBarrierSet(this,
                                ToKeyIndex(transition_number),
                                key);
   NoIncrementalWriteBarrierSet(this,
-                               ToValueIndex(transition_number),
-                               value);
+                               ToTargetIndex(transition_number),
+                               target);
 }
 
 
index 1e965cda716af594d198ab118a01a72bd4a78da8..f2e49ecafec3af954a24602e42a85f5f2f1a7707 100644 (file)
@@ -54,10 +54,10 @@ void TransitionArray::CopyFrom(TransitionArray* origin,
                                int origin_transition,
                                int target_transition,
                                const WhitenessWitness& witness) {
-  this->Set(target_transition,
-            origin->GetKey(origin_transition),
-            origin->GetValue(origin_transition),
-            witness);
+  Set(target_transition,
+      origin->GetKey(origin_transition),
+      origin->GetTarget(origin_transition),
+      witness);
 }
 
 
@@ -66,7 +66,7 @@ static bool InsertionPointFound(String* key1, String* key2) {
 }
 
 
-MaybeObject* TransitionArray::NewWith(String* name, Object* value) {
+MaybeObject* TransitionArray::NewWith(String* name, Map* target) {
   TransitionArray* result;
 
   { MaybeObject* maybe_array;
@@ -76,12 +76,12 @@ MaybeObject* TransitionArray::NewWith(String* name, Object* value) {
 
   FixedArray::WhitenessWitness witness(result);
 
-  result->Set(0, name, value, witness);
+  result->Set(0, name, target, witness);
   return result;
 }
 
 
-MaybeObject* TransitionArray::CopyInsert(String* name, Object* value) {
+MaybeObject* TransitionArray::CopyInsert(String* name, Map* target) {
   TransitionArray* result;
 
   int number_of_transitions = this->number_of_transitions();
@@ -90,10 +90,9 @@ MaybeObject* TransitionArray::CopyInsert(String* name, Object* value) {
   int insertion_index = this->Search(name);
   if (insertion_index == kNotFound) ++new_size;
 
-  { MaybeObject* maybe_array;
-    maybe_array = TransitionArray::Allocate(new_size);
-    if (!maybe_array->To(&result)) return maybe_array;
-  }
+  MaybeObject* maybe_array;
+  maybe_array = TransitionArray::Allocate(new_size);
+  if (!maybe_array->To(&result)) return maybe_array;
 
   if (HasElementsTransition()) {
     result->set_elements_transition(elements_transition());
@@ -109,7 +108,7 @@ MaybeObject* TransitionArray::CopyInsert(String* name, Object* value) {
     for (int i = 0; i < number_of_transitions; ++i) {
       if (i != insertion_index) result->CopyFrom(this, i, i, witness);
     }
-    result->Set(insertion_index, name, value, witness);
+    result->Set(insertion_index, name, target, witness);
     return result;
   }
 
@@ -119,7 +118,7 @@ MaybeObject* TransitionArray::CopyInsert(String* name, Object* value) {
     result->CopyFrom(this, insertion_index, insertion_index, witness);
   }
 
-  result->Set(insertion_index, name, value, witness);
+  result->Set(insertion_index, name, target, witness);
 
   for (; insertion_index < number_of_transitions; ++insertion_index) {
     result->CopyFrom(this, insertion_index, insertion_index + 1, witness);
index a4b5b2760b905c21e19f2d6670104e0eeca7cebb..7acb88fdaf7f4c1a33dda0b548824a5f45020d10 100644 (file)
@@ -51,16 +51,15 @@ class TransitionArray: public FixedArray {
   inline void SetKey(int transition_number, String* value);
   inline Object** GetKeySlot(int transition_number);
 
-  inline Object* GetValue(int transition_number);
-  inline void SetValue(int transition_number, Object* value);
-  inline Object** GetValueSlot(int transition_number);
+  inline Map* GetTarget(int transition_number);
+  inline void SetTarget(int transition_number, Map* target);
+  inline Object** GetTargetSlot(int transition_number);
 
-  inline Map* GetTargetMap(int transition_number);
   inline PropertyDetails GetTargetDetails(int transition_number);
 
   inline Map* elements_transition();
   inline void set_elements_transition(
-      Map* value,
+      Map* target,
       WriteBarrierMode mode = UPDATE_WRITE_BARRIER);
   inline Object** GetElementsTransitionSlot();
   inline bool HasElementsTransition();
@@ -84,12 +83,12 @@ class TransitionArray: public FixedArray {
   inline int number_of_entries() { return number_of_transitions(); }
 
   // Allocate a new transition array with a single entry.
-  static MUST_USE_RESULT MaybeObject* NewWith(String* name, Object* map);
+  static MUST_USE_RESULT MaybeObject* NewWith(String* name, Map* target);
 
   // Copy the transition array, inserting a new transition.
   // TODO(verwaest): This should not cause an existing transition to be
   // overwritten.
-  MUST_USE_RESULT MaybeObject* CopyInsert(String* name, Object* map);
+  MUST_USE_RESULT MaybeObject* CopyInsert(String* name, Map* target);
 
   // Copy a single transition from the origin array.
   inline void CopyFrom(TransitionArray* origin,
@@ -121,7 +120,7 @@ class TransitionArray: public FixedArray {
 
   // Layout of map transition.
   static const int kTransitionKey = 0;
-  static const int kTransitionValue = 1;
+  static const int kTransitionTarget = 1;
   static const int kTransitionSize = 2;
 
 #ifdef OBJECT_PRINT
@@ -150,15 +149,15 @@ class TransitionArray: public FixedArray {
            kTransitionKey;
   }
 
-  static int ToValueIndex(int transition_number) {
+  static int ToTargetIndex(int transition_number) {
     return kFirstIndex +
            (transition_number * kTransitionSize) +
-           kTransitionValue;
+           kTransitionTarget;
   }
 
   inline void Set(int transition_number,
                   String* key,
-                  Object* value,
+                  Map* target,
                   const WhitenessWitness&);
 
   DISALLOW_IMPLICIT_CONSTRUCTORS(TransitionArray);