1
Fork 0

the wasm ABI behavior is a bug

This commit is contained in:
Ralf Jung 2023-09-07 16:04:22 +02:00
parent 243ef313a5
commit 28d152935e
3 changed files with 15 additions and 11 deletions

View file

@ -36,7 +36,10 @@ pub enum PassMode {
Ignore,
/// Pass the argument directly.
///
/// The argument has a layout abi of `Scalar`, `Vector` or in rare cases (e.g. on wasm) `Aggregate`.
/// The argument has a layout abi of `Scalar` or `Vector`.
/// Unfortunately due to past mistakes, in rare cases on wasm, it can also be `Aggregate`.
/// This is bad since it leaks LLVM implementation details into the ABI.
/// (Also see <https://github.com/rust-lang/rust/issues/115666>.)
Direct(ArgAttributes),
/// Pass a pair's elements directly in two arguments.
///
@ -527,7 +530,7 @@ impl<'a, Ty> ArgAbi<'a, Ty> {
scalar_attrs(&layout, b, a.size(cx).align_to(b.align(cx).abi)),
),
Abi::Vector { .. } => PassMode::Direct(ArgAttributes::new()),
// The `Aggregate` ABI is almost always adjusted later.
// The `Aggregate` ABI should always be adjusted later.
Abi::Aggregate { .. } => PassMode::Direct(ArgAttributes::new()),
};
ArgAbi { layout, mode }

View file

@ -61,6 +61,10 @@ where
/// The purpose of this ABI is for matching the WebAssembly standard. This
/// intentionally diverges from the C ABI and is specifically crafted to take
/// advantage of LLVM's support of multiple returns in WebAssembly.
///
/// This ABI is *bad*! It uses `PassMode::Direct` for `abi::Aggregate` types, which leaks LLVM
/// implementation details into the ABI. It's just hard to fix because ABIs are hard to change.
/// Also see <https://github.com/rust-lang/rust/issues/115666>.
pub fn compute_wasm_abi_info<Ty>(fn_abi: &mut FnAbi<'_, Ty>) {
if !fn_abi.ret.is_ignore() {
classify_ret(&mut fn_abi.ret);