Skip to content

Debugging linking errors when wasm exceptions are enabled #17639

Open
@jlb6740

Description

@jlb6740

Hi, I am trying to build and use an example wasm filter in envoy that needs exception support. I want to preface by saying solving this problem may need to be done 100% in the envoy build system, but I filed an issue here because I am simply looking to better understand what is causing the errors emscripten is reporting during linking. I am also hoping someone can point to an emscripten zulip ro slack channel to share these build experiences and discuss in real time.

But back to the question ... envoy uses bazel for it's build system. The code that I am building builds standalone with exception support using a cmake configuration and runs as expected. In that case the "-fwasm_exceptions" flag is passed as a CMAKE_CXX_FLAGS and that pretty much is it as long as you are using the latest emscripten and node. When building the same code in envoy things become more complicated. Building details are more abstracted, but compiling is more complicated, linking is more complicated, and potentially conflicting build flags sneak in from all over the place.

The best combination of flags I can find is:

With bazel build command:
bazel build --subcommands --verbose_failures --explain --sandbox_debug --features wasm_simd --features exceptions --define libhs_compilation_target=wasm //src:example-plugin.wasm

And build flags
proxy_wasm_cc_binary(
name = "example-plugin.wasm",
srcs = [
"hyperscan_plugin.cc",
],
deps = [
"@hyperscan//:libhs",
],
copts = [
"-fwasm-exceptions",
],
linkopts = [
"-fwasm-exceptions",
],
)

And then commenting out code in building.py in the emsdk/upstream/emscripten/tools directory near lines (231-232):

#if not settings.DISABLE_EXCEPTION_CATCHING:
#   args += ['-enable-emscripten-cxx-exceptions']

Obviously I don't want to comment this code out without understanding the ramifications but I found this flag to be incompatible in the linking phase for emscripten and I couldn't figure out a flag combination to pass in bazel to get rid of it. A wasm filter created in this way and run as a standalone in node seems to work and have exceptions caught properly but a more complex example run in envoy did not. Specifically it compiles and runs, but the exception is not caught and handled in the wasm code at runtime. I can not comment out this code and try other flag combinations including introducing the C++ (non-wasm) exception handling code flags: DISABLE_EXCEPTION_CATCHING, EXCEPTION_CATCHING_ALLOWED, and DISABLE_EXCEPTION_THROWING, but applying these combinations in various levels leads to playing wackamole with linking and even compile errors:

image

In particular I am interested in understanding the "ReferenceError: addCxaCatch is not defined" error. (1) Can someone tell me how to make sure emscripten generates this function? I thought it was done when passing "-s DISABLE_EXCEPTION_THROWING=0" but I guess that just causes it to be expected. I am also not clear on if the -03 options is potentially stripping out exception support. Note during linking bazel/envoy is linking in three files and using these parameters:

--sysroot=external/emscripten_bin_linux/emscripten/cache/sysroot
-fdiagnostics-color
-fno-strict-aliasing
-funsigned-char
-no-canonical-prefixes
-msimd128
-s
PRINTF_LONG_DOUBLE=1
--oformat=js
-O0
bazel-out/wasm-fastbuild-ST-2ed02aadfb4a/bin/src/_objs/proxy_wasm_example-plugin/example_plugin.o
bazel-out/wasm-fastbuild-ST-2ed02aadfb4a/bin/external/example/libhs/lib/libhs.a
bazel-out/wasm-fastbuild-ST-2ed02aadfb4a/bin/external/proxy_wasm_cpp_sdk/libproxy_wasm_intrinsics.a
-fwasm-exceptions
-s
DISABLE_EXCEPTION_THROWING=0
--no-entry
--js-library=external/proxy_wasm_cpp_sdk/proxy_wasm_intrinsics.js
-sSTANDALONE_WASM
-sEXPORTED_FUNCTIONS=_malloc
-o
bazel-out/wasm-fastbuild-ST-2ed02aadfb4a/bin/src/proxy_wasm_example-plugin

I've tried to investigate the building of each of those 3 files but so far haven't found any solution. So my question (2) is when linking is various files where wasm exception support is required, are there certain functions that I can look for when doing wasm2wat or certain build flags or just certain things to look out for when building and linking. (3) Are there any flags in the linking phase above that are missing?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions