| Index: src/runtime.cc
|
| diff --git a/src/runtime.cc b/src/runtime.cc
|
| index 81018fe6b1ac7d020d1824e8e2c576669cd8ec5c..6cf8610854f89c55a04b7abe986fc273a060d67c 100644
|
| --- a/src/runtime.cc
|
| +++ b/src/runtime.cc
|
| @@ -501,6 +501,30 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CreateObjectLiteralShallow) {
|
| }
|
|
|
|
|
| +static Handle<AllocationSite> GetLiteralAllocationSite(
|
| + Isolate* isolate,
|
| + Handle<FixedArray> literals,
|
| + int literals_index,
|
| + Handle<FixedArray> elements) {
|
| + // Check if boilerplate exists. If not, create it first.
|
| + Handle<Object> literal_site(literals->get(literals_index), isolate);
|
| + Handle<AllocationSite> site;
|
| + if (*literal_site == isolate->heap()->undefined_value()) {
|
| + ASSERT(*elements != isolate->heap()->empty_fixed_array());
|
| + Handle<Object> boilerplate =
|
| + Runtime::CreateArrayLiteralBoilerplate(isolate, literals, elements);
|
| + if (boilerplate.is_null()) return site;
|
| + site = isolate->factory()->NewAllocationSite();
|
| + site->set_payload(*boilerplate);
|
| + literals->set(literals_index, *site);
|
| + } else {
|
| + site = Handle<AllocationSite>::cast(literal_site);
|
| + }
|
| +
|
| + return site;
|
| +}
|
| +
|
| +
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_CreateArrayLiteral) {
|
| HandleScope scope(isolate);
|
| ASSERT(args.length() == 3);
|
| @@ -508,17 +532,12 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CreateArrayLiteral) {
|
| CONVERT_SMI_ARG_CHECKED(literals_index, 1);
|
| CONVERT_ARG_HANDLE_CHECKED(FixedArray, elements, 2);
|
|
|
| - // Check if boilerplate exists. If not, create it first.
|
| - Handle<Object> boilerplate(literals->get(literals_index), isolate);
|
| - if (*boilerplate == isolate->heap()->undefined_value()) {
|
| - ASSERT(*elements != isolate->heap()->empty_fixed_array());
|
| - boilerplate =
|
| - Runtime::CreateArrayLiteralBoilerplate(isolate, literals, elements);
|
| - RETURN_IF_EMPTY_HANDLE(isolate, boilerplate);
|
| - // Update the functions literal and return the boilerplate.
|
| - literals->set(literals_index, *boilerplate);
|
| - }
|
| - return JSObject::cast(*boilerplate)->DeepCopy(isolate);
|
| + Handle<AllocationSite> site = GetLiteralAllocationSite(isolate, literals,
|
| + literals_index, elements);
|
| + RETURN_IF_EMPTY_HANDLE(isolate, site);
|
| +
|
| + JSObject* boilerplate = JSObject::cast(site->payload());
|
| + return boilerplate->DeepCopy(isolate);
|
| }
|
|
|
|
|
| @@ -529,29 +548,24 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CreateArrayLiteralShallow) {
|
| CONVERT_SMI_ARG_CHECKED(literals_index, 1);
|
| CONVERT_ARG_HANDLE_CHECKED(FixedArray, elements, 2);
|
|
|
| - // Check if boilerplate exists. If not, create it first.
|
| - Handle<Object> boilerplate(literals->get(literals_index), isolate);
|
| - if (*boilerplate == isolate->heap()->undefined_value()) {
|
| - ASSERT(*elements != isolate->heap()->empty_fixed_array());
|
| - boilerplate =
|
| - Runtime::CreateArrayLiteralBoilerplate(isolate, literals, elements);
|
| - RETURN_IF_EMPTY_HANDLE(isolate, boilerplate);
|
| - // Update the functions literal and return the boilerplate.
|
| - literals->set(literals_index, *boilerplate);
|
| - }
|
| - if (JSObject::cast(*boilerplate)->elements()->map() ==
|
| + Handle<AllocationSite> site = GetLiteralAllocationSite(isolate, literals,
|
| + literals_index, elements);
|
| + RETURN_IF_EMPTY_HANDLE(isolate, site);
|
| +
|
| + JSObject* boilerplate = JSObject::cast(site->payload());
|
| + if (boilerplate->elements()->map() ==
|
| isolate->heap()->fixed_cow_array_map()) {
|
| isolate->counters()->cow_arrays_created_runtime()->Increment();
|
| }
|
|
|
| - JSObject* boilerplate_object = JSObject::cast(*boilerplate);
|
| - AllocationSiteMode mode = AllocationSiteInfo::GetMode(
|
| - boilerplate_object->GetElementsKind());
|
| + AllocationSiteMode mode = AllocationSite::GetMode(
|
| + boilerplate->GetElementsKind());
|
| if (mode == TRACK_ALLOCATION_SITE) {
|
| - return isolate->heap()->CopyJSObjectWithAllocationSite(boilerplate_object);
|
| + return isolate->heap()->CopyJSObjectWithAllocationSite(
|
| + boilerplate, *site);
|
| }
|
|
|
| - return isolate->heap()->CopyJSObject(boilerplate_object);
|
| + return isolate->heap()->CopyJSObject(boilerplate);
|
| }
|
|
|
|
|
| @@ -5203,8 +5217,15 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StoreArrayLiteralElement) {
|
| CONVERT_ARG_HANDLE_CHECKED(FixedArray, literals, 3);
|
| CONVERT_SMI_ARG_CHECKED(literal_index, 4);
|
|
|
| - Object* raw_boilerplate_object = literals->get(literal_index);
|
| - Handle<JSArray> boilerplate_object(JSArray::cast(raw_boilerplate_object));
|
| + Object* raw_literal_cell = literals->get(literal_index);
|
| + JSArray* boilerplate = NULL;
|
| + if (raw_literal_cell->IsAllocationSite()) {
|
| + AllocationSite* site = AllocationSite::cast(raw_literal_cell);
|
| + boilerplate = JSArray::cast(site->payload());
|
| + } else {
|
| + boilerplate = JSArray::cast(raw_literal_cell);
|
| + }
|
| + Handle<JSArray> boilerplate_object(boilerplate);
|
| ElementsKind elements_kind = object->GetElementsKind();
|
| ASSERT(IsFastElementsKind(elements_kind));
|
| // Smis should never trigger transitions.
|
| @@ -13818,19 +13839,21 @@ static MaybeObject* ArrayConstructorCommon(Isolate* isolate,
|
| MaybeObject* maybe_array;
|
| if (!type_info.is_null() &&
|
| *type_info != isolate->heap()->undefined_value() &&
|
| - Cell::cast(*type_info)->value()->IsSmi() &&
|
| + Cell::cast(*type_info)->value()->IsAllocationSite() &&
|
| can_use_type_feedback) {
|
| - Cell* cell = Cell::cast(*type_info);
|
| - Smi* smi = Smi::cast(cell->value());
|
| - ElementsKind to_kind = static_cast<ElementsKind>(smi->value());
|
| + Handle<Cell> cell = Handle<Cell>::cast(type_info);
|
| + Handle<AllocationSite> site = Handle<AllocationSite>(
|
| + AllocationSite::cast(cell->value()), isolate);
|
| + ASSERT(!site->IsLiteralSite());
|
| + ElementsKind to_kind = site->GetElementsKindPayload();
|
| if (holey && !IsFastHoleyElementsKind(to_kind)) {
|
| to_kind = GetHoleyElementsKind(to_kind);
|
| // Update the allocation site info to reflect the advice alteration.
|
| - cell->set_value(Smi::FromInt(to_kind));
|
| + site->SetElementsKindPayload(to_kind);
|
| }
|
|
|
| maybe_array = isolate->heap()->AllocateJSObjectWithAllocationSite(
|
| - *constructor, type_info);
|
| + *constructor, site);
|
| if (!maybe_array->To(&array)) return maybe_array;
|
| } else {
|
| maybe_array = isolate->heap()->AllocateJSObject(*constructor);
|
|
|