/**
 * @license
 * Copyright 2015 The Emscripten Authors
 * SPDX-License-Identifier: MIT
 */

// Pthread Web Worker handling code.
// This code runs only on pthread web workers and handles pthread setup
// and communication with the main thread via postMessage.

#if ASSERTIONS
// Unique ID of the current pthread worker (zero on non-pthread-workers
// including the main thread).
var workerID = 0;
#endif

#if MAIN_MODULE
// Map of modules to be shared with new threads.  This gets populated by the
// main thread and shared with all new workers via the initial `load` message.
var sharedModules = {};
#endif

if (ENVIRONMENT_IS_PTHREAD) {
  // Thread-local guard variable for one-time init of the JS state
  var initializedJS = false;

#if LOAD_SOURCE_MAP || USE_OFFSET_CONVERTER
  // When using postMessage to send an object, it is processed by the structured
  // clone algorithm.  The prototype, and hence methods, on that object is then
  // lost. This function adds back the lost prototype.  This does not work with
  // nested objects that has prototypes, but it suffices for WasmSourceMap and
  // WasmOffsetConverter.
  function resetPrototype(constructor, attrs) {
    var object = Object.create(constructor.prototype);
    return Object.assign(object, attrs);
  }
#endif

  // Turn unhandled rejected promises into errors so that the main thread will be
  // notified about them.
  self.onunhandledrejection = (e) => { throw e.reason || e; };

  {{{ asyncIf(ASYNCIFY == 2) }}}function handleMessage(e) {
    try {
      var msgData = e['data'];
      //dbg('msgData: ' + Object.keys(msgData));
      var cmd = msgData.cmd;
      if (cmd === 'load') { // Preload command that is called once per worker to parse and load the Emscripten code.
#if ASSERTIONS
        workerID = msgData.workerID;
#endif
#if PTHREADS_DEBUG
        dbg('worker: loading module')
#endif

        // Until we initialize the runtime, queue up any further incoming messages.
        let messageQueue = [];
        self.onmessage = (e) => messageQueue.push(e);

        // And add a callback for when the runtime is initialized.
        self.startWorker = (instance) => {
          // Notify the main thread that this thread has loaded.
          postMessage({ cmd: 'loaded' });
          // Process any messages that were queued before the thread was ready.
          for (let msg of messageQueue) {
            handleMessage(msg);
          }
          // Restore the real message handler.
          self.onmessage = handleMessage;
        };

#if MAIN_MODULE
        dynamicLibraries = msgData.dynamicLibraries;
        sharedModules = msgData.sharedModules;
#if RUNTIME_DEBUG
        dbg(`worker: received ${Object.keys(msgData.sharedModules).length} shared modules: ${Object.keys(msgData.sharedModules)}`);
#endif
#endif

        // Use `const` here to ensure that the variable is scoped only to
        // that iteration, allowing safe reference from a closure.
        for (const handler of msgData.handlers) {
          // The the main module has a handler for a certain even, but no
          // handler exists on the pthread worker, then proxy that handler
          // back to the main thread.
          if (!Module[handler] || Module[handler].proxy) {
#if RUNTIME_DEBUG
            dbg(`worker: installer proxying handler: ${handler}`);
#endif
            Module[handler] = (...args) => {
#if RUNTIME_DEBUG
              dbg(`worker: calling handler on main thread: ${handler}`);
#endif
              postMessage({ cmd: 'callHandler', handler, args: args });
            }
            // Rebind the out / err handlers if needed
            if (handler == 'print') out = Module[handler];
            if (handler == 'printErr') err = Module[handler];
          }
#if RUNTIME_DEBUG
          else dbg(`worker: using thread-local handler: ${handler}`);
#endif
        }

        wasmMemory = msgData.wasmMemory;
        updateMemoryViews();

#if LOAD_SOURCE_MAP
        wasmSourceMap = resetPrototype(WasmSourceMap, msgData.wasmSourceMap);
#endif
#if USE_OFFSET_CONVERTER
        wasmOffsetConverter = resetPrototype(WasmOffsetConverter, msgData.wasmOffsetConverter);
#endif

#if MINIMAL_RUNTIME
        // Pass the shared Wasm module in the Module object for MINIMAL_RUNTIME.
        Module['wasm'] = msgData.wasmModule;
        loadModule();
#else
        wasmModuleReceived(msgData.wasmModule);
#endif // MINIMAL_RUNTIME
      } else if (cmd === 'run') {
#if ASSERTIONS
        assert(msgData.pthread_ptr);
#endif
        // Call inside JS module to set up the stack frame for this pthread in JS module scope.
        // This needs to be the first thing that we do, as we cannot call to any C/C++ functions
        // until the thread stack is initialized.
        establishStackSpace(msgData.pthread_ptr);

        // Pass the thread address to wasm to store it for fast access.
        __emscripten_thread_init(msgData.pthread_ptr, /*is_main=*/0, /*is_runtime=*/0, /*can_block=*/1, 0, 0);

#if OFFSCREENCANVAS_SUPPORT
        PThread.receiveOffscreenCanvases(msgData);
#endif
        PThread.threadInitTLS();

        // Await mailbox notifications with `Atomics.waitAsync` so we can start
        // using the fast `Atomics.notify` notification path.
        __emscripten_thread_mailbox_await(msgData.pthread_ptr);

        if (!initializedJS) {
#if EMBIND
#if PTHREADS_DEBUG
          dbg(`worker: Pthread 0x${_pthread_self().toString(16)} initializing embind.`);
#endif
          // Embind must initialize itself on all threads, as it generates support JS.
          // We only do this once per worker since they get reused
          __embind_initialize_bindings();
#endif // EMBIND
          initializedJS = true;
        }

        try {
          {{{ awaitIf(ASYNCIFY == 2) }}}invokeEntryPoint(msgData.start_routine, msgData.arg);
        } catch(ex) {
          if (ex != 'unwind') {
            // The pthread "crashed".  Do not call `_emscripten_thread_exit` (which
            // would make this thread joinable).  Instead, re-throw the exception
            // and let the top level handler propagate it back to the main thread.
            throw ex;
          }
#if RUNTIME_DEBUG
          dbg(`worker: Pthread 0x${_pthread_self().toString(16)} completed its main entry point with an 'unwind', keeping the worker alive for asynchronous operation.`);
#endif
        }
      } else if (msgData.target === 'setimmediate') {
        // no-op
      } else if (cmd === 'checkMailbox') {
        if (initializedJS) {
          checkMailbox();
        }
      } else if (cmd) {
        // The received message looks like something that should be handled by this message
        // handler, (since there is a cmd field present), but is not one of the
        // recognized commands:
        err(`worker: received unknown command ${cmd}`);
        err(msgData);
      }
    } catch(ex) {
#if ASSERTIONS
      err(`worker: onmessage() captured an uncaught exception: ${ex}`);
      if (ex?.stack) err(ex.stack);
#endif
      __emscripten_thread_crashed();
      throw ex;
    }
  };

  self.onmessage = handleMessage;

} // ENVIRONMENT_IS_PTHREAD
