Compile ctc-emcc and ctc-wasm-ld native launchers if not already present. Uses clang-tool-chain's compile-native command to build native C++ wrappers that bypass Python/Node startup overhead for emcc and wasm-ld invocations. The binaries are cached in .build/native-tools/ and reused acr
()
| 191 | |
| 192 | |
| 193 | def ensure_native_tools() -> bool: |
| 194 | """Compile ctc-emcc and ctc-wasm-ld native launchers if not already present. |
| 195 | |
| 196 | Uses clang-tool-chain's compile-native command to build native C++ wrappers |
| 197 | that bypass Python/Node startup overhead for emcc and wasm-ld invocations. |
| 198 | The binaries are cached in .build/native-tools/ and reused across builds. |
| 199 | |
| 200 | Returns True if native tools are available. |
| 201 | """ |
| 202 | global _native_tools_dir, _native_emcc, _native_wasm_ld |
| 203 | |
| 204 | if _native_emcc is not None: |
| 205 | return True |
| 206 | |
| 207 | project_root = Path(__file__).parent.parent |
| 208 | tools_dir = project_root / ".build" / "native-tools" |
| 209 | _native_tools_dir = tools_dir |
| 210 | |
| 211 | is_windows = platform.system().lower() == "windows" |
| 212 | exe_suffix = ".exe" if is_windows else "" |
| 213 | |
| 214 | emcc_bin = tools_dir / f"ctc-emcc{exe_suffix}" |
| 215 | wasm_ld_bin = tools_dir / f"ctc-wasm-ld{exe_suffix}" |
| 216 | |
| 217 | if emcc_bin.exists() and wasm_ld_bin.exists(): |
| 218 | _native_emcc = str(emcc_bin) |
| 219 | _native_wasm_ld = str(wasm_ld_bin) |
| 220 | return True |
| 221 | |
| 222 | # Compile native tools using clang-tool-chain |
| 223 | try: |
| 224 | from clang_tool_chain.commands.compile_native import compile_native |
| 225 | |
| 226 | print("[WASM] Compiling native WASM launchers (one-time)...") |
| 227 | rc = compile_native(str(tools_dir)) |
| 228 | if rc == 0 and emcc_bin.exists() and wasm_ld_bin.exists(): |
| 229 | _native_emcc = str(emcc_bin) |
| 230 | _native_wasm_ld = str(wasm_ld_bin) |
| 231 | return True |
| 232 | except Exception as e: |
| 233 | print(f"[WASM] Native tool compilation failed: {e}") |
| 234 | |
| 235 | return False |
| 236 | |
| 237 | |
| 238 | def get_native_emcc() -> Optional[str]: |
no test coverage detected