| Index: src/objects.cc
 | 
| diff --git a/src/objects.cc b/src/objects.cc
 | 
| index c02cdd944934dbefdd02b5872735526e5a2f3f20..bbbc8f92796272eeab7ff93d97beebdff015d318 100644
 | 
| --- a/src/objects.cc
 | 
| +++ b/src/objects.cc
 | 
| @@ -7902,6 +7902,31 @@ String* SeqString::Truncate(int new_length) {
 | 
|  }
 | 
|  
 | 
|  
 | 
| +AllocationSiteInfo* AllocationSiteInfo::FindForJSObject(JSObject* object) {
 | 
| +  // Currently, AllocationSiteInfo objects are only allocated immediately
 | 
| +  // after JSArrays in NewSpace, and detecting whether a JSArray has one
 | 
| +  // involves carefully checking the object immediately after the JSArray
 | 
| +  // (if there is one) to see if it's an AllocationSiteInfo.
 | 
| +  if (FLAG_track_allocation_sites && object->GetHeap()->InNewSpace(object)) {
 | 
| +    Address ptr_end = (reinterpret_cast<Address>(object) - kHeapObjectTag) +
 | 
| +        object->Size();
 | 
| +    if ((ptr_end + AllocationSiteInfo::kSize) <=
 | 
| +        object->GetHeap()->NewSpaceTop()) {
 | 
| +      // There is room in newspace for allocation info. Do we have some?
 | 
| +      Map** possible_allocation_site_info_map =
 | 
| +          reinterpret_cast<Map**>(ptr_end);
 | 
| +      if (*possible_allocation_site_info_map ==
 | 
| +          object->GetHeap()->allocation_site_info_map()) {
 | 
| +        AllocationSiteInfo* info = AllocationSiteInfo::cast(
 | 
| +            reinterpret_cast<Object*>(ptr_end + 1));
 | 
| +        return info;
 | 
| +      }
 | 
| +    }
 | 
| +  }
 | 
| +  return NULL;
 | 
| +}
 | 
| +
 | 
| +
 | 
|  uint32_t StringHasher::MakeArrayIndexHash(uint32_t value, int length) {
 | 
|    // For array indexes mix the length into the hash as an array index could
 | 
|    // be zero.
 | 
| @@ -10248,6 +10273,14 @@ MaybeObject* JSObject::SetFastElement(uint32_t index,
 | 
|    }
 | 
|    // Convert to fast double elements if appropriate.
 | 
|    if (HasFastSmiElements() && !value->IsSmi() && value->IsNumber()) {
 | 
| +    // Consider fixing the boilerplate as well if we have one.
 | 
| +    ElementsKind to_kind = IsHoleyElementsKind(elements_kind)
 | 
| +        ? FAST_HOLEY_DOUBLE_ELEMENTS
 | 
| +        : FAST_DOUBLE_ELEMENTS;
 | 
| +
 | 
| +    MaybeObject* trans = PossiblyTransitionArrayBoilerplate(to_kind);
 | 
| +    if (trans != NULL && trans->IsFailure()) return trans;
 | 
| +
 | 
|      MaybeObject* maybe =
 | 
|          SetFastDoubleElementsCapacityAndLength(new_capacity, array_length);
 | 
|      if (maybe->IsFailure()) return maybe;
 | 
| @@ -10789,6 +10822,24 @@ Handle<Object> JSObject::TransitionElementsKind(Handle<JSObject> object,
 | 
|  }
 | 
|  
 | 
|  
 | 
| +MaybeObject* JSObject::PossiblyTransitionArrayBoilerplate(
 | 
| +    ElementsKind to_kind) {
 | 
| +  ASSERT(IsJSArray());
 | 
| +  MaybeObject* ret = NULL;
 | 
| +  AllocationSiteInfo* info = AllocationSiteInfo::FindForJSObject(this);
 | 
| +  if (info != NULL) {
 | 
| +    JSObject* payload = JSObject::cast(info->payload());
 | 
| +    if (payload->GetElementsKind() != to_kind) {
 | 
| +      if (IsMoreGeneralElementsKindTransition(payload->GetElementsKind(),
 | 
| +                                              to_kind)) {
 | 
| +        ret = payload->TransitionElementsKind(to_kind);
 | 
| +      }
 | 
| +    }
 | 
| +  }
 | 
| +  return ret;
 | 
| +}
 | 
| +
 | 
| +
 | 
|  MaybeObject* JSObject::TransitionElementsKind(ElementsKind to_kind) {
 | 
|    ASSERT(!map()->is_observed());
 | 
|    ElementsKind from_kind = map()->elements_kind();
 | 
| @@ -10799,6 +10850,9 @@ MaybeObject* JSObject::TransitionElementsKind(ElementsKind to_kind) {
 | 
|  
 | 
|    if (from_kind == to_kind) return this;
 | 
|  
 | 
| +  MaybeObject* trans = PossiblyTransitionArrayBoilerplate(to_kind);
 | 
| +  if (trans != NULL && trans->IsFailure()) return trans;
 | 
| +
 | 
|    Isolate* isolate = GetIsolate();
 | 
|    if (elements() == isolate->heap()->empty_fixed_array() ||
 | 
|        (IsFastSmiOrObjectElementsKind(from_kind) &&
 | 
| 
 |