-
Notifications
You must be signed in to change notification settings - Fork 1.6k
Description
Most of the public API surface for working with Wasm-visible storage in Wasmtime takes an AsContextMut parameter. For random examples, StructRef::field, Memory::data, and Table::get all take either an AsContext/AsContextMut or an Into<StoreContext{,Mut}>.
It makes sense that accessors require "the store" (in some vague sense) to access the linear memories, tables, and GC heap, because all of these units of storage are owned by the store.
However, in the context of the guest-debugging API, it turns out that we need to expose an AsContextMut from the "debug session" handle type in #11826, because without that, while the debug session owns the store, there is no way to actually do anything with GC refs that one reads out, or read data in the linear memories, etc. In other words, regular debugger access will want to get at the guest's data and objects.
Likewise, In #11769 I put accessors for the values on stack (locals and operand stack) directly on a StackView, and this suffices for core Wasm types (ints/floats/vectors) but as soon as one actually wants to examine a GC ref that one reads out, one will want an AsContextMut.
This is possible (and I've done it in the draft #11826 in the latest commit), and I believe it's still sound (one can view a "debugger pause" as like a hostcall; so it morally has access to whatever a Caller has access to, and Caller impls AsContextMut), but I don't like it because it forces over-monomorphization: it means that the whole debugger API gets the T from the Store. It also interacts somewhat poorly with internals: for example, AutoAssertNoGc holds the StoreOpaque, but we actually want to hold the StoreInner<T> if we want to be able to pass out a StoreContextMut.
It seems like we should define traits that morally wrap the StoreOpaque, and are sufficient to get at Wasm-accessible objects (linear memories, tables, GC), since none of those can be dependent on the host-side T anyway; and then add the right impls to make that automatically work as before with AsContextMut-types. Function calls still need the monomorphized StoreContextMut because a Caller can pop out the other end that needs the T. Stated succinctly: access to Wasm data should not need T so is not monomorphized; calls to Wasm code does need T so is monomorphized. Thoughts?