Problem
Compiling a defined, streamable function return value can fail during WASM linking. Example that must compile and run:
#include <iostream>
int val() { return 5; }
int main() {
std::cout << val();
}
Observed diagnostics include:
wasm-ld: error: /tmp/main-*.o: undefined symbol: __cxa_allocate_exception
wasm-ld: error: /tmp/main-*.o: undefined symbol: __cxa_throw
This points to the browser compiler worker's direct Clang/LLD invocation and C++ exception/runtime library linkage, rather than to the source expression itself.
Proposed plan
- Reproduce the failure through the real extension worker pipeline before choosing a fix. Capture the
clang++ -### output, parsed plan.linkStep.args, and the existence of every driver-selected startup object, archive, and -L path in the fresh LLD virtual filesystem immediately before invoking wasm-ld.
- Determine whether the cause is driver-discovery stubs, parsed/forwarded argv, static-library ordering, or a virtual-path mismatch. Do not assume the sysroot is absent: the worker already extracts it into both compiler and linker instances.
- Add an artifact-aware E2E regression harness that executes the real
clang++ -### -> -cc1 -> wasm-ld pipeline. Because the packaged compiler modules cannot be loaded directly in Node without a loader adaptation, use a browser/Worker-based harness, a deliberate loader shim, or extracted reusable worker logic; do not duplicate the worker pipeline in a mock-only test.
- Cover defined
int and std::string return values streamed through std::cout; require successful compile, link, execution, and expected terminal output with no undefined __cxa_* diagnostics.
- Retain an undefined-function linker-failure control to prove diagnostics name the user symbol rather than a C++ runtime symbol.
- Apply the smallest confirmed fix to the worker or compile-plan execution, preserving all driver-selected linker arguments.
- Extend browser smoke coverage to replace the editor content with the defined
int val(){ return 5; } stream-insertion program and compile/run it through the real extension path. Start with Chromium, then run the equivalent smoke on each supported browser target if the shared compiler path is unchanged.
Acceptance criteria
- A defined
int val(){ return 5; } used in std::cout << val(); compiles, links, runs, and prints 5.
- A defined function returning
std::string can be streamed successfully.
- Successful valid cases have no undefined
__cxa_* diagnostics.
- An undefined declared function continues to report a linker failure naming the user symbol.
- The new artifact-aware E2E test and Chromium browser smoke exercise real stream insertion through the compiler worker.
- Lint, build, E2E suite, and required browser smoke tests pass.
Likely files
src/workers/compiler.worker.js
src/workers/compile-plan.mjs (only if plan parsing loses driver argv)
- a new real-toolchain E2E test under
scripts/
scripts/smoke-browser.mjs
Evidence
The sysroot contains libc++.a, libc++abi.a, and compiler builtins, while the worker separately discovers driver commands and invokes wasm-ld in a fresh virtual filesystem. The investigation must confirm that the selected linker inputs remain available and correctly ordered there.
Problem
Compiling a defined, streamable function return value can fail during WASM linking. Example that must compile and run:
Observed diagnostics include:
This points to the browser compiler worker's direct Clang/LLD invocation and C++ exception/runtime library linkage, rather than to the source expression itself.
Proposed plan
clang++ -###output, parsedplan.linkStep.args, and the existence of every driver-selected startup object, archive, and-Lpath in the fresh LLD virtual filesystem immediately before invokingwasm-ld.clang++ -###->-cc1->wasm-ldpipeline. Because the packaged compiler modules cannot be loaded directly in Node without a loader adaptation, use a browser/Worker-based harness, a deliberate loader shim, or extracted reusable worker logic; do not duplicate the worker pipeline in a mock-only test.intandstd::stringreturn values streamed throughstd::cout; require successful compile, link, execution, and expected terminal output with no undefined__cxa_*diagnostics.int val(){ return 5; }stream-insertion program and compile/run it through the real extension path. Start with Chromium, then run the equivalent smoke on each supported browser target if the shared compiler path is unchanged.Acceptance criteria
int val(){ return 5; }used instd::cout << val();compiles, links, runs, and prints5.std::stringcan be streamed successfully.__cxa_*diagnostics.Likely files
src/workers/compiler.worker.jssrc/workers/compile-plan.mjs(only if plan parsing loses driver argv)scripts/scripts/smoke-browser.mjsEvidence
The sysroot contains
libc++.a,libc++abi.a, and compiler builtins, while the worker separately discovers driver commands and invokeswasm-ldin a fresh virtual filesystem. The investigation must confirm that the selected linker inputs remain available and correctly ordered there.