From 0b80037ebc7825db0e67c2433f556dd8d07118a2 Mon Sep 17 00:00:00 2001 From: Ben Smith Date: Fri, 25 Jan 2019 09:42:09 -0800 Subject: [PATCH] [test] Add js-api tests (#114) This tests the `WebAssembly.Memory` constructor and the `grow` method. * Memory.buffer should be frozen and not extensible when shared * Don't check isFrozen during grow (constructor test is sufficient) * Don't check stray argument in shared memory detach test --- test/js-api/memory/constructor.any.js | 31 ++++++++++++++++++++++++--- test/js-api/memory/grow.any.js | 29 ++++++++++++++++++++++++- 2 files changed, 56 insertions(+), 4 deletions(-) diff --git a/test/js-api/memory/constructor.any.js b/test/js-api/memory/constructor.any.js index 11e309fe65..a0b90fb7f5 100644 --- a/test/js-api/memory/constructor.any.js +++ b/test/js-api/memory/constructor.any.js @@ -8,15 +8,18 @@ function assert_Memory(memory, expected) { // https://github.com/WebAssembly/spec/issues/840 assert_equals(memory.buffer, memory.buffer, "buffer should be idempotent"); - assert_equals(Object.getPrototypeOf(memory.buffer), ArrayBuffer.prototype, - "prototype of buffer"); - assert_true(Object.isExtensible(memory.buffer), "buffer extensibility"); + const isShared = !!expected.shared; + const bufferType = isShared ? self.SharedArrayBuffer : ArrayBuffer; + assert_equals(Object.getPrototypeOf(memory.buffer), bufferType.prototype, + 'prototype of buffer'); assert_equals(memory.buffer.byteLength, 0x10000 * expected.size, "size of buffer"); if (expected.size > 0) { const array = new Uint8Array(memory.buffer); assert_equals(array[0], 0, "first element of buffer"); assert_equals(array[array.byteLength - 1], 0, "last element of buffer"); } + assert_equals(isShared, Object.isFrozen(memory.buffer), "buffer frozen"); + assert_not_equals(Object.isExtensible(memory.buffer), isShared, "buffer extensibility"); } test(() => { @@ -83,6 +86,10 @@ test(() => { assert_throws(new RangeError(), () => new WebAssembly.Memory({ "initial": 10, "maximum": 9 })); }, "Initial value exceeds maximum"); +test(() => { + assert_throws(new TypeError(), () => new WebAssembly.Memory({ "initial": 10, "shared": true })); +}, "Shared memory without maximum"); + test(() => { const proxy = new Proxy({}, { has(o, x) { @@ -118,6 +125,16 @@ test(() => { }, }; }, + + get shared() { + order.push("shared"); + return { + valueOf() { + order.push("shared valueOf"); + return true; + }, + }; + }, }); assert_array_equals(order, [ @@ -125,6 +142,8 @@ test(() => { "initial valueOf", "maximum", "maximum valueOf", + "shared", + "shared valueOf", ]); }, "Order of evaluation for descriptor"); @@ -145,3 +164,9 @@ test(() => { const memory = new WebAssembly.Memory(argument, {}); assert_Memory(memory, { "size": 0 }); }, "Stray argument"); + +test(() => { + const argument = { "initial": 4, "maximum": 10, shared: true }; + const memory = new WebAssembly.Memory(argument); + assert_Memory(memory, { "size": 4, "shared": true }); +}, "Shared memory"); diff --git a/test/js-api/memory/grow.any.js b/test/js-api/memory/grow.any.js index 1ccfb94675..11c4194251 100644 --- a/test/js-api/memory/grow.any.js +++ b/test/js-api/memory/grow.any.js @@ -2,7 +2,8 @@ function assert_ArrayBuffer(actual, expected, message) { // https://github.com/WebAssembly/spec/issues/840 - assert_equals(Object.getPrototypeOf(actual), ArrayBuffer.prototype, + const bufferType = expected.shared ? self.SharedArrayBuffer : ArrayBuffer; + assert_equals(Object.getPrototypeOf(actual), bufferType.prototype, `${message}: prototype`); if (expected.detached) { // https://github.com/tc39/ecma262/issues/678 @@ -183,3 +184,29 @@ test(() => { assert_ArrayBuffer(oldMemory, { "detached": true }, "Old buffer after growing"); assert_ArrayBuffer(newMemory, { "size": 2 }, "New buffer after growing"); }, "Stray argument"); + +test(() => { + const argument = { "initial": 1, "maximum": 2, "shared": true }; + const memory = new WebAssembly.Memory(argument); + const oldMemory = memory.buffer; + assert_ArrayBuffer(oldMemory, { "size": 1, "shared": true }, "Buffer before growing"); + + const result = memory.grow(1); + assert_equals(result, 1); + + const newMemory = memory.buffer; + assert_not_equals(oldMemory, newMemory); + assert_ArrayBuffer(oldMemory, { "size": 1, "shared": true }, "Old buffer after growing"); + assert_ArrayBuffer(newMemory, { "size": 2, "shared": true }, "New buffer after growing"); + + // The old and new buffers must have the same value for the + // [[ArrayBufferData]] internal slot. + const oldArray = new Uint8Array(oldMemory); + const newArray = new Uint8Array(newMemory); + assert_equals(oldArray[0], 0, "old first element"); + assert_equals(newArray[0], 0, "new first element"); + oldArray[0] = 1; + assert_equals(oldArray[0], 1, "old first element"); + assert_equals(newArray[0], 1, "new first element"); + +}, "Growing shared memory does not detach old buffer");