summaryrefslogtreecommitdiff
path: root/deps/v8/src/builtins/builtins-array-gen.cc
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/builtins/builtins-array-gen.cc')
-rw-r--r--deps/v8/src/builtins/builtins-array-gen.cc65
1 files changed, 45 insertions, 20 deletions
diff --git a/deps/v8/src/builtins/builtins-array-gen.cc b/deps/v8/src/builtins/builtins-array-gen.cc
index d61a516422..4aebe2e02b 100644
--- a/deps/v8/src/builtins/builtins-array-gen.cc
+++ b/deps/v8/src/builtins/builtins-array-gen.cc
@@ -212,7 +212,7 @@ Node* ArrayBuiltinsAssembler::FindProcessor(Node* k_value, Node* k) {
context(), original_array, length, method_name);
// In the Spec and our current implementation, the length check is already
// performed in TypedArraySpeciesCreate.
- CSA_ASSERT(this, SmiLessThanOrEqual(CAST(len_), LoadTypedArrayLength(a)));
+ CSA_ASSERT(this, SmiLessThanOrEqual(CAST(len_), LoadJSTypedArrayLength(a)));
fast_typed_array_target_ =
Word32Equal(LoadInstanceType(LoadElements(original_array)),
LoadInstanceType(LoadElements(a)));
@@ -530,10 +530,11 @@ Node* ArrayBuiltinsAssembler::FindProcessor(Node* k_value, Node* k) {
TNode<JSTypedArray> typed_array = CAST(receiver_);
o_ = typed_array;
- TNode<JSArrayBuffer> array_buffer = LoadArrayBufferViewBuffer(typed_array);
+ TNode<JSArrayBuffer> array_buffer =
+ LoadJSArrayBufferViewBuffer(typed_array);
ThrowIfArrayBufferIsDetached(context_, array_buffer, name_);
- len_ = LoadTypedArrayLength(typed_array);
+ len_ = LoadJSTypedArrayLength(typed_array);
Label throw_not_callable(this, Label::kDeferred);
Label distinguish_types(this);
@@ -964,8 +965,7 @@ TF_BUILTIN(ArrayPrototypePop, CodeStubAssembler) {
// 3) Check that the elements backing store isn't copy-on-write.
Node* elements = LoadElements(array_receiver);
- GotoIf(WordEqual(LoadMap(elements),
- LoadRoot(Heap::kFixedCOWArrayMapRootIndex)),
+ GotoIf(WordEqual(LoadMap(elements), LoadRoot(RootIndex::kFixedCOWArrayMap)),
&runtime);
Node* new_length = IntPtrSub(length, IntPtrConstant(1));
@@ -1378,8 +1378,8 @@ TF_BUILTIN(ArrayPrototypeSlice, ArrayPrototypeSliceCodeStubAssembler) {
Goto(&generic_length);
BIND(&load_arguments_length);
- Node* arguments_length =
- LoadObjectField(array_receiver, JSArgumentsObject::kLengthOffset);
+ Node* arguments_length = LoadObjectField(
+ array_receiver, JSArgumentsObjectWithLength::kLengthOffset);
GotoIf(TaggedIsNotSmi(arguments_length), &generic_length);
o = CAST(receiver);
len.Bind(arguments_length);
@@ -1524,19 +1524,23 @@ TF_BUILTIN(ArrayPrototypeShift, CodeStubAssembler) {
{
TNode<JSArray> array_receiver = CAST(receiver);
CSA_ASSERT(this, TaggedIsPositiveSmi(LoadJSArrayLength(array_receiver)));
+
+ // 2) Ensure that the length is writable.
+ // This check needs to happen before the check for length zero.
+ // The spec requires a "SetProperty(array, 'length', 0)" call when
+ // the length is zero. This must throw an exception in the case of a
+ // read-only length.
+ EnsureArrayLengthWritable(LoadMap(array_receiver), &runtime);
+
Node* length =
LoadAndUntagObjectField(array_receiver, JSArray::kLengthOffset);
Label return_undefined(this), fast_elements_tagged(this),
fast_elements_smi(this);
GotoIf(IntPtrEqual(length, IntPtrConstant(0)), &return_undefined);
- // 2) Ensure that the length is writable.
- EnsureArrayLengthWritable(LoadMap(array_receiver), &runtime);
-
// 3) Check that the elements backing store isn't copy-on-write.
Node* elements = LoadElements(array_receiver);
- GotoIf(WordEqual(LoadMap(elements),
- LoadRoot(Heap::kFixedCOWArrayMapRootIndex)),
+ GotoIf(WordEqual(LoadMap(elements), LoadRoot(RootIndex::kFixedCOWArrayMap)),
&runtime);
Node* new_length = IntPtrSub(length, IntPtrConstant(1));
@@ -1679,15 +1683,38 @@ TF_BUILTIN(ExtractFastJSArray, ArrayBuiltinsAssembler) {
TF_BUILTIN(CloneFastJSArray, ArrayBuiltinsAssembler) {
TNode<Context> context = CAST(Parameter(Descriptor::kContext));
- Node* array = Parameter(Descriptor::kSource);
+ TNode<JSArray> array = CAST(Parameter(Descriptor::kSource));
- CSA_ASSERT(this, IsJSArray(array));
- CSA_ASSERT(this, Word32BinaryNot(IsNoElementsProtectorCellInvalid()));
+ CSA_ASSERT(this,
+ Word32Or(Word32BinaryNot(IsHoleyFastElementsKind(
+ LoadMapElementsKind(LoadMap(array)))),
+ Word32BinaryNot(IsNoElementsProtectorCellInvalid())));
ParameterMode mode = OptimalParameterMode();
Return(CloneFastJSArray(context, array, mode));
}
+// This builtin copies the backing store of fast arrays, while converting any
+// holes to undefined.
+// - If there are no holes in the source, its ElementsKind will be preserved. In
+// that case, this builtin should perform as fast as CloneFastJSArray. (In fact,
+// for fast packed arrays, the behavior is equivalent to CloneFastJSArray.)
+// - If there are holes in the source, the ElementsKind of the "copy" will be
+// PACKED_ELEMENTS (such that undefined can be stored).
+TF_BUILTIN(CloneFastJSArrayFillingHoles, ArrayBuiltinsAssembler) {
+ TNode<Context> context = CAST(Parameter(Descriptor::kContext));
+ TNode<JSArray> array = CAST(Parameter(Descriptor::kSource));
+
+ CSA_ASSERT(this,
+ Word32Or(Word32BinaryNot(IsHoleyFastElementsKind(
+ LoadMapElementsKind(LoadMap(array)))),
+ Word32BinaryNot(IsNoElementsProtectorCellInvalid())));
+
+ ParameterMode mode = OptimalParameterMode();
+ Return(CloneFastJSArray(context, array, mode, nullptr,
+ HoleConversionMode::kConvertToUndefined));
+}
+
TF_BUILTIN(ArrayFindLoopContinuation, ArrayBuiltinsAssembler) {
TNode<Context> context = CAST(Parameter(Descriptor::kContext));
TNode<Object> receiver = CAST(Parameter(Descriptor::kReceiver));
@@ -3582,6 +3609,8 @@ TF_BUILTIN(ArrayIteratorPrototypeNext, CodeStubAssembler) {
BIND(&if_hole);
{
GotoIf(IsNoElementsProtectorCellInvalid(), &if_generic);
+ GotoIfNot(IsPrototypeInitialArrayPrototype(context, array_map),
+ &if_generic);
var_value.Bind(UndefinedConstant());
Goto(&allocate_entry_if_needed);
}
@@ -3654,7 +3683,7 @@ TF_BUILTIN(ArrayIteratorPrototypeNext, CodeStubAssembler) {
// [[ArrayIteratorNextIndex]] anymore, since a JSTypedArray's
// length cannot change anymore, so this {iterator} will never
// produce values again anyways.
- TNode<Smi> length = LoadTypedArrayLength(CAST(array));
+ TNode<Smi> length = LoadJSTypedArrayLength(CAST(array));
GotoIfNot(SmiBelow(CAST(index), length), &allocate_iterator_result);
StoreObjectFieldNoWriteBarrier(iterator, JSArrayIterator::kNextIndexOffset,
SmiInc(CAST(index)));
@@ -3701,8 +3730,6 @@ TF_BUILTIN(ArrayIteratorPrototypeNext, CodeStubAssembler) {
}
}
-namespace {
-
class ArrayFlattenAssembler : public CodeStubAssembler {
public:
explicit ArrayFlattenAssembler(compiler::CodeAssemblerState* state)
@@ -3843,8 +3870,6 @@ class ArrayFlattenAssembler : public CodeStubAssembler {
}
};
-} // namespace
-
// https://tc39.github.io/proposal-flatMap/#sec-FlattenIntoArray
TF_BUILTIN(FlattenIntoArray, ArrayFlattenAssembler) {
Node* const context = Parameter(Descriptor::kContext);