From f1a001f6afb36fc09cce59b4c8870579414003a3 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 13 Jul 2022 09:38:58 +0300 Subject: [PATCH 01/10] add fast-path for static array lowering if values is typedarray --- src/bindings/js.ts | 6 +- tests/compiler/bindings/esm.debug.d.ts | 24 ++- tests/compiler/bindings/esm.debug.js | 38 +++-- tests/compiler/bindings/esm.debug.wat | 110 ++++++++++---- tests/compiler/bindings/esm.js | 4 + tests/compiler/bindings/esm.release.d.ts | 24 ++- tests/compiler/bindings/esm.release.js | 38 +++-- tests/compiler/bindings/esm.release.wat | 181 ++++++++++++++--------- tests/compiler/bindings/esm.ts | 8 + tests/compiler/bindings/raw.debug.d.ts | 24 ++- tests/compiler/bindings/raw.debug.js | 36 +++-- tests/compiler/bindings/raw.debug.wat | 110 ++++++++++---- tests/compiler/bindings/raw.release.d.ts | 24 ++- tests/compiler/bindings/raw.release.js | 36 +++-- tests/compiler/bindings/raw.release.wat | 181 ++++++++++++++--------- 15 files changed, 571 insertions(+), 273 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 52f0e6d08d..c4e377323d 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -789,7 +789,11 @@ export class JSBuilder extends ExportsWalker { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + if (ArrayBuffer.isView(values)) { + new (values.constructor)(memory.buffer, buffer, length).set(values); + } else { + for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + } exports.__unpin(buffer); return buffer; } diff --git a/tests/compiler/bindings/esm.debug.d.ts b/tests/compiler/bindings/esm.debug.d.ts index a9d795fee1..686556afd8 100644 --- a/tests/compiler/bindings/esm.debug.d.ts +++ b/tests/compiler/bindings/esm.debug.d.ts @@ -87,6 +87,18 @@ export declare function typedarrayFunction(a: Int16Array, b: Float32Array): BigU * @returns `~lib/staticarray/StaticArray` */ export declare function staticarrayFunction(a: Array, b: Array): Array; +/** + * bindings/esm/staticarrayU16 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ +export declare function staticarrayU16(a: Array): Array; +/** + * bindings/esm/staticarrayI64 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ +export declare function staticarrayI64(a: Array): Array; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` @@ -100,21 +112,21 @@ export declare function arrayFunction(a: Array, b: Array): Array * @param b `bindings/esm/PlainObject` * @returns `bindings/esm/PlainObject` */ -export declare function objectFunction(a: __Record8, b: __Record8): __Record8; +export declare function objectFunction(a: __Record10, b: __Record10): __Record10; /** * bindings/esm/newInternref * @returns `bindings/esm/NonPlainObject` */ -export declare function newInternref(): __Internref11; +export declare function newInternref(): __Internref13; /** * bindings/esm/internrefFunction * @param a `bindings/esm/NonPlainObject` * @param b `bindings/esm/NonPlainObject` * @returns `bindings/esm/NonPlainObject` */ -export declare function internrefFunction(a: __Internref11, b: __Internref11): __Internref11; +export declare function internrefFunction(a: __Internref13, b: __Internref13): __Internref13; /** bindings/esm/PlainObject */ -declare interface __Record8 { +declare interface __Record10 { /** @type `i8` */ a: number | TOmittable; /** @type `i16` */ @@ -149,6 +161,6 @@ declare interface __Record8 { p: Array | null | TOmittable; } /** bindings/esm/NonPlainObject */ -declare class __Internref11 extends Number { - private __nominal11: symbol; +declare class __Internref13 extends Number { + private __nominal13: symbol; } diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index ad6cfd1467..f3dd63ebf2 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -137,10 +137,20 @@ async function instantiate(module, imports = {}) { __release(a); } }, + staticarrayU16(a) { + // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); + }, + staticarrayI64(a) { + // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); + }, arrayFunction(a, b) { // bindings/esm/arrayFunction(~lib/array/Array, ~lib/array/Array) => ~lib/array/Array - a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, a) || __notnull()); - b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, b) || __notnull(); + a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, a) || __notnull()); + b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, b) || __notnull(); try { return __liftArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.arrayFunction(a, b) >>> 0); } finally { @@ -149,10 +159,10 @@ async function instantiate(module, imports = {}) { }, objectFunction(a, b) { // bindings/esm/objectFunction(bindings/esm/PlainObject, bindings/esm/PlainObject) => bindings/esm/PlainObject - a = __retain(__lowerRecord8(a) || __notnull()); - b = __lowerRecord8(b) || __notnull(); + a = __retain(__lowerRecord10(a) || __notnull()); + b = __lowerRecord10(b) || __notnull(); try { - return __liftRecord8(exports.objectFunction(a, b) >>> 0); + return __liftRecord10(exports.objectFunction(a, b) >>> 0); } finally { __release(a); } @@ -172,11 +182,11 @@ async function instantiate(module, imports = {}) { } }, }, exports); - function __lowerRecord8(value) { + function __lowerRecord10(value) { // bindings/esm/PlainObject // Hint: Opt-out from lowering as a record by providing an empty constructor if (value == null) return 0; - const pointer = exports.__pin(exports.__new(68, 8)); + const pointer = exports.__pin(exports.__new(68, 10)); new Int8Array(memory.buffer)[pointer + 0 >>> 0] = value.a; new Int16Array(memory.buffer)[pointer + 2 >>> 1] = value.b; new Int32Array(memory.buffer)[pointer + 4 >>> 2] = value.c; @@ -191,12 +201,12 @@ async function instantiate(module, imports = {}) { new Float32Array(memory.buffer)[pointer + 44 >>> 2] = value.l; new Float64Array(memory.buffer)[pointer + 48 >>> 3] = value.m; new Uint32Array(memory.buffer)[pointer + 56 >>> 2] = __lowerString(value.n); - new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 9, 0, value.o); - new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 10, 2, value.p); + new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 11, 0, value.o); + new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 12, 2, value.p); exports.__unpin(pointer); return pointer; } - function __liftRecord8(pointer) { + function __liftRecord10(pointer) { // bindings/esm/PlainObject // Hint: Opt-out from lifting as a record by providing an empty constructor if (!pointer) return null; @@ -311,7 +321,11 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + if (ArrayBuffer.isView(values)) { + new (values.constructor)(memory.buffer, buffer, length).set(values); + } else { + for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + } exports.__unpin(buffer); return buffer; } @@ -365,6 +379,8 @@ export const { stringFunctionOptional, typedarrayFunction, staticarrayFunction, + staticarrayU16, + staticarrayI64, arrayFunction, objectFunction, newInternref, diff --git a/tests/compiler/bindings/esm.debug.wat b/tests/compiler/bindings/esm.debug.wat index e811a94fe6..b244cd356d 100644 --- a/tests/compiler/bindings/esm.debug.wat +++ b/tests/compiler/bindings/esm.debug.wat @@ -51,9 +51,9 @@ (global $~lib/native/ASC_RUNTIME i32 (i32.const 2)) (global $~argumentsLength (mut i32) (i32.const 0)) (global $~lib/rt/__rtti_base i32 (i32.const 1024)) - (global $~lib/memory/__data_end i32 (i32.const 1124)) - (global $~lib/memory/__stack_pointer (mut i32) (i32.const 17508)) - (global $~lib/memory/__heap_base i32 (i32.const 17508)) + (global $~lib/memory/__data_end i32 (i32.const 1140)) + (global $~lib/memory/__stack_pointer (mut i32) (i32.const 17524)) + (global $~lib/memory/__heap_base i32 (i32.const 17524)) (global $~started (mut i32) (i32.const 0)) (memory $0 1) (data (i32.const 12) "\1c\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\02\00\00\00a\00\00\00\00\00\00\00\00\00\00\00") @@ -76,7 +76,7 @@ (data (i32.const 844) ",\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\1a\00\00\00~\00l\00i\00b\00/\00a\00r\00r\00a\00y\00.\00t\00s\00\00\00") (data (i32.const 892) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00*\00\00\00O\00b\00j\00e\00c\00t\00 \00a\00l\00r\00e\00a\00d\00y\00 \00p\00i\00n\00n\00e\00d\00\00\00") (data (i32.const 956) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00(\00\00\00O\00b\00j\00e\00c\00t\00 \00i\00s\00 \00n\00o\00t\00 \00p\00i\00n\00n\00e\00d\00\00\00\00\00") - (data (i32.const 1024) "\0c\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\02\t\00\00\00\00\00\00\00\00\00\00\00\00\00\00A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 \00\00\00\00\00\00\00") + (data (i32.const 1024) "\0e\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\a4\00\00\00\00\00\00\00$\n\00\00\00\00\00\00\02\t\00\00\00\00\00\00\00\00\00\00\00\00\00\00A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 \00\00\00\00\00\00\00") (table $0 1 1 funcref) (elem $0 (i32.const 1)) (export "plainGlobal" (global $bindings/esm/plainGlobal)) @@ -105,6 +105,8 @@ (export "stringFunctionOptional" (func $export:bindings/esm/stringFunctionOptional@varargs)) (export "typedarrayFunction" (func $export:bindings/esm/typedarrayFunction)) (export "staticarrayFunction" (func $export:bindings/esm/staticarrayFunction)) + (export "staticarrayU16" (func $export:bindings/esm/staticarrayU16)) + (export "staticarrayI64" (func $export:bindings/esm/staticarrayI64)) (export "arrayFunction" (func $export:bindings/esm/arrayFunction)) (export "objectFunction" (func $export:bindings/esm/objectFunction)) (export "internrefFunction" (func $export:bindings/esm/internrefFunction)) @@ -2450,6 +2452,12 @@ local.get $2 call $~lib/staticarray/StaticArray#__uset ) + (func $bindings/esm/staticarrayU16 (param $0 i32) (result i32) + local.get $0 + ) + (func $bindings/esm/staticarrayI64 (param $0 i32) (result i32) + local.get $0 + ) (func $~lib/array/Array#set:buffer (param $0 i32) (param $1 i32) local.get $0 local.get $1 @@ -3064,41 +3072,47 @@ block $~lib/typedarray/Uint8Array block $bindings/esm/PlainObject block $~lib/array/Array - block $~lib/staticarray/StaticArray - block $~lib/typedarray/Uint64Array - block $~lib/typedarray/Float32Array - block $~lib/typedarray/Int16Array - block $~lib/arraybuffer/ArrayBufferView - block $~lib/string/String - block $~lib/arraybuffer/ArrayBuffer - local.get $0 - i32.const 8 - i32.sub - i32.load - br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/typedarray/Int16Array $~lib/typedarray/Float32Array $~lib/typedarray/Uint64Array $~lib/staticarray/StaticArray $~lib/array/Array $bindings/esm/PlainObject $~lib/typedarray/Uint8Array $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/typedarray/Uint64Array + block $~lib/typedarray/Float32Array + block $~lib/typedarray/Int16Array + block $~lib/arraybuffer/ArrayBufferView + block $~lib/string/String + block $~lib/arraybuffer/ArrayBuffer + local.get $0 + i32.const 8 + i32.sub + i32.load + br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/typedarray/Int16Array $~lib/typedarray/Float32Array $~lib/typedarray/Uint64Array $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/array/Array $bindings/esm/PlainObject $~lib/typedarray/Uint8Array $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + end + return + end + return end + local.get $0 + local.get $1 + call $~lib/arraybuffer/ArrayBufferView~visit return end + local.get $0 + local.get $1 + call $~lib/typedarray/Int16Array~visit return end local.get $0 local.get $1 - call $~lib/arraybuffer/ArrayBufferView~visit + call $~lib/typedarray/Float32Array~visit return end local.get $0 local.get $1 - call $~lib/typedarray/Int16Array~visit + call $~lib/typedarray/Uint64Array~visit return end - local.get $0 - local.get $1 - call $~lib/typedarray/Float32Array~visit return end - local.get $0 - local.get $1 - call $~lib/typedarray/Uint64Array~visit return end return @@ -3162,8 +3176,8 @@ global.get $~lib/memory/__data_end i32.lt_s if - i32.const 17536 - i32.const 17584 + i32.const 17552 + i32.const 17600 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3735,7 +3749,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 16 - i32.const 7 + i32.const 9 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -3901,7 +3915,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 68 - i32.const 8 + i32.const 10 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -4015,7 +4029,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 0 - i32.const 11 + i32.const 13 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -4143,6 +4157,44 @@ global.set $~lib/memory/__stack_pointer local.get $2 ) + (func $export:bindings/esm/staticarrayU16 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + call $~stack_check + global.get $~lib/memory/__stack_pointer + local.get $0 + i32.store + local.get $0 + call $bindings/esm/staticarrayU16 + local.set $1 + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $1 + ) + (func $export:bindings/esm/staticarrayI64 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + call $~stack_check + global.get $~lib/memory/__stack_pointer + local.get $0 + i32.store + local.get $0 + call $bindings/esm/staticarrayI64 + local.set $1 + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $1 + ) (func $export:bindings/esm/arrayFunction (param $0 i32) (param $1 i32) (result i32) (local $2 i32) global.get $~lib/memory/__stack_pointer diff --git a/tests/compiler/bindings/esm.js b/tests/compiler/bindings/esm.js index b279d8e09d..a5fcd35982 100644 --- a/tests/compiler/bindings/esm.js +++ b/tests/compiler/bindings/esm.js @@ -55,6 +55,10 @@ export async function postInstantiate(instance) { assert.deepStrictEqual(exports.staticarrayFunction([1, 2, 3], [4, 5, 6]), [1, 2, 3, 4, 5, 6]); + assert.deepStrictEqual(exports.staticarrayU16(Uint16Array.of(1, 2, 3)), [1, 2, 3]); + + assert.deepStrictEqual(exports.staticarrayI64(BigInt64Array.of(1n, 2n, 3n)), [1n, 2n, 3n]); + assert.deepStrictEqual(exports.arrayFunction([1, 2, 3], [4, 5, 6]), [1, 2, 3, 4, 5, 6]); { diff --git a/tests/compiler/bindings/esm.release.d.ts b/tests/compiler/bindings/esm.release.d.ts index a9d795fee1..686556afd8 100644 --- a/tests/compiler/bindings/esm.release.d.ts +++ b/tests/compiler/bindings/esm.release.d.ts @@ -87,6 +87,18 @@ export declare function typedarrayFunction(a: Int16Array, b: Float32Array): BigU * @returns `~lib/staticarray/StaticArray` */ export declare function staticarrayFunction(a: Array, b: Array): Array; +/** + * bindings/esm/staticarrayU16 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ +export declare function staticarrayU16(a: Array): Array; +/** + * bindings/esm/staticarrayI64 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ +export declare function staticarrayI64(a: Array): Array; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` @@ -100,21 +112,21 @@ export declare function arrayFunction(a: Array, b: Array): Array * @param b `bindings/esm/PlainObject` * @returns `bindings/esm/PlainObject` */ -export declare function objectFunction(a: __Record8, b: __Record8): __Record8; +export declare function objectFunction(a: __Record10, b: __Record10): __Record10; /** * bindings/esm/newInternref * @returns `bindings/esm/NonPlainObject` */ -export declare function newInternref(): __Internref11; +export declare function newInternref(): __Internref13; /** * bindings/esm/internrefFunction * @param a `bindings/esm/NonPlainObject` * @param b `bindings/esm/NonPlainObject` * @returns `bindings/esm/NonPlainObject` */ -export declare function internrefFunction(a: __Internref11, b: __Internref11): __Internref11; +export declare function internrefFunction(a: __Internref13, b: __Internref13): __Internref13; /** bindings/esm/PlainObject */ -declare interface __Record8 { +declare interface __Record10 { /** @type `i8` */ a: number | TOmittable; /** @type `i16` */ @@ -149,6 +161,6 @@ declare interface __Record8 { p: Array | null | TOmittable; } /** bindings/esm/NonPlainObject */ -declare class __Internref11 extends Number { - private __nominal11: symbol; +declare class __Internref13 extends Number { + private __nominal13: symbol; } diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index f2b51c2895..e8b25ba01c 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -137,10 +137,20 @@ async function instantiate(module, imports = {}) { __release(a); } }, + staticarrayU16(a) { + // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); + }, + staticarrayI64(a) { + // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); + }, arrayFunction(a, b) { // bindings/esm/arrayFunction(~lib/array/Array, ~lib/array/Array) => ~lib/array/Array - a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, a) || __notnull()); - b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, b) || __notnull(); + a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, a) || __notnull()); + b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, b) || __notnull(); try { return __liftArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.arrayFunction(a, b) >>> 0); } finally { @@ -149,10 +159,10 @@ async function instantiate(module, imports = {}) { }, objectFunction(a, b) { // bindings/esm/objectFunction(bindings/esm/PlainObject, bindings/esm/PlainObject) => bindings/esm/PlainObject - a = __retain(__lowerRecord8(a) || __notnull()); - b = __lowerRecord8(b) || __notnull(); + a = __retain(__lowerRecord10(a) || __notnull()); + b = __lowerRecord10(b) || __notnull(); try { - return __liftRecord8(exports.objectFunction(a, b) >>> 0); + return __liftRecord10(exports.objectFunction(a, b) >>> 0); } finally { __release(a); } @@ -172,11 +182,11 @@ async function instantiate(module, imports = {}) { } }, }, exports); - function __lowerRecord8(value) { + function __lowerRecord10(value) { // bindings/esm/PlainObject // Hint: Opt-out from lowering as a record by providing an empty constructor if (value == null) return 0; - const pointer = exports.__pin(exports.__new(68, 8)); + const pointer = exports.__pin(exports.__new(68, 10)); new Int8Array(memory.buffer)[pointer + 0 >>> 0] = value.a; new Int16Array(memory.buffer)[pointer + 2 >>> 1] = value.b; new Int32Array(memory.buffer)[pointer + 4 >>> 2] = value.c; @@ -191,12 +201,12 @@ async function instantiate(module, imports = {}) { new Float32Array(memory.buffer)[pointer + 44 >>> 2] = value.l; new Float64Array(memory.buffer)[pointer + 48 >>> 3] = value.m; new Uint32Array(memory.buffer)[pointer + 56 >>> 2] = __lowerString(value.n); - new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 9, 0, value.o); - new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 10, 2, value.p); + new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 11, 0, value.o); + new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 12, 2, value.p); exports.__unpin(pointer); return pointer; } - function __liftRecord8(pointer) { + function __liftRecord10(pointer) { // bindings/esm/PlainObject // Hint: Opt-out from lifting as a record by providing an empty constructor if (!pointer) return null; @@ -311,7 +321,11 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + if (ArrayBuffer.isView(values)) { + new (values.constructor)(memory.buffer, buffer, length).set(values); + } else { + for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + } exports.__unpin(buffer); return buffer; } @@ -365,6 +379,8 @@ export const { stringFunctionOptional, typedarrayFunction, staticarrayFunction, + staticarrayU16, + staticarrayI64, arrayFunction, objectFunction, newInternref, diff --git a/tests/compiler/bindings/esm.release.wat b/tests/compiler/bindings/esm.release.wat index 333923028d..7dbfee09d2 100644 --- a/tests/compiler/bindings/esm.release.wat +++ b/tests/compiler/bindings/esm.release.wat @@ -5,12 +5,12 @@ (type $none_=>_i32 (func (result i32))) (type $i32_i32_=>_none (func (param i32 i32))) (type $i32_i32_i32_=>_none (func (param i32 i32 i32))) + (type $i32_=>_i32 (func (param i32) (result i32))) (type $i32_i32_f64_f64_f64_f64_f64_=>_none (func (param i32 i32 f64 f64 f64 f64 f64))) (type $f64_=>_f64 (func (param f64) (result f64))) (type $i64_i64_=>_i64 (func (param i64 i64) (result i64))) (type $i32_i32_i32_i32_=>_none (func (param i32 i32 i32 i32))) (type $i32_i32_i64_=>_none (func (param i32 i32 i64))) - (type $i32_=>_i32 (func (param i32) (result i32))) (import "env" "Math.E" (global $~lib/bindings/dom/Math.E f64)) (import "env" "trace" (func $~lib/builtins/trace (param i32 i32 f64 f64 f64 f64 f64))) (import "env" "console.log" (func $~lib/bindings/dom/console.log (param i32))) @@ -39,7 +39,7 @@ (global $~lib/rt/tlsf/ROOT (mut i32) (i32.const 0)) (global $~argumentsLength (mut i32) (i32.const 0)) (global $~lib/rt/__rtti_base i32 (i32.const 2048)) - (global $~lib/memory/__stack_pointer (mut i32) (i32.const 18532)) + (global $~lib/memory/__stack_pointer (mut i32) (i32.const 18548)) (global $~started (mut i32) (i32.const 0)) (memory $0 1) (data (i32.const 1036) "\1c") @@ -76,9 +76,9 @@ (data (i32.const 1928) "\01\00\00\00*\00\00\00O\00b\00j\00e\00c\00t\00 \00a\00l\00r\00e\00a\00d\00y\00 \00p\00i\00n\00n\00e\00d") (data (i32.const 1980) "<") (data (i32.const 1992) "\01\00\00\00(\00\00\00O\00b\00j\00e\00c\00t\00 \00i\00s\00 \00n\00o\00t\00 \00p\00i\00n\00n\00e\00d") - (data (i32.const 2048) "\0c\00\00\00 \00\00\00\00\00\00\00 ") - (data (i32.const 2076) "\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\02\t") - (data (i32.const 2124) "A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 ") + (data (i32.const 2048) "\0e\00\00\00 \00\00\00\00\00\00\00 ") + (data (i32.const 2076) "\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\a4\00\00\00\00\00\00\00$\n\00\00\00\00\00\00\02\t") + (data (i32.const 2140) "A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 ") (export "plainGlobal" (global $bindings/esm/plainGlobal)) (export "plainMutableGlobal" (global $bindings/esm/plainMutableGlobal)) (export "stringGlobal" (global $bindings/esm/stringGlobal)) @@ -105,6 +105,8 @@ (export "stringFunctionOptional" (func $export:bindings/esm/stringFunctionOptional@varargs)) (export "typedarrayFunction" (func $export:bindings/esm/typedarrayFunction)) (export "staticarrayFunction" (func $export:bindings/esm/staticarrayFunction)) + (export "staticarrayU16" (func $export:bindings/esm/staticarrayU16)) + (export "staticarrayI64" (func $export:bindings/esm/staticarrayU16)) (export "arrayFunction" (func $export:bindings/esm/arrayFunction)) (export "objectFunction" (func $export:bindings/esm/objectFunction)) (export "internrefFunction" (func $export:bindings/esm/internrefFunction)) @@ -188,7 +190,7 @@ if i32.const 0 local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u local.get $0 i32.load offset=8 @@ -843,10 +845,10 @@ if unreachable end - i32.const 18544 + i32.const 18560 i32.const 0 i32.store - i32.const 20112 + i32.const 20128 i32.const 0 i32.store loop $for-loop|0 @@ -857,7 +859,7 @@ local.get $0 i32.const 2 i32.shl - i32.const 18544 + i32.const 18560 i32.add i32.const 0 i32.store offset=4 @@ -875,7 +877,7 @@ i32.add i32.const 2 i32.shl - i32.const 18544 + i32.const 18560 i32.add i32.const 0 i32.store offset=96 @@ -893,13 +895,13 @@ br $for-loop|0 end end - i32.const 18544 - i32.const 20116 + i32.const 18560 + i32.const 20132 memory.size i32.const 16 i32.shl call $~lib/rt/tlsf/addMemory - i32.const 18544 + i32.const 18560 global.set $~lib/rt/tlsf/ROOT ) (func $~lib/rt/itcms/step (result i32) @@ -984,7 +986,7 @@ local.set $0 loop $while-continue|0 local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u if local.get $0 @@ -1084,7 +1086,7 @@ unreachable end local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u if local.get $0 @@ -1107,7 +1109,7 @@ i32.const 4 i32.add local.tee $0 - i32.const 18532 + i32.const 18548 i32.ge_u if global.get $~lib/rt/tlsf/ROOT @@ -1608,11 +1610,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -1916,11 +1918,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -1932,7 +1934,7 @@ i32.store local.get $0 i32.const 0 - i32.const 11 + i32.const 13 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -2097,14 +2099,20 @@ block $bindings/esm/NonPlainObject block $~lib/array/Array<~lib/string/String> block $bindings/esm/PlainObject - block $~lib/staticarray/StaticArray - block $~lib/string/String - block $~lib/arraybuffer/ArrayBuffer - local.get $0 - i32.const 8 - i32.sub - i32.load - br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner0 $folding-inner0 $folding-inner0 $~lib/staticarray/StaticArray $folding-inner1 $bindings/esm/PlainObject $folding-inner0 $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/string/String + block $~lib/arraybuffer/ArrayBuffer + local.get $0 + i32.const 8 + i32.sub + i32.load + br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner0 $folding-inner0 $folding-inner0 $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $folding-inner1 $bindings/esm/PlainObject $folding-inner0 $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + end + return + end + return end return end @@ -2203,11 +2211,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2245,7 +2253,7 @@ memory.size i32.const 16 i32.shl - i32.const 18532 + i32.const 18548 i32.sub i32.const 1 i32.shr_u @@ -2286,7 +2294,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2301,7 +2309,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2325,7 +2333,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2376,8 +2384,8 @@ local.get $5 return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2390,11 +2398,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2423,7 +2431,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2438,7 +2446,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2473,8 +2481,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2492,7 +2500,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2507,7 +2515,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2532,7 +2540,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner00 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner00 global.get $~lib/memory/__stack_pointer @@ -2551,7 +2559,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner00 global.get $~lib/memory/__stack_pointer @@ -2728,8 +2736,8 @@ local.get $2 return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2745,7 +2753,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2762,7 +2770,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2788,7 +2796,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2890,13 +2898,40 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort unreachable ) + (func $export:bindings/esm/staticarrayU16 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + global.get $~lib/memory/__stack_pointer + i32.const 2164 + i32.lt_s + if + i32.const 18576 + i32.const 18624 + i32.const 1 + i32.const 1 + call $~lib/builtins/abort + unreachable + end + global.get $~lib/memory/__stack_pointer + local.tee $1 + local.get $0 + i32.store + local.get $1 + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $0 + ) (func $export:bindings/esm/arrayFunction (param $0 i32) (param $1 i32) (result i32) (local $2 i32) (local $3 i32) @@ -2909,7 +2944,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2928,7 +2963,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2946,7 +2981,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2955,7 +2990,7 @@ i64.store local.get $0 i32.const 16 - i32.const 7 + i32.const 9 call $~lib/rt/itcms/__new local.tee $2 i32.store @@ -3081,8 +3116,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3097,7 +3132,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -3114,7 +3149,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -3126,7 +3161,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -3135,7 +3170,7 @@ i32.store local.get $3 i32.const 68 - i32.const 8 + i32.const 10 call $~lib/rt/itcms/__new local.tee $3 i32.store @@ -3223,8 +3258,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3237,11 +3272,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort diff --git a/tests/compiler/bindings/esm.ts b/tests/compiler/bindings/esm.ts index 944e35d859..8b6511ad48 100644 --- a/tests/compiler/bindings/esm.ts +++ b/tests/compiler/bindings/esm.ts @@ -65,6 +65,14 @@ export function staticarrayFunction(a: StaticArray, b: StaticArray): S return c; } +export function staticarrayU16(a: StaticArray): StaticArray { + return a; +} + +export function staticarrayI64(a: StaticArray): StaticArray { + return a; +} + export function arrayFunction(a: Array, b: Array): Array { var c = new Array(a.length + b.length); for (let i = 0; i < a.length; ++i) { diff --git a/tests/compiler/bindings/raw.debug.d.ts b/tests/compiler/bindings/raw.debug.d.ts index 14bc6d53ec..b7c0627f6e 100644 --- a/tests/compiler/bindings/raw.debug.d.ts +++ b/tests/compiler/bindings/raw.debug.d.ts @@ -88,6 +88,18 @@ declare namespace __AdaptedExports { * @returns `~lib/staticarray/StaticArray` */ export function staticarrayFunction(a: Array, b: Array): Array; + /** + * bindings/esm/staticarrayU16 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ + export function staticarrayU16(a: Array): Array; + /** + * bindings/esm/staticarrayI64 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ + export function staticarrayI64(a: Array): Array; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` @@ -101,22 +113,22 @@ declare namespace __AdaptedExports { * @param b `bindings/esm/PlainObject` * @returns `bindings/esm/PlainObject` */ - export function objectFunction(a: __Record8, b: __Record8): __Record8; + export function objectFunction(a: __Record10, b: __Record10): __Record10; /** * bindings/esm/newInternref * @returns `bindings/esm/NonPlainObject` */ - export function newInternref(): __Internref11; + export function newInternref(): __Internref13; /** * bindings/esm/internrefFunction * @param a `bindings/esm/NonPlainObject` * @param b `bindings/esm/NonPlainObject` * @returns `bindings/esm/NonPlainObject` */ - export function internrefFunction(a: __Internref11, b: __Internref11): __Internref11; + export function internrefFunction(a: __Internref13, b: __Internref13): __Internref13; } /** bindings/esm/PlainObject */ -declare interface __Record8 { +declare interface __Record10 { /** @type `i8` */ a: number | TOmittable; /** @type `i16` */ @@ -151,8 +163,8 @@ declare interface __Record8 { p: Array | null | TOmittable; } /** bindings/esm/NonPlainObject */ -declare class __Internref11 extends Number { - private __nominal11: symbol; +declare class __Internref13 extends Number { + private __nominal13: symbol; } /** Instantiates the compiled WebAssembly module with the given imports. */ export declare function instantiate(module: WebAssembly.Module, imports: { diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index dabcb032b9..9b79cf0b89 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -137,10 +137,20 @@ export async function instantiate(module, imports = {}) { __release(a); } }, + staticarrayU16(a) { + // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); + }, + staticarrayI64(a) { + // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); + }, arrayFunction(a, b) { // bindings/esm/arrayFunction(~lib/array/Array, ~lib/array/Array) => ~lib/array/Array - a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, a) || __notnull()); - b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, b) || __notnull(); + a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, a) || __notnull()); + b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, b) || __notnull(); try { return __liftArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.arrayFunction(a, b) >>> 0); } finally { @@ -149,10 +159,10 @@ export async function instantiate(module, imports = {}) { }, objectFunction(a, b) { // bindings/esm/objectFunction(bindings/esm/PlainObject, bindings/esm/PlainObject) => bindings/esm/PlainObject - a = __retain(__lowerRecord8(a) || __notnull()); - b = __lowerRecord8(b) || __notnull(); + a = __retain(__lowerRecord10(a) || __notnull()); + b = __lowerRecord10(b) || __notnull(); try { - return __liftRecord8(exports.objectFunction(a, b) >>> 0); + return __liftRecord10(exports.objectFunction(a, b) >>> 0); } finally { __release(a); } @@ -172,11 +182,11 @@ export async function instantiate(module, imports = {}) { } }, }, exports); - function __lowerRecord8(value) { + function __lowerRecord10(value) { // bindings/esm/PlainObject // Hint: Opt-out from lowering as a record by providing an empty constructor if (value == null) return 0; - const pointer = exports.__pin(exports.__new(68, 8)); + const pointer = exports.__pin(exports.__new(68, 10)); new Int8Array(memory.buffer)[pointer + 0 >>> 0] = value.a; new Int16Array(memory.buffer)[pointer + 2 >>> 1] = value.b; new Int32Array(memory.buffer)[pointer + 4 >>> 2] = value.c; @@ -191,12 +201,12 @@ export async function instantiate(module, imports = {}) { new Float32Array(memory.buffer)[pointer + 44 >>> 2] = value.l; new Float64Array(memory.buffer)[pointer + 48 >>> 3] = value.m; new Uint32Array(memory.buffer)[pointer + 56 >>> 2] = __lowerString(value.n); - new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 9, 0, value.o); - new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 10, 2, value.p); + new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 11, 0, value.o); + new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 12, 2, value.p); exports.__unpin(pointer); return pointer; } - function __liftRecord8(pointer) { + function __liftRecord10(pointer) { // bindings/esm/PlainObject // Hint: Opt-out from lifting as a record by providing an empty constructor if (!pointer) return null; @@ -311,7 +321,11 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + if (ArrayBuffer.isView(values)) { + new (values.constructor)(memory.buffer, buffer, length).set(values); + } else { + for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + } exports.__unpin(buffer); return buffer; } diff --git a/tests/compiler/bindings/raw.debug.wat b/tests/compiler/bindings/raw.debug.wat index f987fcf6b2..913823f67b 100644 --- a/tests/compiler/bindings/raw.debug.wat +++ b/tests/compiler/bindings/raw.debug.wat @@ -51,9 +51,9 @@ (global $~lib/native/ASC_RUNTIME i32 (i32.const 2)) (global $~argumentsLength (mut i32) (i32.const 0)) (global $~lib/rt/__rtti_base i32 (i32.const 1024)) - (global $~lib/memory/__data_end i32 (i32.const 1124)) - (global $~lib/memory/__stack_pointer (mut i32) (i32.const 17508)) - (global $~lib/memory/__heap_base i32 (i32.const 17508)) + (global $~lib/memory/__data_end i32 (i32.const 1140)) + (global $~lib/memory/__stack_pointer (mut i32) (i32.const 17524)) + (global $~lib/memory/__heap_base i32 (i32.const 17524)) (global $~started (mut i32) (i32.const 0)) (memory $0 1) (data (i32.const 12) "\1c\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\02\00\00\00a\00\00\00\00\00\00\00\00\00\00\00") @@ -76,7 +76,7 @@ (data (i32.const 844) ",\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\1a\00\00\00~\00l\00i\00b\00/\00a\00r\00r\00a\00y\00.\00t\00s\00\00\00") (data (i32.const 892) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00*\00\00\00O\00b\00j\00e\00c\00t\00 \00a\00l\00r\00e\00a\00d\00y\00 \00p\00i\00n\00n\00e\00d\00\00\00") (data (i32.const 956) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00(\00\00\00O\00b\00j\00e\00c\00t\00 \00i\00s\00 \00n\00o\00t\00 \00p\00i\00n\00n\00e\00d\00\00\00\00\00") - (data (i32.const 1024) "\0c\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\02\t\00\00\00\00\00\00\00\00\00\00\00\00\00\00A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 \00\00\00\00\00\00\00") + (data (i32.const 1024) "\0e\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\a4\00\00\00\00\00\00\00$\n\00\00\00\00\00\00\02\t\00\00\00\00\00\00\00\00\00\00\00\00\00\00A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 \00\00\00\00\00\00\00") (table $0 1 1 funcref) (elem $0 (i32.const 1)) (export "plainGlobal" (global $bindings/esm/plainGlobal)) @@ -105,6 +105,8 @@ (export "stringFunctionOptional" (func $export:bindings/esm/stringFunctionOptional@varargs)) (export "typedarrayFunction" (func $export:bindings/esm/typedarrayFunction)) (export "staticarrayFunction" (func $export:bindings/esm/staticarrayFunction)) + (export "staticarrayU16" (func $export:bindings/esm/staticarrayU16)) + (export "staticarrayI64" (func $export:bindings/esm/staticarrayI64)) (export "arrayFunction" (func $export:bindings/esm/arrayFunction)) (export "objectFunction" (func $export:bindings/esm/objectFunction)) (export "internrefFunction" (func $export:bindings/esm/internrefFunction)) @@ -2453,6 +2455,12 @@ local.get $2 call $~lib/staticarray/StaticArray#__uset ) + (func $bindings/esm/staticarrayU16 (param $0 i32) (result i32) + local.get $0 + ) + (func $bindings/esm/staticarrayI64 (param $0 i32) (result i32) + local.get $0 + ) (func $~lib/array/Array#set:buffer (param $0 i32) (param $1 i32) local.get $0 local.get $1 @@ -3067,41 +3075,47 @@ block $~lib/typedarray/Uint8Array block $bindings/esm/PlainObject block $~lib/array/Array - block $~lib/staticarray/StaticArray - block $~lib/typedarray/Uint64Array - block $~lib/typedarray/Float32Array - block $~lib/typedarray/Int16Array - block $~lib/arraybuffer/ArrayBufferView - block $~lib/string/String - block $~lib/arraybuffer/ArrayBuffer - local.get $0 - i32.const 8 - i32.sub - i32.load - br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/typedarray/Int16Array $~lib/typedarray/Float32Array $~lib/typedarray/Uint64Array $~lib/staticarray/StaticArray $~lib/array/Array $bindings/esm/PlainObject $~lib/typedarray/Uint8Array $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/typedarray/Uint64Array + block $~lib/typedarray/Float32Array + block $~lib/typedarray/Int16Array + block $~lib/arraybuffer/ArrayBufferView + block $~lib/string/String + block $~lib/arraybuffer/ArrayBuffer + local.get $0 + i32.const 8 + i32.sub + i32.load + br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/typedarray/Int16Array $~lib/typedarray/Float32Array $~lib/typedarray/Uint64Array $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/array/Array $bindings/esm/PlainObject $~lib/typedarray/Uint8Array $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + end + return + end + return end + local.get $0 + local.get $1 + call $~lib/arraybuffer/ArrayBufferView~visit return end + local.get $0 + local.get $1 + call $~lib/typedarray/Int16Array~visit return end local.get $0 local.get $1 - call $~lib/arraybuffer/ArrayBufferView~visit + call $~lib/typedarray/Float32Array~visit return end local.get $0 local.get $1 - call $~lib/typedarray/Int16Array~visit + call $~lib/typedarray/Uint64Array~visit return end - local.get $0 - local.get $1 - call $~lib/typedarray/Float32Array~visit return end - local.get $0 - local.get $1 - call $~lib/typedarray/Uint64Array~visit return end return @@ -3165,8 +3179,8 @@ global.get $~lib/memory/__data_end i32.lt_s if - i32.const 17536 - i32.const 17584 + i32.const 17552 + i32.const 17600 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3738,7 +3752,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 16 - i32.const 7 + i32.const 9 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -3904,7 +3918,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 68 - i32.const 8 + i32.const 10 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -4018,7 +4032,7 @@ if global.get $~lib/memory/__stack_pointer i32.const 0 - i32.const 11 + i32.const 13 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -4146,6 +4160,44 @@ global.set $~lib/memory/__stack_pointer local.get $2 ) + (func $export:bindings/esm/staticarrayU16 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + call $~stack_check + global.get $~lib/memory/__stack_pointer + local.get $0 + i32.store + local.get $0 + call $bindings/esm/staticarrayU16 + local.set $1 + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $1 + ) + (func $export:bindings/esm/staticarrayI64 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + call $~stack_check + global.get $~lib/memory/__stack_pointer + local.get $0 + i32.store + local.get $0 + call $bindings/esm/staticarrayI64 + local.set $1 + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $1 + ) (func $export:bindings/esm/arrayFunction (param $0 i32) (param $1 i32) (result i32) (local $2 i32) global.get $~lib/memory/__stack_pointer diff --git a/tests/compiler/bindings/raw.release.d.ts b/tests/compiler/bindings/raw.release.d.ts index 14bc6d53ec..b7c0627f6e 100644 --- a/tests/compiler/bindings/raw.release.d.ts +++ b/tests/compiler/bindings/raw.release.d.ts @@ -88,6 +88,18 @@ declare namespace __AdaptedExports { * @returns `~lib/staticarray/StaticArray` */ export function staticarrayFunction(a: Array, b: Array): Array; + /** + * bindings/esm/staticarrayU16 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ + export function staticarrayU16(a: Array): Array; + /** + * bindings/esm/staticarrayI64 + * @param a `~lib/staticarray/StaticArray` + * @returns `~lib/staticarray/StaticArray` + */ + export function staticarrayI64(a: Array): Array; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` @@ -101,22 +113,22 @@ declare namespace __AdaptedExports { * @param b `bindings/esm/PlainObject` * @returns `bindings/esm/PlainObject` */ - export function objectFunction(a: __Record8, b: __Record8): __Record8; + export function objectFunction(a: __Record10, b: __Record10): __Record10; /** * bindings/esm/newInternref * @returns `bindings/esm/NonPlainObject` */ - export function newInternref(): __Internref11; + export function newInternref(): __Internref13; /** * bindings/esm/internrefFunction * @param a `bindings/esm/NonPlainObject` * @param b `bindings/esm/NonPlainObject` * @returns `bindings/esm/NonPlainObject` */ - export function internrefFunction(a: __Internref11, b: __Internref11): __Internref11; + export function internrefFunction(a: __Internref13, b: __Internref13): __Internref13; } /** bindings/esm/PlainObject */ -declare interface __Record8 { +declare interface __Record10 { /** @type `i8` */ a: number | TOmittable; /** @type `i16` */ @@ -151,8 +163,8 @@ declare interface __Record8 { p: Array | null | TOmittable; } /** bindings/esm/NonPlainObject */ -declare class __Internref11 extends Number { - private __nominal11: symbol; +declare class __Internref13 extends Number { + private __nominal13: symbol; } /** Instantiates the compiled WebAssembly module with the given imports. */ export declare function instantiate(module: WebAssembly.Module, imports: { diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index dabcb032b9..9b79cf0b89 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -137,10 +137,20 @@ export async function instantiate(module, imports = {}) { __release(a); } }, + staticarrayU16(a) { + // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); + }, + staticarrayI64(a) { + // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); + }, arrayFunction(a, b) { // bindings/esm/arrayFunction(~lib/array/Array, ~lib/array/Array) => ~lib/array/Array - a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, a) || __notnull()); - b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 7, 2, b) || __notnull(); + a = __retain(__lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, a) || __notnull()); + b = __lowerArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 9, 2, b) || __notnull(); try { return __liftArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.arrayFunction(a, b) >>> 0); } finally { @@ -149,10 +159,10 @@ export async function instantiate(module, imports = {}) { }, objectFunction(a, b) { // bindings/esm/objectFunction(bindings/esm/PlainObject, bindings/esm/PlainObject) => bindings/esm/PlainObject - a = __retain(__lowerRecord8(a) || __notnull()); - b = __lowerRecord8(b) || __notnull(); + a = __retain(__lowerRecord10(a) || __notnull()); + b = __lowerRecord10(b) || __notnull(); try { - return __liftRecord8(exports.objectFunction(a, b) >>> 0); + return __liftRecord10(exports.objectFunction(a, b) >>> 0); } finally { __release(a); } @@ -172,11 +182,11 @@ export async function instantiate(module, imports = {}) { } }, }, exports); - function __lowerRecord8(value) { + function __lowerRecord10(value) { // bindings/esm/PlainObject // Hint: Opt-out from lowering as a record by providing an empty constructor if (value == null) return 0; - const pointer = exports.__pin(exports.__new(68, 8)); + const pointer = exports.__pin(exports.__new(68, 10)); new Int8Array(memory.buffer)[pointer + 0 >>> 0] = value.a; new Int16Array(memory.buffer)[pointer + 2 >>> 1] = value.b; new Int32Array(memory.buffer)[pointer + 4 >>> 2] = value.c; @@ -191,12 +201,12 @@ export async function instantiate(module, imports = {}) { new Float32Array(memory.buffer)[pointer + 44 >>> 2] = value.l; new Float64Array(memory.buffer)[pointer + 48 >>> 3] = value.m; new Uint32Array(memory.buffer)[pointer + 56 >>> 2] = __lowerString(value.n); - new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 9, 0, value.o); - new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 10, 2, value.p); + new Uint32Array(memory.buffer)[pointer + 60 >>> 2] = __lowerTypedArray(Uint8Array, 11, 0, value.o); + new Uint32Array(memory.buffer)[pointer + 64 >>> 2] = __lowerArray((pointer, value) => { new Uint32Array(memory.buffer)[pointer >>> 2] = __lowerString(value) || __notnull(); }, 12, 2, value.p); exports.__unpin(pointer); return pointer; } - function __liftRecord8(pointer) { + function __liftRecord10(pointer) { // bindings/esm/PlainObject // Hint: Opt-out from lifting as a record by providing an empty constructor if (!pointer) return null; @@ -311,7 +321,11 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + if (ArrayBuffer.isView(values)) { + new (values.constructor)(memory.buffer, buffer, length).set(values); + } else { + for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); + } exports.__unpin(buffer); return buffer; } diff --git a/tests/compiler/bindings/raw.release.wat b/tests/compiler/bindings/raw.release.wat index f5f70ccc7a..be333234d2 100644 --- a/tests/compiler/bindings/raw.release.wat +++ b/tests/compiler/bindings/raw.release.wat @@ -5,12 +5,12 @@ (type $none_=>_i32 (func (result i32))) (type $i32_i32_=>_none (func (param i32 i32))) (type $i32_i32_i32_=>_none (func (param i32 i32 i32))) + (type $i32_=>_i32 (func (param i32) (result i32))) (type $i32_i32_f64_f64_f64_f64_f64_=>_none (func (param i32 i32 f64 f64 f64 f64 f64))) (type $f64_=>_f64 (func (param f64) (result f64))) (type $i64_i64_=>_i64 (func (param i64 i64) (result i64))) (type $i32_i32_i32_i32_=>_none (func (param i32 i32 i32 i32))) (type $i32_i32_i64_=>_none (func (param i32 i32 i64))) - (type $i32_=>_i32 (func (param i32) (result i32))) (import "env" "Math.E" (global $~lib/bindings/dom/Math.E f64)) (import "env" "trace" (func $~lib/builtins/trace (param i32 i32 f64 f64 f64 f64 f64))) (import "env" "console.log" (func $~lib/bindings/dom/console.log (param i32))) @@ -39,7 +39,7 @@ (global $~lib/rt/tlsf/ROOT (mut i32) (i32.const 0)) (global $~argumentsLength (mut i32) (i32.const 0)) (global $~lib/rt/__rtti_base i32 (i32.const 2048)) - (global $~lib/memory/__stack_pointer (mut i32) (i32.const 18532)) + (global $~lib/memory/__stack_pointer (mut i32) (i32.const 18548)) (global $~started (mut i32) (i32.const 0)) (memory $0 1) (data (i32.const 1036) "\1c") @@ -76,9 +76,9 @@ (data (i32.const 1928) "\01\00\00\00*\00\00\00O\00b\00j\00e\00c\00t\00 \00a\00l\00r\00e\00a\00d\00y\00 \00p\00i\00n\00n\00e\00d") (data (i32.const 1980) "<") (data (i32.const 1992) "\01\00\00\00(\00\00\00O\00b\00j\00e\00c\00t\00 \00i\00s\00 \00n\00o\00t\00 \00p\00i\00n\00n\00e\00d") - (data (i32.const 2048) "\0c\00\00\00 \00\00\00\00\00\00\00 ") - (data (i32.const 2076) "\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\02\t") - (data (i32.const 2124) "A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 ") + (data (i32.const 2048) "\0e\00\00\00 \00\00\00\00\00\00\00 ") + (data (i32.const 2076) "\81\08\00\00\02\00\00\00\01\19\00\00\02\00\00\00\01\02\00\00\02\00\00\00$\t\00\00\00\00\00\00\a4\00\00\00\00\00\00\00$\n\00\00\00\00\00\00\02\t") + (data (i32.const 2140) "A\00\00\00\02\00\00\00\02A\00\00\00\00\00\00 ") (export "plainGlobal" (global $bindings/esm/plainGlobal)) (export "plainMutableGlobal" (global $bindings/esm/plainMutableGlobal)) (export "stringGlobal" (global $bindings/esm/stringGlobal)) @@ -105,6 +105,8 @@ (export "stringFunctionOptional" (func $export:bindings/esm/stringFunctionOptional@varargs)) (export "typedarrayFunction" (func $export:bindings/esm/typedarrayFunction)) (export "staticarrayFunction" (func $export:bindings/esm/staticarrayFunction)) + (export "staticarrayU16" (func $export:bindings/esm/staticarrayU16)) + (export "staticarrayI64" (func $export:bindings/esm/staticarrayU16)) (export "arrayFunction" (func $export:bindings/esm/arrayFunction)) (export "objectFunction" (func $export:bindings/esm/objectFunction)) (export "internrefFunction" (func $export:bindings/esm/internrefFunction)) @@ -188,7 +190,7 @@ if i32.const 0 local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u local.get $0 i32.load offset=8 @@ -843,10 +845,10 @@ if unreachable end - i32.const 18544 + i32.const 18560 i32.const 0 i32.store - i32.const 20112 + i32.const 20128 i32.const 0 i32.store loop $for-loop|0 @@ -857,7 +859,7 @@ local.get $0 i32.const 2 i32.shl - i32.const 18544 + i32.const 18560 i32.add i32.const 0 i32.store offset=4 @@ -875,7 +877,7 @@ i32.add i32.const 2 i32.shl - i32.const 18544 + i32.const 18560 i32.add i32.const 0 i32.store offset=96 @@ -893,13 +895,13 @@ br $for-loop|0 end end - i32.const 18544 - i32.const 20116 + i32.const 18560 + i32.const 20132 memory.size i32.const 16 i32.shl call $~lib/rt/tlsf/addMemory - i32.const 18544 + i32.const 18560 global.set $~lib/rt/tlsf/ROOT ) (func $~lib/rt/itcms/step (result i32) @@ -984,7 +986,7 @@ local.set $0 loop $while-continue|0 local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u if local.get $0 @@ -1084,7 +1086,7 @@ unreachable end local.get $0 - i32.const 18532 + i32.const 18548 i32.lt_u if local.get $0 @@ -1107,7 +1109,7 @@ i32.const 4 i32.add local.tee $0 - i32.const 18532 + i32.const 18548 i32.ge_u if global.get $~lib/rt/tlsf/ROOT @@ -1608,11 +1610,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -1916,11 +1918,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -1932,7 +1934,7 @@ i32.store local.get $0 i32.const 0 - i32.const 11 + i32.const 13 call $~lib/rt/itcms/__new local.tee $0 i32.store @@ -2097,14 +2099,20 @@ block $bindings/esm/NonPlainObject block $~lib/array/Array<~lib/string/String> block $bindings/esm/PlainObject - block $~lib/staticarray/StaticArray - block $~lib/string/String - block $~lib/arraybuffer/ArrayBuffer - local.get $0 - i32.const 8 - i32.sub - i32.load - br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner0 $folding-inner0 $folding-inner0 $~lib/staticarray/StaticArray $folding-inner1 $bindings/esm/PlainObject $folding-inner0 $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/staticarray/StaticArray + block $~lib/string/String + block $~lib/arraybuffer/ArrayBuffer + local.get $0 + i32.const 8 + i32.sub + i32.load + br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner0 $folding-inner0 $folding-inner0 $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $~lib/staticarray/StaticArray $folding-inner1 $bindings/esm/PlainObject $folding-inner0 $~lib/array/Array<~lib/string/String> $bindings/esm/NonPlainObject $invalid + end + return + end + return end return end @@ -2203,11 +2211,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2245,7 +2253,7 @@ memory.size i32.const 16 i32.shl - i32.const 18532 + i32.const 18548 i32.sub i32.const 1 i32.shr_u @@ -2286,7 +2294,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2301,7 +2309,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2325,7 +2333,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2376,8 +2384,8 @@ local.get $5 return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2390,11 +2398,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2423,7 +2431,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2438,7 +2446,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2473,8 +2481,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2492,7 +2500,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2507,7 +2515,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2532,7 +2540,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner00 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner00 global.get $~lib/memory/__stack_pointer @@ -2551,7 +2559,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner00 global.get $~lib/memory/__stack_pointer @@ -2728,8 +2736,8 @@ local.get $2 return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -2745,7 +2753,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2762,7 +2770,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2788,7 +2796,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2890,13 +2898,40 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort unreachable ) + (func $export:bindings/esm/staticarrayU16 (param $0 i32) (result i32) + (local $1 i32) + global.get $~lib/memory/__stack_pointer + i32.const 4 + i32.sub + global.set $~lib/memory/__stack_pointer + global.get $~lib/memory/__stack_pointer + i32.const 2164 + i32.lt_s + if + i32.const 18576 + i32.const 18624 + i32.const 1 + i32.const 1 + call $~lib/builtins/abort + unreachable + end + global.get $~lib/memory/__stack_pointer + local.tee $1 + local.get $0 + i32.store + local.get $1 + i32.const 4 + i32.add + global.set $~lib/memory/__stack_pointer + local.get $0 + ) (func $export:bindings/esm/arrayFunction (param $0 i32) (param $1 i32) (result i32) (local $2 i32) (local $3 i32) @@ -2909,7 +2944,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -2928,7 +2963,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2946,7 +2981,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -2955,7 +2990,7 @@ i64.store local.get $0 i32.const 16 - i32.const 7 + i32.const 9 call $~lib/rt/itcms/__new local.tee $2 i32.store @@ -3081,8 +3116,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3097,7 +3132,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner1 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner1 global.get $~lib/memory/__stack_pointer @@ -3114,7 +3149,7 @@ global.set $~lib/memory/__stack_pointer block $folding-inner0 global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -3126,7 +3161,7 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s br_if $folding-inner0 global.get $~lib/memory/__stack_pointer @@ -3135,7 +3170,7 @@ i32.store local.get $3 i32.const 68 - i32.const 8 + i32.const 10 call $~lib/rt/itcms/__new local.tee $3 i32.store @@ -3223,8 +3258,8 @@ global.set $~lib/memory/__stack_pointer return end - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort @@ -3237,11 +3272,11 @@ i32.sub global.set $~lib/memory/__stack_pointer global.get $~lib/memory/__stack_pointer - i32.const 2148 + i32.const 2164 i32.lt_s if - i32.const 18560 - i32.const 18608 + i32.const 18576 + i32.const 18624 i32.const 1 i32.const 1 call $~lib/builtins/abort From 3fac53f67c7fa5decce35787b7def536f807ebbd Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 13 Jul 2022 12:34:27 +0300 Subject: [PATCH 02/10] remove parens --- src/bindings/js.ts | 2 +- tests/compiler/bindings/esm.debug.js | 2 +- tests/compiler/bindings/esm.release.js | 2 +- tests/compiler/bindings/raw.debug.js | 2 +- tests/compiler/bindings/raw.release.js | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index c4e377323d..9bd85ff5c1 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -790,7 +790,7 @@ export class JSBuilder extends ExportsWalker { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - new (values.constructor)(memory.buffer, buffer, length).set(values); + new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index f3dd63ebf2..8ed9e0a2a3 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -322,7 +322,7 @@ async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - new (values.constructor)(memory.buffer, buffer, length).set(values); + new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index e8b25ba01c..948f922cd2 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -322,7 +322,7 @@ async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - new (values.constructor)(memory.buffer, buffer, length).set(values); + new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index 9b79cf0b89..7b26cb4fc6 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -322,7 +322,7 @@ export async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - new (values.constructor)(memory.buffer, buffer, length).set(values); + new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index 9b79cf0b89..7b26cb4fc6 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -322,7 +322,7 @@ export async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - new (values.constructor)(memory.buffer, buffer, length).set(values); + new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } From b1a24b3ea1a6a47c576e2773a7a35962920123e7 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Thu, 14 Jul 2022 12:54:26 +0300 Subject: [PATCH 03/10] use ArrayLike for StaticArrays --- src/bindings/tsd.ts | 10 ++++++---- tests/compiler/bindings/esm.debug.d.ts | 6 +++--- tests/compiler/bindings/esm.release.d.ts | 6 +++--- tests/compiler/bindings/raw.debug.d.ts | 6 +++--- tests/compiler/bindings/raw.release.d.ts | 6 +++--- 5 files changed, 18 insertions(+), 16 deletions(-) diff --git a/src/bindings/tsd.ts b/src/bindings/tsd.ts index ffab273e0b..77af310251 100644 --- a/src/bindings/tsd.ts +++ b/src/bindings/tsd.ts @@ -241,14 +241,16 @@ export class TSDBuilder extends ExportsWalker { sb.push("ArrayBuffer"); } else if (clazz.extends(this.program.stringInstance.prototype)) { sb.push("string"); - } else if ( - clazz.extends(this.program.arrayPrototype) || - clazz.extends(this.program.staticArrayPrototype) - ) { + } else if (clazz.extends(this.program.arrayPrototype)) { const valueType = clazz.getArrayValueType(); sb.push("Array<"); sb.push(this.toTypeScriptType(valueType, mode)); sb.push(">"); + } else if (clazz.extends(this.program.staticArrayPrototype)) { + const valueType = clazz.getArrayValueType(); + sb.push("ArrayLike<"); + sb.push(this.toTypeScriptType(valueType, mode)); + sb.push(">"); } else if (clazz.extends(this.program.arrayBufferViewInstance.prototype)) { const valueType = clazz.getArrayValueType(); if (valueType == Type.i8) { diff --git a/tests/compiler/bindings/esm.debug.d.ts b/tests/compiler/bindings/esm.debug.d.ts index 686556afd8..d2c016a486 100644 --- a/tests/compiler/bindings/esm.debug.d.ts +++ b/tests/compiler/bindings/esm.debug.d.ts @@ -86,19 +86,19 @@ export declare function typedarrayFunction(a: Int16Array, b: Float32Array): BigU * @param b `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayFunction(a: Array, b: Array): Array; +export declare function staticarrayFunction(a: ArrayLike, b: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayU16 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayU16(a: Array): Array; +export declare function staticarrayU16(a: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayI64 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayI64(a: Array): Array; +export declare function staticarrayI64(a: ArrayLike): ArrayLike; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` diff --git a/tests/compiler/bindings/esm.release.d.ts b/tests/compiler/bindings/esm.release.d.ts index 686556afd8..d2c016a486 100644 --- a/tests/compiler/bindings/esm.release.d.ts +++ b/tests/compiler/bindings/esm.release.d.ts @@ -86,19 +86,19 @@ export declare function typedarrayFunction(a: Int16Array, b: Float32Array): BigU * @param b `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayFunction(a: Array, b: Array): Array; +export declare function staticarrayFunction(a: ArrayLike, b: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayU16 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayU16(a: Array): Array; +export declare function staticarrayU16(a: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayI64 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ -export declare function staticarrayI64(a: Array): Array; +export declare function staticarrayI64(a: ArrayLike): ArrayLike; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` diff --git a/tests/compiler/bindings/raw.debug.d.ts b/tests/compiler/bindings/raw.debug.d.ts index b7c0627f6e..77059e1080 100644 --- a/tests/compiler/bindings/raw.debug.d.ts +++ b/tests/compiler/bindings/raw.debug.d.ts @@ -87,19 +87,19 @@ declare namespace __AdaptedExports { * @param b `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayFunction(a: Array, b: Array): Array; + export function staticarrayFunction(a: ArrayLike, b: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayU16 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayU16(a: Array): Array; + export function staticarrayU16(a: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayI64 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayI64(a: Array): Array; + export function staticarrayI64(a: ArrayLike): ArrayLike; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` diff --git a/tests/compiler/bindings/raw.release.d.ts b/tests/compiler/bindings/raw.release.d.ts index b7c0627f6e..77059e1080 100644 --- a/tests/compiler/bindings/raw.release.d.ts +++ b/tests/compiler/bindings/raw.release.d.ts @@ -87,19 +87,19 @@ declare namespace __AdaptedExports { * @param b `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayFunction(a: Array, b: Array): Array; + export function staticarrayFunction(a: ArrayLike, b: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayU16 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayU16(a: Array): Array; + export function staticarrayU16(a: ArrayLike): ArrayLike; /** * bindings/esm/staticarrayI64 * @param a `~lib/staticarray/StaticArray` * @returns `~lib/staticarray/StaticArray` */ - export function staticarrayI64(a: Array): Array; + export function staticarrayI64(a: ArrayLike): ArrayLike; /** * bindings/esm/arrayFunction * @param a `~lib/array/Array` From 4cd13df6eafa66de36228bd87c14fdec5b53311c Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 15:50:39 +0300 Subject: [PATCH 04/10] add element check --- src/bindings/js.ts | 1 + tests/compiler/bindings/esm.debug.js | 1 + tests/compiler/bindings/esm.release.js | 1 + tests/compiler/bindings/raw.debug.js | 1 + tests/compiler/bindings/raw.release.js | 1 + 5 files changed, 5 insertions(+) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index c4920e4b19..1d68d7a35f 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -790,6 +790,7 @@ export class JSBuilder extends ExportsWalker { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { + if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index 1c4eb51f6d..e479d343b1 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -330,6 +330,7 @@ async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { + if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index ddb2d9cb96..5db2dba08f 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -330,6 +330,7 @@ async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { + if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index 139e4f0035..9e72d3faa8 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -330,6 +330,7 @@ export async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { + if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index 139e4f0035..9e72d3faa8 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -330,6 +330,7 @@ export async function instantiate(module, imports = {}) { length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { + if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); new values.constructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); From 85948581c8fae62fdd7b7cdbadb3b5b6e8b35df3 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 16:23:53 +0300 Subject: [PATCH 05/10] use static determined constructor --- src/bindings/js.ts | 36 +++++++++++++++++++++++--- tests/compiler/bindings/esm.debug.js | 13 +++++----- tests/compiler/bindings/esm.release.js | 13 +++++----- tests/compiler/bindings/raw.debug.js | 13 +++++----- tests/compiler/bindings/raw.release.js | 13 +++++----- 5 files changed, 56 insertions(+), 32 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 1d68d7a35f..3632647924 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -784,14 +784,13 @@ export class JSBuilder extends ExportsWalker { `); } if (this.needsLowerStaticArray) { - sb.push(` function __lowerStaticArray(lowerElement, id, align, values) { + sb.push(` function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { if (values == null) return 0; const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); - new values.constructor(memory.buffer, buffer, length).set(values); + new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } @@ -1054,9 +1053,38 @@ export class JSBuilder extends ExportsWalker { sb.push("__lowerStaticArray("); this.makeLowerToMemory(valueType, sb); sb.push(", "); + if (valueType.isNumericValue) { + if (valueType == Type.u8) { + sb.push("Uint8Array"); + } else if (valueType == Type.i8) { + sb.push("Int8Array"); + } else if (valueType == Type.u16) { + sb.push("Uint16Array"); + } else if (valueType == Type.i16) { + sb.push("Int16Array"); + } else if (valueType == Type.u32) { + sb.push("Uint32Array"); + } else if (valueType == Type.i32) { + sb.push("Int32Array"); + } else if (valueType == Type.u64) { + sb.push("BigUint64Array"); + } else if (valueType == Type.i64) { + sb.push("BigInt64Array"); + } else if (valueType == Type.f32) { + sb.push("Float32Array"); + } else if (valueType == Type.f64) { + sb.push("Float64Array"); + } else { + // unreachable + assert(false); + } + } else { + sb.push("undefined"); + } + sb.push(", "); sb.push(clazz.id.toString()); sb.push(", "); - sb.push(clazz.getArrayValueType().alignLog2.toString()); + sb.push(valueType.alignLog2.toString()); sb.push(", "); this.needsLowerStaticArray = true; } else if (clazz.extends(this.program.arrayBufferViewInstance.prototype)) { diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index e479d343b1..6f2fa8cd5c 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -137,8 +137,8 @@ async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,14 +324,13 @@ async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, id, align, values) { + function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { if (values == null) return 0; const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); - new values.constructor(memory.buffer, buffer, length).set(values); + new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index 5db2dba08f..1e5f3926b5 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -137,8 +137,8 @@ async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,14 +324,13 @@ async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, id, align, values) { + function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { if (values == null) return 0; const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); - new values.constructor(memory.buffer, buffer, length).set(values); + new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index 9e72d3faa8..d25dadbba1 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -137,8 +137,8 @@ export async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ export async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,14 +324,13 @@ export async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, id, align, values) { + function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { if (values == null) return 0; const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); - new values.constructor(memory.buffer, buffer, length).set(values); + new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index 9e72d3faa8..d25dadbba1 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -137,8 +137,8 @@ export async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ export async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,14 +324,13 @@ export async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, id, align, values) { + function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { if (values == null) return 0; const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; if (ArrayBuffer.isView(values)) { - if (values.constructor.BYTES_PER_ELEMENT !== (1 << align)) throw new Error("Mismatch element type"); - new values.constructor(memory.buffer, buffer, length).set(values); + new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); } From cc8679ccef165db2ab4a28ec6838b6e474ddcec4 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 16:26:47 +0300 Subject: [PATCH 06/10] better --- src/bindings/js.ts | 2 +- tests/compiler/bindings/esm.debug.js | 2 +- tests/compiler/bindings/esm.release.js | 2 +- tests/compiler/bindings/raw.debug.js | 2 +- tests/compiler/bindings/raw.release.js | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 3632647924..2b9a9f8152 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -789,7 +789,7 @@ export class JSBuilder extends ExportsWalker { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (ArrayBuffer.isView(values)) { + if (values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index 6f2fa8cd5c..629e55e717 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (ArrayBuffer.isView(values)) { + if (values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index 1e5f3926b5..8ded03ab5e 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (ArrayBuffer.isView(values)) { + if (values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index d25dadbba1..9737d4dede 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (ArrayBuffer.isView(values)) { + if (values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index d25dadbba1..9737d4dede 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (ArrayBuffer.isView(values)) { + if (values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); From 4f2104ae339103adb89fea18b73ed9179d40906e Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 16:32:06 +0300 Subject: [PATCH 07/10] fix --- src/bindings/js.ts | 2 +- tests/compiler/bindings/esm.debug.js | 2 +- tests/compiler/bindings/esm.release.js | 2 +- tests/compiler/bindings/raw.debug.js | 2 +- tests/compiler/bindings/raw.release.js | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 2b9a9f8152..445c1d222f 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -789,7 +789,7 @@ export class JSBuilder extends ExportsWalker { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (values instanceof typedConstructor) { + if (typedConstructor && values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index 629e55e717..aeadde7ac3 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (values instanceof typedConstructor) { + if (typedConstructor && values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index 8ded03ab5e..10fd726ba6 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (values instanceof typedConstructor) { + if (typedConstructor && values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index 9737d4dede..c6457bf963 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (values instanceof typedConstructor) { + if (typedConstructor && values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index 9737d4dede..c6457bf963 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (values instanceof typedConstructor) { + if (typedConstructor && values instanceof typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); From a80a6a4c3807c42247f7ff34f71d2ab2eb245647 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 16:43:01 +0300 Subject: [PATCH 08/10] add bool type --- src/bindings/js.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 445c1d222f..9165894d2f 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -1054,7 +1054,7 @@ export class JSBuilder extends ExportsWalker { this.makeLowerToMemory(valueType, sb); sb.push(", "); if (valueType.isNumericValue) { - if (valueType == Type.u8) { + if (valueType == Type.u8 || valueType == Type.bool) { sb.push("Uint8Array"); } else if (valueType == Type.i8) { sb.push("Int8Array"); From ea9f9881780d06b8ca5df259ebb8c954e8d4f82c Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 16:55:48 +0300 Subject: [PATCH 09/10] move ctr arg to tail --- src/bindings/js.ts | 62 +++++++++++++------------- tests/compiler/bindings/esm.debug.js | 10 ++--- tests/compiler/bindings/esm.release.js | 10 ++--- tests/compiler/bindings/raw.debug.js | 10 ++--- tests/compiler/bindings/raw.release.js | 10 ++--- 5 files changed, 52 insertions(+), 50 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index 9165894d2f..c4c61c894a 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -784,7 +784,7 @@ export class JSBuilder extends ExportsWalker { `); } if (this.needsLowerStaticArray) { - sb.push(` function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { + sb.push(` function __lowerStaticArray(lowerElement, id, align, values, typedConstructor) { if (values == null) return 0; const length = values.length, @@ -1053,35 +1053,6 @@ export class JSBuilder extends ExportsWalker { sb.push("__lowerStaticArray("); this.makeLowerToMemory(valueType, sb); sb.push(", "); - if (valueType.isNumericValue) { - if (valueType == Type.u8 || valueType == Type.bool) { - sb.push("Uint8Array"); - } else if (valueType == Type.i8) { - sb.push("Int8Array"); - } else if (valueType == Type.u16) { - sb.push("Uint16Array"); - } else if (valueType == Type.i16) { - sb.push("Int16Array"); - } else if (valueType == Type.u32) { - sb.push("Uint32Array"); - } else if (valueType == Type.i32) { - sb.push("Int32Array"); - } else if (valueType == Type.u64) { - sb.push("BigUint64Array"); - } else if (valueType == Type.i64) { - sb.push("BigInt64Array"); - } else if (valueType == Type.f32) { - sb.push("Float32Array"); - } else if (valueType == Type.f64) { - sb.push("Float64Array"); - } else { - // unreachable - assert(false); - } - } else { - sb.push("undefined"); - } - sb.push(", "); sb.push(clazz.id.toString()); sb.push(", "); sb.push(valueType.alignLog2.toString()); @@ -1119,6 +1090,37 @@ export class JSBuilder extends ExportsWalker { this.needsLowerInternref = true; } sb.push(name); + if (clazz.extends(this.program.staticArrayPrototype)) { + // optional last argument for __lowerStaticArray + let valueType = clazz.getArrayValueType(); + if (valueType.isNumericValue) { + sb.push(", "); + if (valueType == Type.u8 || valueType == Type.bool) { + sb.push("Uint8Array"); + } else if (valueType == Type.i8) { + sb.push("Int8Array"); + } else if (valueType == Type.u16) { + sb.push("Uint16Array"); + } else if (valueType == Type.i16) { + sb.push("Int16Array"); + } else if (valueType == Type.u32) { + sb.push("Uint32Array"); + } else if (valueType == Type.i32) { + sb.push("Int32Array"); + } else if (valueType == Type.u64) { + sb.push("BigUint64Array"); + } else if (valueType == Type.i64) { + sb.push("BigInt64Array"); + } else if (valueType == Type.f32) { + sb.push("Float32Array"); + } else if (valueType == Type.f64) { + sb.push("Float64Array"); + } else { + // unreachable + assert(false); + } + } + } sb.push(")"); if (!type.is(TypeFlags.NULLABLE)) { this.needsNotNull = true; diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index aeadde7ac3..3ffb1f6059 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -137,8 +137,8 @@ async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a, Int32Array) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b, Int32Array) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a, Uint16Array) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a, BigInt64Array) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,7 +324,7 @@ async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { + function __lowerStaticArray(lowerElement, id, align, values, typedConstructor) { if (values == null) return 0; const length = values.length, diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index 10fd726ba6..220ad256dd 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -137,8 +137,8 @@ async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a, Int32Array) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b, Int32Array) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a, Uint16Array) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a, BigInt64Array) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,7 +324,7 @@ async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { + function __lowerStaticArray(lowerElement, id, align, values, typedConstructor) { if (values == null) return 0; const length = values.length, diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index c6457bf963..9043d3371e 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -137,8 +137,8 @@ export async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a, Int32Array) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b, Int32Array) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ export async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a, Uint16Array) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a, BigInt64Array) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,7 +324,7 @@ export async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { + function __lowerStaticArray(lowerElement, id, align, values, typedConstructor) { if (values == null) return 0; const length = values.length, diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index c6457bf963..9043d3371e 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -137,8 +137,8 @@ export async function instantiate(module, imports = {}) { }, staticarrayFunction(a, b) { // bindings/esm/staticarrayFunction(~lib/staticarray/StaticArray, ~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, a) || __notnull()); - b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, Int32Array, 6, 2, b) || __notnull(); + a = __retain(__lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, a, Int32Array) || __notnull()); + b = __lowerStaticArray((pointer, value) => { new Int32Array(memory.buffer)[pointer >>> 2] = value; }, 6, 2, b, Int32Array) || __notnull(); try { return __liftStaticArray(pointer => new Int32Array(memory.buffer)[pointer >>> 2], 2, exports.staticarrayFunction(a, b) >>> 0); } finally { @@ -147,12 +147,12 @@ export async function instantiate(module, imports = {}) { }, staticarrayU16(a) { // bindings/esm/staticarrayU16(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, Uint16Array, 7, 1, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new Uint16Array(memory.buffer)[pointer >>> 1] = value; }, 7, 1, a, Uint16Array) || __notnull(); return __liftStaticArray(pointer => new Uint16Array(memory.buffer)[pointer >>> 1], 1, exports.staticarrayU16(a) >>> 0); }, staticarrayI64(a) { // bindings/esm/staticarrayI64(~lib/staticarray/StaticArray) => ~lib/staticarray/StaticArray - a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, BigInt64Array, 8, 3, a) || __notnull(); + a = __lowerStaticArray((pointer, value) => { new BigInt64Array(memory.buffer)[pointer >>> 3] = value || 0n; }, 8, 3, a, BigInt64Array) || __notnull(); return __liftStaticArray(pointer => new BigInt64Array(memory.buffer)[pointer >>> 3], 3, exports.staticarrayI64(a) >>> 0); }, arrayFunction(a, b) { @@ -324,7 +324,7 @@ export async function instantiate(module, imports = {}) { for (let i = 0; i < length; ++i) values[i] = liftElement(pointer + (i << align >>> 0)); return values; } - function __lowerStaticArray(lowerElement, typedConstructor, id, align, values) { + function __lowerStaticArray(lowerElement, id, align, values, typedConstructor) { if (values == null) return 0; const length = values.length, From eaefc008f522152938589df4a01f003e5e9dae68 Mon Sep 17 00:00:00 2001 From: MaxGraey Date: Wed, 20 Jul 2022 17:19:45 +0300 Subject: [PATCH 10/10] simplify checks --- src/bindings/js.ts | 2 +- tests/compiler/bindings/esm.debug.js | 2 +- tests/compiler/bindings/esm.release.js | 2 +- tests/compiler/bindings/raw.debug.js | 2 +- tests/compiler/bindings/raw.release.js | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/bindings/js.ts b/src/bindings/js.ts index c4c61c894a..1dae4fde8b 100644 --- a/src/bindings/js.ts +++ b/src/bindings/js.ts @@ -789,7 +789,7 @@ export class JSBuilder extends ExportsWalker { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (typedConstructor && values instanceof typedConstructor) { + if (typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.debug.js b/tests/compiler/bindings/esm.debug.js index 3ffb1f6059..fdc6303178 100644 --- a/tests/compiler/bindings/esm.debug.js +++ b/tests/compiler/bindings/esm.debug.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (typedConstructor && values instanceof typedConstructor) { + if (typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/esm.release.js b/tests/compiler/bindings/esm.release.js index 220ad256dd..e38479066a 100644 --- a/tests/compiler/bindings/esm.release.js +++ b/tests/compiler/bindings/esm.release.js @@ -329,7 +329,7 @@ async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (typedConstructor && values instanceof typedConstructor) { + if (typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.debug.js b/tests/compiler/bindings/raw.debug.js index 9043d3371e..11516eb03f 100644 --- a/tests/compiler/bindings/raw.debug.js +++ b/tests/compiler/bindings/raw.debug.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (typedConstructor && values instanceof typedConstructor) { + if (typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]); diff --git a/tests/compiler/bindings/raw.release.js b/tests/compiler/bindings/raw.release.js index 9043d3371e..11516eb03f 100644 --- a/tests/compiler/bindings/raw.release.js +++ b/tests/compiler/bindings/raw.release.js @@ -329,7 +329,7 @@ export async function instantiate(module, imports = {}) { const length = values.length, buffer = exports.__pin(exports.__new(length << align, id)) >>> 0; - if (typedConstructor && values instanceof typedConstructor) { + if (typedConstructor) { new typedConstructor(memory.buffer, buffer, length).set(values); } else { for (let i = 0; i < length; i++) lowerElement(buffer + (i << align >>> 0), values[i]);