Stream: git-wasmtime

Topic: wasmtime / issue #11651 `Access::instance` panics


view this post on Zulip Wasmtime GitHub notifications bot (Sep 09 2025 at 14:22):

rvolosatovs opened issue #11651:

Test Case

Use store option to bindgen without async or simply call instance on Access returned by Access::new

Steps to Reproduce

apply the following diff to #11649

diff --git a/crates/wasi-http/src/p3/bindings.rs b/crates/wasi-http/src/p3/bindings.rs
index b7fec724c1..9f2bd8e9cf 100644
--- a/crates/wasi-http/src/p3/bindings.rs
+++ b/crates/wasi-http/src/p3/bindings.rs
@@ -11,8 +11,8 @@ mod generated {
             "wasi:http/types/[drop]response": store | trappable | tracing,
             "wasi:http/types/[method]request.consume-body": async | store | trappable | tracing,
             "wasi:http/types/[method]response.consume-body": async | store | trappable | tracing,
-            "wasi:http/types/[static]request.new": async | store | trappable | tracing,
-            "wasi:http/types/[static]response.new": async | store | trappable | tracing,
+            "wasi:http/types/[static]request.new": store | trappable | tracing,
+            "wasi:http/types/[static]response.new": store | trappable | tracing,
             default: trappable | tracing,
         },
         exports: { default: async | store },
diff --git a/crates/wasi-http/src/p3/host/types.rs b/crates/wasi-http/src/p3/host/types.rs
index 165e4e4e12..3d662da585 100644
--- a/crates/wasi-http/src/p3/host/types.rs
+++ b/crates/wasi-http/src/p3/host/types.rs
@@ -303,45 +303,43 @@ impl HostFields for WasiHttpCtxView<'_> {
 }

 impl HostRequestWithStore for WasiHttp {
-    async fn new<T>(
-        store: &Accessor<T, Self>,
+    fn new<T>(
+        mut store: Access<'_, T, Self>,
         headers: Resource<Headers>,
         contents: Option<StreamReader<u8>>,
         trailers: FutureReader<Result<Option<Resource<Trailers>>, ErrorCode>>,
         options: Option<Resource<RequestOptions>>,
     ) -> wasmtime::Result<(Resource<Request>, FutureReader<Result<(), ErrorCode>>)> {
+        let WasiHttpCtxView { table, .. } = store.get();
+        let headers = delete_fields(table, headers)?;
+        let options = options
+            .map(|options| delete_request_options(table, options))
+            .transpose()?;
+        let (result_tx, result_rx) = oneshot::channel();
+        let body = Body::Guest {
+            contents_rx: contents,
+            trailers_rx: trailers,
+            result_tx,
+        };
+        let req = Request {
+            method: http::Method::GET,
+            scheme: None,
+            authority: None,
+            path_with_query: None,
+            headers: headers.into(),
+            options: options.map(Into::into),
+            body,
+        };
+        let req = table.push(req).context("failed to push request to table")?;
         let instance = store.instance();
-        store.with(|mut store| {
-            let (result_tx, result_rx) = oneshot::channel();
-            let WasiHttpCtxView { table, .. } = store.get();
-            let headers = delete_fields(table, headers)?;
-            let options = options
-                .map(|options| delete_request_options(table, options))
-                .transpose()?;
-            let body = Body::Guest {
-                contents_rx: contents,
-                trailers_rx: trailers,
-                result_tx,
-            };
-            let req = Request {
-                method: http::Method::GET,
-                scheme: None,
-                authority: None,
-                path_with_query: None,
-                headers: headers.into(),
-                options: options.map(Into::into),
-                body,
-            };
-            let req = table.push(req).context("failed to push request to table")?;
-            Ok((
-                req,
-                FutureReader::new(
-                    instance,
-                    &mut store,
-                    GuestBodyResultProducer::Receiver(result_rx),
-                ),
-            ))
-        })
+        Ok((
+            req,
+            FutureReader::new(
+                instance,
+                &mut store,
+                GuestBodyResultProducer::Receiver(result_rx),
+            ),
+        ))
     }

     async fn consume_body<T>(
@@ -586,39 +584,37 @@ impl HostRequestOptions for WasiHttpCtxView<'_> {
 }

 impl HostResponseWithStore for WasiHttp {
-    async fn new<T>(
-        store: &Accessor<T, Self>,
+    fn new<T>(
+        mut store: Access<'_, T, Self>,
         headers: Resource<Headers>,
         contents: Option<StreamReader<u8>>,
         trailers: FutureReader<Result<Option<Resource<Trailers>>, ErrorCode>>,
     ) -> wasmtime::Result<(Resource<Response>, FutureReader<Result<(), ErrorCode>>)> {
+        let WasiHttpCtxView { table, .. } = store.get();
+        let headers = delete_fields(table, headers)?;
+        let (result_tx, result_rx) = oneshot::channel();
+        let body = Body::Guest {
+            contents_rx: contents,
+            trailers_rx: trailers,
+            result_tx,
+        };
+        let res = Response {
+            status: http::StatusCode::OK,
+            headers: headers.into(),
+            body,
+        };
+        let res = table
+            .push(res)
+            .context("failed to push response to table")?;
         let instance = store.instance();
-        store.with(|mut store| {
-            let (result_tx, result_rx) = oneshot::channel();
-            let WasiHttpCtxView { table, .. } = store.get();
-            let headers = delete_fields(table, headers)?;
-            let body = Body::Guest {
-                contents_rx: contents,
-                trailers_rx: trailers,
-                result_tx,
-            };
-            let res = Response {
-                status: http::StatusCode::OK,
-                headers: headers.into(),
-                body,
-            };
-            let res = table
-                .push(res)
-                .context("failed to push response to table")?;
-            Ok((
-                res,
-                FutureReader::new(
-                    instance,
-                    &mut store,
-                    GuestBodyResultProducer::Receiver(result_rx),
-                ),
-            ))
-        })
+        Ok((
+            res,
+            FutureReader::new(
+                instance,
+                &mut store,
+                GuestBodyResultProducer::Receiver(result_rx),
+            ),
+        ))
     }

     async fn consume_body<T>(

Expected Results

Success

Actual Results

thread 'p3::p3_http_outbound_request_unsupported_scheme' panicked at /Users/rvolosatovs/src/github.com/bytecodealliance/wasmtime/crates/wasmtime/src/runtime/component/concurrent.rs:255:23:
called `Option::unwrap()` on a `None` value

Extra Info

This was introduced in #11628

cc @alexcrichton

view this post on Zulip Wasmtime GitHub notifications bot (Sep 09 2025 at 14:22):

rvolosatovs added the bug label to Issue #11651.

view this post on Zulip Wasmtime GitHub notifications bot (Sep 09 2025 at 15:12):

alexcrichton commented on issue #11651:

This is currently an intentional design decision but it's based under the assumption that https://github.com/bytecodealliance/wasmtime/issues/11226 is going to be resolved which means that all the Instance parameters are going to go away. We planned on talking to Luke this Thursday about some various ramifications of this decision as it touches on component model semantics a bit, but after that the hope was to implement that and remove the Instance from Accessor too

view this post on Zulip Wasmtime GitHub notifications bot (Sep 11 2025 at 16:40):

fitzgen added the wasm-proposal:component-model-async label to Issue #11651.

view this post on Zulip Wasmtime GitHub notifications bot (Sep 15 2025 at 16:01):

alexcrichton assigned dicej to issue #11651.

view this post on Zulip Wasmtime GitHub notifications bot (Oct 06 2025 at 20:16):

dicej closed issue #11651:

Test Case

Use store option to bindgen without async or simply call instance on Access returned by Access::new

Steps to Reproduce

apply the following diff to #11649

diff --git a/crates/wasi-http/src/p3/bindings.rs b/crates/wasi-http/src/p3/bindings.rs
index b7fec724c1..9f2bd8e9cf 100644
--- a/crates/wasi-http/src/p3/bindings.rs
+++ b/crates/wasi-http/src/p3/bindings.rs
@@ -11,8 +11,8 @@ mod generated {
             "wasi:http/types/[drop]response": store | trappable | tracing,
             "wasi:http/types/[method]request.consume-body": async | store | trappable | tracing,
             "wasi:http/types/[method]response.consume-body": async | store | trappable | tracing,
-            "wasi:http/types/[static]request.new": async | store | trappable | tracing,
-            "wasi:http/types/[static]response.new": async | store | trappable | tracing,
+            "wasi:http/types/[static]request.new": store | trappable | tracing,
+            "wasi:http/types/[static]response.new": store | trappable | tracing,
             default: trappable | tracing,
         },
         exports: { default: async | store },
diff --git a/crates/wasi-http/src/p3/host/types.rs b/crates/wasi-http/src/p3/host/types.rs
index 165e4e4e12..3d662da585 100644
--- a/crates/wasi-http/src/p3/host/types.rs
+++ b/crates/wasi-http/src/p3/host/types.rs
@@ -303,45 +303,43 @@ impl HostFields for WasiHttpCtxView<'_> {
 }

 impl HostRequestWithStore for WasiHttp {
-    async fn new<T>(
-        store: &Accessor<T, Self>,
+    fn new<T>(
+        mut store: Access<'_, T, Self>,
         headers: Resource<Headers>,
         contents: Option<StreamReader<u8>>,
         trailers: FutureReader<Result<Option<Resource<Trailers>>, ErrorCode>>,
         options: Option<Resource<RequestOptions>>,
     ) -> wasmtime::Result<(Resource<Request>, FutureReader<Result<(), ErrorCode>>)> {
+        let WasiHttpCtxView { table, .. } = store.get();
+        let headers = delete_fields(table, headers)?;
+        let options = options
+            .map(|options| delete_request_options(table, options))
+            .transpose()?;
+        let (result_tx, result_rx) = oneshot::channel();
+        let body = Body::Guest {
+            contents_rx: contents,
+            trailers_rx: trailers,
+            result_tx,
+        };
+        let req = Request {
+            method: http::Method::GET,
+            scheme: None,
+            authority: None,
+            path_with_query: None,
+            headers: headers.into(),
+            options: options.map(Into::into),
+            body,
+        };
+        let req = table.push(req).context("failed to push request to table")?;
         let instance = store.instance();
-        store.with(|mut store| {
-            let (result_tx, result_rx) = oneshot::channel();
-            let WasiHttpCtxView { table, .. } = store.get();
-            let headers = delete_fields(table, headers)?;
-            let options = options
-                .map(|options| delete_request_options(table, options))
-                .transpose()?;
-            let body = Body::Guest {
-                contents_rx: contents,
-                trailers_rx: trailers,
-                result_tx,
-            };
-            let req = Request {
-                method: http::Method::GET,
-                scheme: None,
-                authority: None,
-                path_with_query: None,
-                headers: headers.into(),
-                options: options.map(Into::into),
-                body,
-            };
-            let req = table.push(req).context("failed to push request to table")?;
-            Ok((
-                req,
-                FutureReader::new(
-                    instance,
-                    &mut store,
-                    GuestBodyResultProducer::Receiver(result_rx),
-                ),
-            ))
-        })
+        Ok((
+            req,
+            FutureReader::new(
+                instance,
+                &mut store,
+                GuestBodyResultProducer::Receiver(result_rx),
+            ),
+        ))
     }

     async fn consume_body<T>(
@@ -586,39 +584,37 @@ impl HostRequestOptions for WasiHttpCtxView<'_> {
 }

 impl HostResponseWithStore for WasiHttp {
-    async fn new<T>(
-        store: &Accessor<T, Self>,
+    fn new<T>(
+        mut store: Access<'_, T, Self>,
         headers: Resource<Headers>,
         contents: Option<StreamReader<u8>>,
         trailers: FutureReader<Result<Option<Resource<Trailers>>, ErrorCode>>,
     ) -> wasmtime::Result<(Resource<Response>, FutureReader<Result<(), ErrorCode>>)> {
+        let WasiHttpCtxView { table, .. } = store.get();
+        let headers = delete_fields(table, headers)?;
+        let (result_tx, result_rx) = oneshot::channel();
+        let body = Body::Guest {
+            contents_rx: contents,
+            trailers_rx: trailers,
+            result_tx,
+        };
+        let res = Response {
+            status: http::StatusCode::OK,
+            headers: headers.into(),
+            body,
+        };
+        let res = table
+            .push(res)
+            .context("failed to push response to table")?;
         let instance = store.instance();
-        store.with(|mut store| {
-            let (result_tx, result_rx) = oneshot::channel();
-            let WasiHttpCtxView { table, .. } = store.get();
-            let headers = delete_fields(table, headers)?;
-            let body = Body::Guest {
-                contents_rx: contents,
-                trailers_rx: trailers,
-                result_tx,
-            };
-            let res = Response {
-                status: http::StatusCode::OK,
-                headers: headers.into(),
-                body,
-            };
-            let res = table
-                .push(res)
-                .context("failed to push response to table")?;
-            Ok((
-                res,
-                FutureReader::new(
-                    instance,
-                    &mut store,
-                    GuestBodyResultProducer::Receiver(result_rx),
-                ),
-            ))
-        })
+        Ok((
+            res,
+            FutureReader::new(
+                instance,
+                &mut store,
+                GuestBodyResultProducer::Receiver(result_rx),
+            ),
+        ))
     }

     async fn consume_body<T>(

Expected Results

Success

Actual Results

thread 'p3::p3_http_outbound_request_unsupported_scheme' panicked at /Users/rvolosatovs/src/github.com/bytecodealliance/wasmtime/crates/wasmtime/src/runtime/component/concurrent.rs:255:23:
called `Option::unwrap()` on a `None` value

Extra Info

This was introduced in #11628

cc @alexcrichton


Last updated: Dec 06 2025 at 06:05 UTC