Skip to content

Conversation

@andrewweston
Copy link
Contributor

This PR fixes an issue when using the wasip3 http-compat feature.

When the feature is turned on, the http_compat::conversions module uses wit_bindgen::spawn which is now (since 0.48.0) gated behind the async-spawn feature flag.

@alexcrichton
Copy link
Member

Thanks! It's intentional that the main crate doesn't depend on async-spawn to keep dependencies slim. Can this dependency be part of the http-compat feature specifically? Additionally, can you update CI to have a command which fails beforehand but passes after this PR? (e.g. checks that the http-compat feature builds in isolation)

@andrewweston
Copy link
Contributor Author

Certainly, I'll do this this afternoon.

While you are there, I am getting a separate but related issue: Once compiled, when I try to run a simple http guest (using wasmtime 39.0.0) I am getting the following error:

Error: failed to parse WebAssembly module

Caused by:
    invalid leading byte (0x43) for component defined type (at offset 0x5afc7)

A quick look using a hex editor show the offending byte is the C character (as 0x43 would indicate) in

C��request ���������8[async-lift]wasi:http/handler@0.3.0-rc-2025-09-16#handle

Do you have any thoughts before I invest too much time?

@alexcrichton
Copy link
Member

That's "just" a version mismatch in that you're running a binary in Wasmtime-too-old to support it. This is a recently-done change for component-model-async, and you'll want to use Wasmtime's main branch to support it.

@andrewweston
Copy link
Contributor Author

Hah! I'm glad I asked It would have taken me a while to get there. Thanks.

@andrewweston
Copy link
Contributor Author

@alexcrichton I've finally had a chance to get back to this and can report the changes you requested are quite straightforward. However, I've had a bit of a struggle getting a build working. There are 2 ways I can get a successful build:

  1. Using Rust nightly
  2. Building from the project we use as a wrapper for wasmtime (using Rust 1.91).

I have no idea why option 2 works. I can even use a path-based reference to wasip3/examples/http-proxy.rs in the wasi-rs project.

For now, I am proposing to use +nightly when building the wasip3 crate in the GitHub workflow (unless it magically works on linux/amd). Thoughts?

@alexcrichton
Copy link
Member

Sorry I'm not sure I understand, why is nightly related here? Do you have logs or something similar to look at?

FWIW locally in this repository I can reproduce the failure with cargo build -p wasip3 --features http-compat and this is the fix I'm suggesting:

diff --git a/crates/wasip3/Cargo.toml b/crates/wasip3/Cargo.toml
index dff0c16..cfadb6e 100644
--- a/crates/wasip3/Cargo.toml
+++ b/crates/wasip3/Cargo.toml
@@ -17,6 +17,7 @@ http-compat = [
     "dep:http-body",
     "dep:http",
     "dep:thiserror",
+    "wit-bindgen/async-spawn",
 ]

 [dependencies]

@andrewweston
Copy link
Contributor Author

Yes, that is the change I have made. I was in the process of adding the CI check and realised I could not build the example locally. Running

cargo build -p wasip3 --example http-proxy --target wasm32-wasip2

results in the following linker error:

Compiling wasip3 v0.3.0+wasi-0.3.0-rc-2025-09-16 (/Users/andrewweston/rust/github.com/bytecodeallicance/wasi-rs/crates/wasip3)
error: linking with `wasm-component-ld` failed: exit status: 1
  |
  = note:  "wasm-component-ld" "-flavor" "wasm" "--export" "[async-lift]wasi:http/handler@0.3.0-rc-2025-09-16#handle" "--export" "[callback][async-lift]wasi:http/handler@0.3.0-rc-2025-09-16#handle" "--export" "cabi_realloc" "-z" "stack-size=1048576" "--stack-first" "--allow-undefined" "--no-demangle" "<52 object files omitted>" "<sysroot>/lib/rustlib/wasm32-wasip2/lib/libpanic_abort-*.rlib" "/Users/andrewweston/rust/github.com/credibil/wasi-rs/target/wasm32-wasip2/debug/deps/{libhttp-09010019726564dc,libitoa-d51820080b70444e,libbytes-e34527135517c1c5,libwasip3-33268fbdeb0dbfeb,libwit_bindgen-5c04fe2b69135438,libfutures-d67b4af1d3df50b9,libfutures_executor-cfa048bccf402e97,libfutures_util-e94dc5f7e974b5ab,libmemchr-1a50bf734693cd57,libfutures_io-6e2f1d38b1c22d90,libslab-4836812055fc8663,libfutures_channel-2a90decf1c72a53c,libpin_project_lite-f56fcbaaeba2ab50,libfutures_sink-9e2876f5209a73af,libfutures_task-fdd39ee6fedab562,libpin_utils-d7a9662ed3cbc393,libfutures_core-f6a25439bf07949a}.rlib" "<sysroot>/lib/rustlib/wasm32-wasip2/lib/{libstd-*,libwasi-*,libwasi-*,libwit_bindgen-*,libcfg_if-*,librustc_demangle-*,libstd_detect-*,libhashbrown-*,librustc_std_workspace_alloc-*,libminiz_oxide-*,libadler2-*,libunwind-*,liblibc-*}.rlib" "-l" "c" "<sysroot>/lib/rustlib/wasm32-wasip2/lib/{librustc_std_workspace_core-*,liballoc-*,libcore-*,libcompiler_builtins-*}.rlib" "-L" "/Users/andrewweston/rust/github.com/credibil/wasi-rs/target/wasm32-wasip2/debug/build/wit-bindgen-b4f0988555e1479c/out" "-L" "<sysroot>/lib/rustlib/wasm32-wasip2/lib/self-contained" "-o" "/Users/andrewweston/rust/github.com/credibil/wasi-rs/target/wasm32-wasip2/debug/examples/http_proxy-461fd60822606513.wasm" "--gc-sections" "--no-entry" "-O0"
  = note: some arguments are omitted. use `--verbose` to show all linker arguments
  = note: error: failed to parse core wasm for componentization
          
          Caused by:
              0: decoding custom section component-type:wit-bindgen:0.48.0:wasi:http@0.3.0-rc-2025-09-16:proxy:imports and exportsrust-wasip3-0.3.0+wasi-0.3.0-rc-2025-09-16-from-crates-io-proxy-world
              1: invalid leading byte (0x43) for component defined type (at offset 0x120)
          

error: could not compile `wasip3` (example "http-proxy") due to 1 previous error

Running

cargo +nightly build -p wasip3 --example http-proxy --target wasm32-wasip2

gives me a clean build.

The other thing to note is that I have not regenerated the pre-compiled code (proxy.rs, imports.rs, command.rs) using wit-bindgen:0.48.1.

@alexcrichton
Copy link
Member

Ah yes that's expected given a recent change to wasip3, but I'm not sure what you meant in (2) above with wasmtime and Rust 1.91?

@andrewweston
Copy link
Contributor Author

(2) was the observation that, weirdly, I can build and run the example from a pre-existing project. I don't believe I'm sufficiently familiar with the intricacies of Rust to completely understand why. And I may well have gotten my wires crossed somewhere along the way.

The project extends wasmtime so we can inject our own resources (kafka, redis, NATS, etc.).

For interest, here's the relevant Cargo :

[dependencies]
...
wasip3 = { path = "../wasi-rs/crates/wasip3", features = ["http-compat"] }

[[example]]
name = "http-proxy"
path = "../wasi-rs/crates/wasip3/examples/http-proxy.rs"
crate-type = ["cdylib"]

I can build and successfully run the example but only from the abovementioned project.

@alexcrichton
Copy link
Member

Ah ok, in that case it might have to do with the fact that these custom sections and such are dependent on various linker shenanigans as to whether they show up in the final artifact. This means that subtle shifts in code can cause large changes in the output. Overall I wouldn't worry too much about it -- if it doesn't compile it's because something needs updating, and if it does compile then it means that the parts which required an updated weren't included so an update wasn't needed.

* fix feature flag

* only turn on async-spawn feature when using http-compat

* add CI check for http-compat feature

* revert inadvertent format changes
* revert async-spawn -> async

* simplify ci

* trigger workflow

* update generated code

* revert generated code

* bump wit-bindgen version in ci

* update generated code

* revert generated code

* use wasm-tools to run component

* use wasm-tools to run component

* use wasm-tools to run component

* debug ci issue

* debug ci issue

* debug ci issue

* debug ci issue

* debug ci issue

* debug ci issue

* fix fmt
@alexcrichton alexcrichton merged commit f8693c2 into bytecodealliance:main Nov 27, 2025
21 checks passed
@andrewweston
Copy link
Contributor Author

Thank you. One interesting takeaway was the CARGO_TARGET_WASM32_WASIP2_LINKER. Using this with wasm-component-ld@0.5.19 has overcome our main project's build issues

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants