nodejs/deps/v8/test/mjsunit/shared-memory/condition-async-wait.js

48 lines
1.9 KiB
JavaScript
Raw Permalink Normal View History

// Copyright 2024 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// Flags: --harmony-struct --allow-natives-syntax --expose-gc
(function TestAsyncWait() {
let mutex = new Atomics.Mutex;
let cv = new Atomics.Condition;
let notified = false;
let locked = Atomics.Mutex.lockAsync(mutex, async function() {
await Atomics.Condition.waitAsync(cv, mutex);
// There is only one waiter in this isolate's async waiter list, even though
// the lock has been taked 2 times (once in the lockAsync and once after the
// wait was notified).
assertEquals(1, %AtomicsSychronizationNumAsyncWaitersInIsolateForTesting());
notified = true;
});
// The lock is held, but the callback is not executed until the next
// microtask.
assertFalse(Atomics.Mutex.tryLock(mutex, function() {}).success);
// Call gc to test that everything is kept alive while the lock is taken.
gc();
setTimeout(() => {
// The lock callback has been executed and the condition variable
// queued one waiter, and the lock is released.
assertEquals(1, %AtomicsSynchronizationPrimitiveNumWaitersForTesting(cv));
// The condition variable waiters was added to this isolate's async waiter
// list and the mutex waiter is still in the list.
assertEquals(2, %AtomicsSychronizationNumAsyncWaitersInIsolateForTesting());
assertTrue(Atomics.Mutex.tryLock(mutex, function() {}).success);
Atomics.Condition.notify(cv, 1);
// The notification task has been posted, but the execution will continue
// in the next microtask.
assertFalse(notified);
setTimeout(() => {
assertTrue(notified);
// The waiter was removed from this isolate's async waiters list.
assertEquals(
0, %AtomicsSychronizationNumAsyncWaitersInIsolateForTesting());
}, 0);
}, 0);
})();