(in_wasm, out_wasm, outfile_js, js_syms, finalize=True, base_metadata=None)
| 354 | |
| 355 | |
| 356 | def emscript(in_wasm, out_wasm, outfile_js, js_syms, finalize=True, base_metadata=None): |
| 357 | # Overview: |
| 358 | # * Run wasm-emscripten-finalize to extract metadata and modify the binary |
| 359 | # to use emscripten's wasm<->JS ABI |
| 360 | # * Use the metadata to generate the JS glue that goes with the wasm |
| 361 | |
| 362 | # set file locations, so that JS glue can find what it needs |
| 363 | settings.WASM_BINARY_FILE = js_manipulation.escape_for_js_string(os.path.basename(out_wasm)) |
| 364 | |
| 365 | if finalize: |
| 366 | metadata = finalize_wasm(in_wasm, out_wasm, js_syms) |
| 367 | else: |
| 368 | # Skip finalize and only extract the metadata. |
| 369 | if in_wasm != out_wasm: |
| 370 | shutil.copy(in_wasm, out_wasm) |
| 371 | metadata = get_metadata(in_wasm, out_wasm, False, []) |
| 372 | |
| 373 | # If the binary has already been finalized the settings have already been |
| 374 | # updated and we can skip updating them. |
| 375 | if finalize: |
| 376 | update_settings_glue(out_wasm, metadata, base_metadata) |
| 377 | |
| 378 | if not settings.WASM_BIGINT and metadata.em_js_funcs: |
| 379 | for em_js_func, raw in metadata.em_js_funcs.items(): |
| 380 | args, _ = raw.split('<::>', 1) |
| 381 | args = args[1:-1].strip() |
| 382 | |
| 383 | if not args or args == 'void': |
| 384 | args = [] |
| 385 | else: |
| 386 | args = args.split(',') |
| 387 | signature = metadata.em_js_func_types.get(em_js_func) |
| 388 | if signature and len(signature.params) != len(args): |
| 389 | diagnostics.warning('em-js-i64', 'using 64-bit arguments in EM_JS function without WASM_BIGINT is not yet fully supported: `%s` (%s, %s)', em_js_func, args, signature.params) |
| 390 | |
| 391 | asm_consts = create_asm_consts(metadata) |
| 392 | em_js_funcs = create_em_js(metadata) |
| 393 | |
| 394 | if settings.SIDE_MODULE: |
| 395 | # When building side modules, validate the EM_ASM and EM_JS string by running |
| 396 | # them through node. Without this step, syntax errors are not surfaced |
| 397 | # until runtime. |
| 398 | # We use subprocess directly here rather than shared.check_call since |
| 399 | # check_call doesn't support the `input` argument. |
| 400 | if asm_consts: |
| 401 | validate = '\n'.join([f'var tmp = {f};' for _, f in asm_consts]) |
| 402 | proc = subprocess.run([*config.NODE_JS, '--check', '-'], input=validate.encode('utf-8')) |
| 403 | if proc.returncode: |
| 404 | exit_with_error(f'EM_ASM function validation failed (node returned {proc.returncode})') |
| 405 | |
| 406 | if em_js_funcs: |
| 407 | validate = '\n'.join(em_js_funcs) |
| 408 | proc = subprocess.run([*config.NODE_JS, '--check', '-'], input=validate.encode('utf-8')) |
| 409 | if proc.returncode: |
| 410 | exit_with_error(f'EM_JS function validation failed (node returned {proc.returncode})') |
| 411 | |
| 412 | if not outfile_js: |
| 413 | report_missing_exports_wasm_only(metadata) |
nothing calls this directly
no test coverage detected