Files
vpinball-wasm/patches/vpinball/0002-threadpool-single-threaded-emscripten.patch
T

48 lines
1.7 KiB
Diff
Raw Normal View History

--- a/third-party/include/ThreadPool.h
+++ b/third-party/include/ThreadPool.h
@@ -110,9 +110,20 @@
: pool_size(threads)
, in_flight(0)
{
+#ifndef __EMSCRIPTEN__
const std::unique_lock<std::mutex> lock(this->queue_mutex);
for (std::size_t i = 0; i != threads; ++i)
start_worker(i, lock);
+#else
+ // vpinball-wasm: a single-threaded Emscripten build (no -pthread /
+ // SharedArrayBuffer for v1) cannot construct real std::thread workers -
+ // std::thread's constructor throws at runtime otherwise ("thread
+ // constructor failed"). Run zero real workers; enqueue() below executes
+ // tasks synchronously and inline instead, matching the porting plan's
+ // "run ThreadPool work serially" decision for one-off parallel work
+ // (parallel .vpx item deserialization at load, env-map baking, etc.).
+ (void)pool_size;
+#endif
}
// add new work item to the pool
@@ -139,6 +150,15 @@
std::future<return_type> res = task->get_future();
+#ifdef __EMSCRIPTEN__
+ // vpinball-wasm: no real worker threads exist (see the constructor) -
+ // run the task synchronously inline so callers still get a valid,
+ // already-ready future, exactly as if it had run on a worker.
+ (void)std::atomic_fetch_add_explicit(&in_flight, std::size_t(1), std::memory_order_relaxed);
+ (*task)();
+ (void)std::atomic_fetch_sub_explicit(&in_flight, std::size_t(1), std::memory_order_acq_rel);
+ return res;
+#else
std::unique_lock<std::mutex> lock(queue_mutex);
if (tasks.size () >= max_queue_size)
// wait for the queue to empty or be stopped
@@ -160,6 +180,7 @@
condition_consumers.notify_one();
return res;
+#endif
}