Commit b23b2c10 authored by Peter Marshall's avatar Peter Marshall Committed by Commit Bot

[builtins] Port TypedArrayInitialize to CodeStubAssembler.

Turbofan is a lot slower than Crankshaft at constructing TypedArrays,
because we always go to the C++ builtin. Port the builtin to CSA
to improve performance, and to clean up the implementation, which is
split across multiple files and pieces at the moment.

This CL increases the performance with --future to roughly the same
as with crankshaft.

BUG=v8:5977

Change-Id: I5a4c4b544a735a56290b85bf33c2f3718df7e2b8
Reviewed-on: https://chromium-review.googlesource.com/445717
Commit-Queue: Peter Marshall <petermarshall@chromium.org>
Reviewed-by: 's avatarBenedikt Meurer <bmeurer@chromium.org>
Reviewed-by: 's avatarCamillo Bruni <cbruni@chromium.org>
Cr-Commit-Position: refs/heads/master@{#43518}
parent e4f1862b
......@@ -1546,6 +1546,14 @@ ExternalReference ExternalReference::libc_memchr_function(Isolate* isolate) {
return ExternalReference(Redirect(isolate, FUNCTION_ADDR(libc_memchr)));
}
void* libc_memset(void* string, int character, size_t n) {
return memset(string, character, n);
}
ExternalReference ExternalReference::libc_memset_function(Isolate* isolate) {
return ExternalReference(Redirect(isolate, FUNCTION_ADDR(libc_memset)));
}
ExternalReference ExternalReference::page_flags(Page* page) {
return ExternalReference(reinterpret_cast<Address>(page) +
MemoryChunk::kFlagsOffset);
......
......@@ -978,6 +978,7 @@ class ExternalReference BASE_EMBEDDED {
static ExternalReference ieee754_tanh_function(Isolate* isolate);
static ExternalReference libc_memchr_function(Isolate* isolate);
static ExternalReference libc_memset_function(Isolate* isolate);
static ExternalReference page_flags(Page* page);
......
......@@ -2620,6 +2620,13 @@ void Genesis::InitializeGlobal(Handle<JSGlobalObject> global_object,
}
TYPED_ARRAYS(INSTALL_TYPED_ARRAY)
#undef INSTALL_TYPED_ARRAY
// %typed_array_initialize
Handle<JSFunction> typed_array_initialize = SimpleCreateFunction(
isolate, factory->NewStringFromAsciiChecked("typedArrayInitialize"),
Builtins::kTypedArrayInitialize, 6, false);
InstallWithIntrinsicDefaultProto(isolate, typed_array_initialize,
Context::TYPED_ARRAY_INITIALIZE_INDEX);
}
{ // -- D a t a V i e w
......
This diff is collapsed.
......@@ -805,6 +805,7 @@ class Isolate;
TFJ(SymbolPrototypeValueOf, 0) \
\
/* TypedArray */ \
TFJ(TypedArrayInitialize, 6) \
CPP(TypedArrayPrototypeBuffer) \
/* ES6 section 22.2.3.2 get %TypedArray%.prototype.byteLength */ \
TFJ(TypedArrayPrototypeByteLength, 0) \
......
......@@ -68,6 +68,7 @@ enum ContextLookupFlags {
V(REFLECT_DELETE_PROPERTY_INDEX, JSFunction, reflect_delete_property) \
V(SPREAD_ARGUMENTS_INDEX, JSFunction, spread_arguments) \
V(SPREAD_ITERABLE_INDEX, JSFunction, spread_iterable) \
V(TYPED_ARRAY_INITIALIZE_INDEX, JSFunction, typed_array_initialize) \
V(MATH_FLOOR_INDEX, JSFunction, math_floor) \
V(MATH_POW_INDEX, JSFunction, math_pow) \
V(NEW_PROMISE_CAPABILITY_INDEX, JSFunction, new_promise_capability) \
......
......@@ -233,6 +233,8 @@ void ExternalReferenceTable::AddReferences(Isolate* isolate) {
"wasm::call_trap_callback_for_testing");
Add(ExternalReference::libc_memchr_function(isolate).address(),
"libc_memchr");
Add(ExternalReference::libc_memset_function(isolate).address(),
"libc_memset");
Add(ExternalReference::log_enter_external_function(isolate).address(),
"Logger::EnterExternal");
Add(ExternalReference::log_leave_external_function(isolate).address(),
......
......@@ -2017,23 +2017,20 @@ Handle<JSSetIterator> Factory::NewJSSetIterator() {
JSSetIterator);
}
namespace {
ElementsKind GetExternalArrayElementsKind(ExternalArrayType type) {
switch (type) {
ExternalArrayType Factory::GetArrayTypeFromElementsKind(ElementsKind kind) {
switch (kind) {
#define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
case kExternal##Type##Array: \
return TYPE##_ELEMENTS;
case TYPE##_ELEMENTS: \
return kExternal##Type##Array;
TYPED_ARRAYS(TYPED_ARRAY_CASE)
default:
UNREACHABLE();
return kExternalInt8Array;
}
UNREACHABLE();
return FIRST_FIXED_TYPED_ARRAY_ELEMENTS_KIND;
#undef TYPED_ARRAY_CASE
}
size_t GetExternalArrayElementSize(ExternalArrayType type) {
size_t Factory::GetExternalArrayElementSize(ExternalArrayType type) {
switch (type) {
#define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
case kExternal##Type##Array: \
......@@ -2046,30 +2043,29 @@ size_t GetExternalArrayElementSize(ExternalArrayType type) {
#undef TYPED_ARRAY_CASE
}
namespace {
size_t GetFixedTypedArraysElementSize(ElementsKind kind) {
switch (kind) {
ElementsKind GetExternalArrayElementsKind(ExternalArrayType type) {
switch (type) {
#define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
case TYPE##_ELEMENTS: \
return size;
case kExternal##Type##Array: \
return TYPE##_ELEMENTS;
TYPED_ARRAYS(TYPED_ARRAY_CASE)
default:
UNREACHABLE();
return 0;
}
UNREACHABLE();
return FIRST_FIXED_TYPED_ARRAY_ELEMENTS_KIND;
#undef TYPED_ARRAY_CASE
}
ExternalArrayType GetArrayTypeFromElementsKind(ElementsKind kind) {
size_t GetFixedTypedArraysElementSize(ElementsKind kind) {
switch (kind) {
#define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
case TYPE##_ELEMENTS: \
return kExternal##Type##Array;
return size;
TYPED_ARRAYS(TYPED_ARRAY_CASE)
default:
UNREACHABLE();
return kExternalInt8Array;
return 0;
}
#undef TYPED_ARRAY_CASE
}
......
......@@ -536,6 +536,9 @@ class V8_EXPORT_PRIVATE Factory final {
SharedFlag shared = SharedFlag::kNotShared,
PretenureFlag pretenure = NOT_TENURED);
ExternalArrayType GetArrayTypeFromElementsKind(ElementsKind kind);
size_t GetExternalArrayElementSize(ExternalArrayType type);
Handle<JSTypedArray> NewJSTypedArray(ExternalArrayType type,
PretenureFlag pretenure = NOT_TENURED);
......
......@@ -169,13 +169,14 @@ function NAMEConstructByArrayBuffer(obj, buffer, byteOffset, length) {
throw %make_range_error(kInvalidTypedArrayLength);
}
}
%_TypedArrayInitialize(obj, ARRAY_ID, buffer, offset, newByteLength, true);
var newLength = newByteLength / ELEMENT_SIZE;
%typed_array_initialize(obj, newLength, buffer, offset, newByteLength, true);
}
function NAMEConstructByLength(obj, length) {
var l = IS_UNDEFINED(length) ?
0 : ToIndex(length, kInvalidTypedArrayLength);
if (length > %_MaxSmi()) {
if (l > %_MaxSmi()) {
// Note: this is not per spec, but rather a constraint of our current
// representation (which uses smi's).
throw %make_range_error(kInvalidTypedArrayLength);
......@@ -183,9 +184,9 @@ function NAMEConstructByLength(obj, length) {
var byteLength = l * ELEMENT_SIZE;
if (byteLength > %_TypedArrayMaxSizeInHeap()) {
var buffer = new GlobalArrayBuffer(byteLength);
%_TypedArrayInitialize(obj, ARRAY_ID, buffer, 0, byteLength, true);
%typed_array_initialize(obj, l, buffer, 0, byteLength, true);
} else {
%_TypedArrayInitialize(obj, ARRAY_ID, null, 0, byteLength, true);
%typed_array_initialize(obj, l, null, 0, byteLength, true);
}
}
......@@ -198,7 +199,7 @@ function NAMEConstructByArrayLike(obj, arrayLike, length) {
var initialized = false;
var byteLength = l * ELEMENT_SIZE;
if (byteLength <= %_TypedArrayMaxSizeInHeap()) {
%_TypedArrayInitialize(obj, ARRAY_ID, null, 0, byteLength, false);
%typed_array_initialize(obj, l, null, 0, byteLength, false);
} else {
initialized =
%TypedArrayInitializeFromArrayLike(obj, ARRAY_ID, arrayLike, l);
......
......@@ -822,3 +822,12 @@ function TestNonConfigurableProperties(constructor) {
for(i = 0; i < typedArrayConstructors.length; i++) {
TestNonConfigurableProperties(typedArrayConstructors[i]);
}
(function TestInitialization() {
for (var i = 0; i <= 128; i++) {
var arr = new Uint8Array(i);
for (var j = 0; j < i; j++) {
assertEquals(0, arr[j]);
}
}
})();
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment