| Index: src/builtins.cc
|
| diff --git a/src/builtins.cc b/src/builtins.cc
|
| index 5104f6d0d144e98eb6343003df40d9f02662ed7e..e005eda0289a05f0d89c31018994d0d8ffb92a4b 100644
|
| --- a/src/builtins.cc
|
| +++ b/src/builtins.cc
|
| @@ -242,11 +242,9 @@ BUILTIN(ArrayCodeGeneric) {
|
| }
|
|
|
| // Set length and elements on the array.
|
| - if (FLAG_smi_only_arrays) {
|
| - MaybeObject* maybe_object =
|
| - array->EnsureCanContainElements(FixedArray::cast(obj));
|
| - if (maybe_object->IsFailure()) return maybe_object;
|
| - }
|
| + MaybeObject* maybe_object =
|
| + array->EnsureCanContainElements(FixedArray::cast(obj));
|
| + if (maybe_object->IsFailure()) return maybe_object;
|
|
|
| AssertNoAllocation no_gc;
|
| FixedArray* elms = FixedArray::cast(obj);
|
| @@ -402,15 +400,36 @@ static bool ArrayPrototypeHasNoElements(Heap* heap,
|
|
|
| MUST_USE_RESULT
|
| static inline MaybeObject* EnsureJSArrayWithWritableFastElements(
|
| - Heap* heap, Object* receiver) {
|
| + Heap* heap, Object* receiver, Arguments* args, int first_added_arg) {
|
| if (!receiver->IsJSArray()) return NULL;
|
| JSArray* array = JSArray::cast(receiver);
|
| HeapObject* elms = array->elements();
|
| - if (elms->map() == heap->fixed_array_map()) return elms;
|
| - if (elms->map() == heap->fixed_cow_array_map()) {
|
| - return array->EnsureWritableFastElements();
|
| + Map* map = elms->map();
|
| + if (map == heap->fixed_array_map()) {
|
| + if (args == NULL || !array->HasFastSmiOnlyElements()) {
|
| + return elms;
|
| + }
|
| + } else if (map == heap->fixed_cow_array_map()) {
|
| + MaybeObject* maybe_writable_result = array->EnsureWritableFastElements();
|
| + if (args == NULL || !array->HasFastSmiOnlyElements() ||
|
| + maybe_writable_result->IsFailure()) {
|
| + return maybe_writable_result;
|
| + }
|
| + } else {
|
| + return NULL;
|
| }
|
| - return NULL;
|
| +
|
| + // Need to ensure that the arguments passed in args can be contained in
|
| + // the array.
|
| + int args_length = args->length();
|
| + if (first_added_arg >= args_length) return array->elements();
|
| +
|
| + MaybeObject* maybe_array = array->EnsureCanContainElements(
|
| + args,
|
| + first_added_arg,
|
| + args_length - first_added_arg);
|
| + if (maybe_array->IsFailure()) return maybe_array;
|
| + return array->elements();
|
| }
|
|
|
|
|
| @@ -457,7 +476,7 @@ BUILTIN(ArrayPush) {
|
| Object* receiver = *args.receiver();
|
| Object* elms_obj;
|
| { MaybeObject* maybe_elms_obj =
|
| - EnsureJSArrayWithWritableFastElements(heap, receiver);
|
| + EnsureJSArrayWithWritableFastElements(heap, receiver, &args, 1);
|
| if (maybe_elms_obj == NULL) {
|
| return CallJsBuiltin(isolate, "ArrayPush", args);
|
| }
|
| @@ -495,9 +514,6 @@ BUILTIN(ArrayPush) {
|
| elms = new_elms;
|
| }
|
|
|
| - MaybeObject* maybe = array->EnsureCanContainElements(&args, 1, to_add);
|
| - if (maybe->IsFailure()) return maybe;
|
| -
|
| // Add the provided values.
|
| AssertNoAllocation no_gc;
|
| WriteBarrierMode mode = elms->GetWriteBarrierMode(no_gc);
|
| @@ -520,7 +536,7 @@ BUILTIN(ArrayPop) {
|
| Object* receiver = *args.receiver();
|
| Object* elms_obj;
|
| { MaybeObject* maybe_elms_obj =
|
| - EnsureJSArrayWithWritableFastElements(heap, receiver);
|
| + EnsureJSArrayWithWritableFastElements(heap, receiver, NULL, 0);
|
| if (maybe_elms_obj == NULL) return CallJsBuiltin(isolate, "ArrayPop", args);
|
| if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
|
| }
|
| @@ -553,7 +569,7 @@ BUILTIN(ArrayShift) {
|
| Object* receiver = *args.receiver();
|
| Object* elms_obj;
|
| { MaybeObject* maybe_elms_obj =
|
| - EnsureJSArrayWithWritableFastElements(heap, receiver);
|
| + EnsureJSArrayWithWritableFastElements(heap, receiver, NULL, 0);
|
| if (maybe_elms_obj == NULL)
|
| return CallJsBuiltin(isolate, "ArrayShift", args);
|
| if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
|
| @@ -595,7 +611,7 @@ BUILTIN(ArrayUnshift) {
|
| Object* receiver = *args.receiver();
|
| Object* elms_obj;
|
| { MaybeObject* maybe_elms_obj =
|
| - EnsureJSArrayWithWritableFastElements(heap, receiver);
|
| + EnsureJSArrayWithWritableFastElements(heap, receiver, NULL, 0);
|
| if (maybe_elms_obj == NULL)
|
| return CallJsBuiltin(isolate, "ArrayUnshift", args);
|
| if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
|
| @@ -614,11 +630,9 @@ BUILTIN(ArrayUnshift) {
|
| // we should never hit this case.
|
| ASSERT(to_add <= (Smi::kMaxValue - len));
|
|
|
| - if (FLAG_smi_only_arrays) {
|
| - MaybeObject* maybe_object =
|
| - array->EnsureCanContainElements(&args, 1, to_add);
|
| - if (maybe_object->IsFailure()) return maybe_object;
|
| - }
|
| + MaybeObject* maybe_object =
|
| + array->EnsureCanContainElements(&args, 1, to_add);
|
| + if (maybe_object->IsFailure()) return maybe_object;
|
|
|
| if (new_length > elms->length()) {
|
| // New backing storage is needed.
|
| @@ -747,11 +761,9 @@ BUILTIN(ArraySlice) {
|
| }
|
| FixedArray* result_elms = FixedArray::cast(result);
|
|
|
| - if (FLAG_smi_only_arrays) {
|
| - MaybeObject* maybe_object =
|
| - result_array->EnsureCanContainElements(result_elms);
|
| - if (maybe_object->IsFailure()) return maybe_object;
|
| - }
|
| + MaybeObject* maybe_object =
|
| + result_array->EnsureCanContainElements(result_elms);
|
| + if (maybe_object->IsFailure()) return maybe_object;
|
|
|
| AssertNoAllocation no_gc;
|
| CopyElements(heap, &no_gc, result_elms, 0, elms, k, result_len);
|
| @@ -770,7 +782,7 @@ BUILTIN(ArraySplice) {
|
| Object* receiver = *args.receiver();
|
| Object* elms_obj;
|
| { MaybeObject* maybe_elms_obj =
|
| - EnsureJSArrayWithWritableFastElements(heap, receiver);
|
| + EnsureJSArrayWithWritableFastElements(heap, receiver, &args, 3);
|
| if (maybe_elms_obj == NULL)
|
| return CallJsBuiltin(isolate, "ArraySplice", args);
|
| if (!maybe_elms_obj->ToObject(&elms_obj)) return maybe_elms_obj;
|
| @@ -857,12 +869,6 @@ BUILTIN(ArraySplice) {
|
| }
|
|
|
| int item_count = (n_arguments > 1) ? (n_arguments - 2) : 0;
|
| -
|
| - if (FLAG_smi_only_arrays) {
|
| - MaybeObject* maybe = array->EnsureCanContainElements(&args, 3, item_count);
|
| - if (maybe->IsFailure()) return maybe;
|
| - }
|
| -
|
| int new_length = len - actual_delete_count + item_count;
|
|
|
| bool elms_changed = false;
|
| @@ -999,15 +1005,13 @@ BUILTIN(ArrayConcat) {
|
| }
|
| FixedArray* result_elms = FixedArray::cast(result);
|
|
|
| - if (FLAG_smi_only_arrays) {
|
| + // Ensure element type transitions happen before copying elements in.
|
| + if (result_array->HasFastSmiOnlyElements()) {
|
| for (int i = 0; i < n_arguments; i++) {
|
| JSArray* array = JSArray::cast(args[i]);
|
| - int len = Smi::cast(array->length())->value();
|
| - if (len > 0) {
|
| - FixedArray* elms = FixedArray::cast(array->elements());
|
| - MaybeObject* maybe_object =
|
| - result_array->EnsureCanContainElements(elms);
|
| - if (maybe_object->IsFailure()) return maybe_object;
|
| + if (!array->HasFastSmiOnlyElements()) {
|
| + result_array->EnsureCanContainNonSmiElements();
|
| + break;
|
| }
|
| }
|
| }
|
|
|