diff --git a/test/built-ins/Atomics/waitAsync/false-for-timeout-agent.js b/test/built-ins/Atomics/waitAsync/false-for-timeout-agent.js new file mode 100644 index 0000000000..b9091cfa4c --- /dev/null +++ b/test/built-ins/Atomics/waitAsync/false-for-timeout-agent.js @@ -0,0 +1,76 @@ +// Copyright (C) 2020 Rick Waldron. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: sec-atomics.waitasync +description: > + False timeout arg should result in an +0 timeout +info: | + Atomics.waitAsync( typedArray, index, value, timeout ) + + 1. Return DoWait(async, typedArray, index, value, timeout). + + DoWait ( mode, typedArray, index, value, timeout ) + + 6. Let q be ? ToNumber(timeout). + +includes: [atomicsHelper.js] +features: [Atomics.waitAsync, SharedArrayBuffer, TypedArray, Atomics] +---*/ +const RUNNING = 1; + +$262.agent.start(` + const valueOf = { + valueOf() { + return false; + } + }; + + const toPrimitive = { + [Symbol.toPrimitive]() { + return false; + } + }; + + $262.agent.receiveBroadcast(async (sab) => { + const i32a = new Int32Array(sab); + Atomics.add(i32a, ${RUNNING}, 1); + + const status1 = await Atomics.waitAsync(i32a, 0, 0, false); + const status2 = await Atomics.waitAsync(i32a, 0, 0, valueOf); + const status3 = await Atomics.waitAsync(i32a, 0, 0, toPrimitive); + + $262.agent.report(status1); + $262.agent.report(status2); + $262.agent.report(status3); + $262.agent.leaving(); + }); +`); + +const i32a = new Int32Array( + new SharedArrayBuffer(Int32Array.BYTES_PER_ELEMENT * 4) +); + +$262.agent.safeBroadcast(i32a); +$262.agent.waitUntil(i32a, RUNNING, 1); + +// Try to yield control to ensure the agent actually started to wait. +$262.agent.tryYield(); + +assert.sameValue( + $262.agent.getReport(), + 'timed-out', + '$262.agent.getReport() returns "timed-out"' +); +assert.sameValue( + $262.agent.getReport(), + 'timed-out', + '$262.agent.getReport() returns "timed-out"' +); +assert.sameValue( + $262.agent.getReport(), + 'timed-out', + '$262.agent.getReport() returns "timed-out"' +); + +assert.sameValue(Atomics.notify(i32a, 0), 0, 'Atomics.notify(i32a, 0) returns 0'); diff --git a/test/built-ins/Atomics/waitAsync/false-for-timeout.js b/test/built-ins/Atomics/waitAsync/false-for-timeout.js new file mode 100644 index 0000000000..0a1206caf5 --- /dev/null +++ b/test/built-ins/Atomics/waitAsync/false-for-timeout.js @@ -0,0 +1,58 @@ +// Copyright (C) 2020 Rick Waldron. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: sec-atomics.waitasync +description: > + False timeout arg should result in an +0 timeout +info: | + Atomics.waitAsync( typedArray, index, value, timeout ) + + 1. Return DoWait(async, typedArray, index, value, timeout). + + DoWait ( mode, typedArray, index, value, timeout ) + + 6. Let q be ? ToNumber(timeout). + +flags: [async, CanBlockIsTrue] +includes: [atomicsHelper.js] +features: [Atomics.waitAsync, SharedArrayBuffer, TypedArray, Atomics] +---*/ +const i32a = new Int32Array( + new SharedArrayBuffer(Int32Array.BYTES_PER_ELEMENT * 4) +); + +const valueOf = { + valueOf() { + return false; + } +}; + +const toPrimitive = { + [Symbol.toPrimitive]() { + return false; + } +}; + +(async () => { + try { + assert.sameValue( + await Atomics.waitAsync(i32a, 0, 0, false), + 'timed-out', + 'Atomics.waitAsync(i32a, 0, 0, false) returns "timed-out"' + ); + assert.sameValue( + await Atomics.waitAsync(i32a, 0, 0, valueOf), + 'timed-out', + 'Atomics.waitAsync(i32a, 0, 0, valueOf) returns "timed-out"' + ); + assert.sameValue( + await Atomics.waitAsync(i32a, 0, 0, toPrimitive), + 'timed-out', + 'Atomics.waitAsync(i32a, 0, 0, toPrimitive) returns "timed-out"' + ); + $DONE(); + } catch (error) { + $DONE(error); + } +})(); diff --git a/test/built-ins/Atomics/waitAsync/good-views.js b/test/built-ins/Atomics/waitAsync/good-views.js new file mode 100644 index 0000000000..15e851b511 --- /dev/null +++ b/test/built-ins/Atomics/waitAsync/good-views.js @@ -0,0 +1,67 @@ +// Copyright (C) 2020 Rick Waldron. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: sec-atomics.waitasync +description: > + Test Atomics.waitAsync on arrays that allow atomic operations, + in an Agent that is allowed to wait. +includes: [atomicsHelper.js] +features: [Atomics.waitAsync, Atomics] +---*/ +// Let's assume 'wait' is not allowed on the main thread, +// even in the shell. + +$262.agent.start(` + (async () => { + var sab = new SharedArrayBuffer(1024); + var ab = new ArrayBuffer(16); + + var good_indices = [ (view) => 0/-1, // -0 + (view) => '-0', + (view) => view.length - 1, + (view) => ({ valueOf: () => 0 }), + (view) => ({ toString: () => '0', valueOf: false }) // non-callable valueOf triggers invocation of toString + ]; + + var view = new Int32Array(sab, 32, 20); + + view[0] = 0; + $262.agent.report("A " + (await Atomics.waitAsync(view, 0, 0, 0))) + $262.agent.report("B " + (await Atomics.waitAsync(view, 0, 37, 0))); + + // In-bounds boundary cases for indexing + for ( let IdxGen of good_indices ) { + let Idx = IdxGen(view); + view.fill(0); + // Atomics.store() computes an index from Idx in the same way as other + // Atomics operations, not quite like view[Idx]. + Atomics.store(view, Idx, 37); + $262.agent.report("C " + (await Atomics.waitAsync(view, Idx, 0))); + } + + $262.agent.report("done"); + $262.agent.leaving(); + })(); +`); + +assert.sameValue( + $262.agent.getReport(), + 'A timed-out', + '$262.agent.getReport() returns "A timed-out"' +); + +assert.sameValue( + $262.agent.getReport(), + 'B not-equal', + '$262.agent.getReport() returns "B not-equal"' +); + +var r; +while ((r = $262.agent.getReport()) !== "done") { + assert.sameValue( + r, + 'C not-equal', + '$262.agent.getReport() returns "C not-equal"' + ); +} diff --git a/test/built-ins/Atomics/waitAsync/nan-for-timeout.js b/test/built-ins/Atomics/waitAsync/nan-for-timeout.js new file mode 100644 index 0000000000..4fd9364aa9 --- /dev/null +++ b/test/built-ins/Atomics/waitAsync/nan-for-timeout.js @@ -0,0 +1,44 @@ +// Copyright (C) 2020 Rick Waldron. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: sec-atomics.waitasync +description: > + NaN timeout arg should result in an infinite timeout +info: | + Atomics.waitAsync( typedArray, index, value, timeout ) + + 1. Return DoWait(async, typedArray, index, value, timeout). + + DoWait ( mode, typedArray, index, value, timeout ) + + 6. Let q be ? ToNumber(timeout). + +includes: [atomicsHelper.js] +features: [Atomics.waitAsync, SharedArrayBuffer, TypedArray, Atomics] +---*/ + +const RUNNING = 1; + +$262.agent.start(` + $262.agent.receiveBroadcast(async (sab) => { + const i32a = new Int32Array(sab); + Atomics.add(i32a, ${RUNNING}, 1); + + $262.agent.report(await Atomics.waitAsync(i32a, 0, 0, NaN)); // NaN => +Infinity + $262.agent.leaving(); + }); +`); + +const i32a = new Int32Array( + new SharedArrayBuffer(Int32Array.BYTES_PER_ELEMENT * 4) +); + +$262.agent.safeBroadcast(i32a); +$262.agent.waitUntil(i32a, RUNNING, 1); + +// Try to yield control to ensure the agent actually started to wait. +$262.agent.tryYield(); + +assert.sameValue(Atomics.notify(i32a, 0), 1, 'Atomics.notify(i32a, 0) returns 1'); +assert.sameValue($262.agent.getReport(), "ok", '$262.agent.getReport() returns "ok"');