Make wasm-bindgen compatible with the standard C ABI#3595
Make wasm-bindgen compatible with the standard C ABI#3595Liamolucko merged 7 commits intowasm-bindgen:mainfrom
wasm-bindgen compatible with the standard C ABI#3595Conversation
For some reason a couple of functions got switched around; no actual meaningful changes.
|
I've given it a quick glance, really nice solution! I imagined this to be way messier, but it's pretty neat! Even though this only touched unstable ABI would you mind adding an entry in the changelog? Thinking of deployment here, we could expose an unstable |
Done. I've also just realised that I forgot to add a changelog entry in #3554, should I open a PR to add one? (edit: opened #3599)
I'm not sure what you mean. The new generated bindings still work fine with the existing C ABI, the whole point is that they now work with both that and the standard one. So there's no need for this to be unstable. I'm now realising that I've been using the word 'ABI' to mean two different things interchangeably: actual Rust ABIs like |
I mean specifically to switch to the new ABI, that doesn't work until Rust fixes it's C ABI, right? |
I've been assuming that Rust will just directly cut over to the fixed ABI, so that all of Are you suggesting that there should be some kind of testing period, where there's a perma-nightly |
I was assuming that this would be the case, but I'm not advocating for it. If we can skip it and move directly to the fixed C ABI I'm fine with that, but that's not up to us. In any case, there's nothing for us to do here right now until we know what will happen on Rusts side. |
Co-authored-by: daxpedda <daxpedda@gmail.com>
This is the first step of #3454: making
wasm-bindgencompatible with the standard(ish) Wasm C ABI, whichclanguses.This PR more or less implements @alexcrichton's suggestion in #3454 (comment), to allow
{From,Into}WasmAbiimpls to manually specify multiple types thatSelfshould get splatted into when passed as an argument. I implemented it a bit differently though - instead of actually adding multiple associated types to{From,Into}WasmAbi, I changed the meaning ofWasmAbi:This means that
{From,Into}WasmAbiimpls can still return single, typed values like before, and then it's up to those types to implementWasmAbiand specify how they should be splatted. Also,WasmAbitypes no longer actually have to be FFI-safe themselves - even when they're passed as return values,splitis still called, and those values are then put into a#[repr(C)]struct (WasmRet<T>).The new trait
WasmPrimitivenow has the old meaning ofWasmAbi, minus allowing#[repr(C)]types - any Wasm primitive type.This PR doesn't actually change
wasm-bindgen's ABI at all, just how it's implemented. This meant that I didn't have to touch the CLI.One thing that this PR doesn't fix is #3552.
extern "C"functions still return#[repr(C)]structs the same as before, since the retptr handling happens to be the same between the current and standard C ABI. That is, unless you turn on multivalue, in which case the return value will get splatted with the current ABI. (I'm referring torustc'smultivaluetarget feature here, notwasm-bindgen's own multivalue post processing step.)It's not a blocker for migrating the ABI, since
wasm-bindgen's already broken when multivalue is enabled, but it's still be nice to fix it.I'm not sure how it could be fixed without always using a retptr though, which I'd rather avoid. I've experimented a little with type system shenanigans like this:
There'd be one impl where
RetptrandRetget set to()andSelf::Prim1respectively, ifSelf's last 3 primitives are all(), and another one whereRetptrandRetget set to*mut WasmRet<Self>and()respectively, ifSelf::Prim2(and potentiallyPrim3,Prim4) isn't(). Then a generated importfoo() -> Twould look something like this:Unfortunately, I couldn't convince
rustcthatPrim2not being()meant that those two impls didn't conflict. Maybe someone who's more of a type system guru than me can figure it out, but it might be impossible without specialisation. It'll become unnecessary if/when the C ABI gets fixed anyway.