| Index: src/elements.cc
|
| diff --git a/src/elements.cc b/src/elements.cc
|
| index 7b7f6893d84b557224acb1232b7798eb39cbb461..3b181e10506c4a6da30111e431c262d9f235ba67 100644
|
| --- a/src/elements.cc
|
| +++ b/src/elements.cc
|
| @@ -470,6 +470,23 @@ static void SortIndices(
|
| }
|
| }
|
|
|
| +static Object* FillNumberSlowPath(Isolate* isolate, Handle<JSTypedArray> array,
|
| + Handle<Object> obj_value,
|
| + uint32_t start, uint32_t end) {
|
| + const char* kMethodName = "%TypedArray%.prototype.fill";
|
| + Handle<Object> cast_value;
|
| + ElementsAccessor* elements = array->GetElementsAccessor();
|
| +
|
| + for (uint32_t k = start; k < end; ++k) {
|
| + ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
|
| + isolate, cast_value, Object::ToNumber(obj_value));
|
| + // TODO(caitp,cbruni): throw on neutered array
|
| + if (V8_UNLIKELY(array->WasNeutered())) return *array;
|
| + elements->Set(array, k, *cast_value);
|
| + }
|
| + return *array;
|
| +}
|
| +
|
| static Maybe<bool> IncludesValueSlowPath(Isolate* isolate,
|
| Handle<JSObject> receiver,
|
| Handle<Object> value,
|
| @@ -1191,6 +1208,17 @@ class ElementsAccessorBase : public ElementsAccessor {
|
| return Subclass::GetCapacityImpl(holder, backing_store);
|
| }
|
|
|
| + static Object* FillImpl(Isolate* isolate, Handle<JSObject> receiver,
|
| + Handle<Object> obj_value, uint32_t start, uint32_t end) {
|
| + UNREACHABLE();
|
| + return *receiver;
|
| + }
|
| +
|
| + Object* Fill(Isolate* isolate, Handle<JSObject> receiver,
|
| + Handle<Object> obj_value, uint32_t start, uint32_t end) {
|
| + return Subclass::FillImpl(isolate, receiver, obj_value, start, end);
|
| + }
|
| +
|
| static Maybe<bool> IncludesValueImpl(Isolate* isolate,
|
| Handle<JSObject> receiver,
|
| Handle<Object> value,
|
| @@ -2815,6 +2843,60 @@ class TypedElementsAccessor
|
| return Just(true);
|
| }
|
|
|
| + static inline uint8_t ConvertNumberToUint8Clamped(Handle<Object> obj_value) {
|
| + if (obj_value->IsSmi()) {
|
| + int value = Smi::cast(*obj_value)->value();
|
| + value = std::min<int>(std::max<int>(0, value), 255);
|
| + return static_cast<uint8_t>(value);
|
| + } else {
|
| + DCHECK(obj_value->IsHeapNumber());
|
| + double value = 0.0;
|
| + value = HeapNumber::cast(*obj_value)->value();
|
| + value = std::rint(value);
|
| + value = std::min<double>(std::max<double>(0, value), 255);
|
| + return static_cast<uint8_t>(value);
|
| + }
|
| + }
|
| +
|
| + static inline ctype ConvertToNumber(Handle<Object> obj_value) {
|
| + ctype value = 0;
|
| + if (obj_value->IsSmi()) {
|
| + value = static_cast<ctype>(Smi::cast(*obj_value)->value());
|
| + } else {
|
| + DCHECK(obj_value->IsHeapNumber());
|
| + value = static_cast<ctype>(HeapNumber::cast(*obj_value)->value());
|
| + }
|
| + return value;
|
| + }
|
| +
|
| + static Object* FillImpl(Isolate* isolate, Handle<JSObject> receiver,
|
| + Handle<Object> obj_value, uint32_t start, uint32_t end) {
|
| + Handle<JSTypedArray> array = Handle<JSTypedArray>::cast(receiver);
|
| + DCHECK(!array->WasNeutered());
|
| +
|
| + if (!obj_value->IsNumber()) {
|
| + return FillNumberSlowPath(isolate, array, obj_value, start, end);
|
| + }
|
| +
|
| + ctype value = 0;
|
| + if (Kind == UINT8_CLAMPED_ELEMENTS) {
|
| + value = ConvertNumberToUint8Clamped(obj_value);
|
| + } else {
|
| + value = ConvertToNumber(obj_value);
|
| + }
|
| +
|
| + // Ensure indexes are within array bounds
|
| + DCHECK_LE(0, start);
|
| + DCHECK_LE(start, end);
|
| + DCHECK_LE(end, array->length_value());
|
| +
|
| + DisallowHeapAllocation no_gc;
|
| + BackingStore* elements = BackingStore::cast(receiver->elements());
|
| + ctype* data = static_cast<ctype*>(elements->DataPtr());
|
| + std::fill(data + start, data + end, value);
|
| + return *array;
|
| + }
|
| +
|
| static Maybe<bool> IncludesValueImpl(Isolate* isolate,
|
| Handle<JSObject> receiver,
|
| Handle<Object> value,
|
|
|