alexcrichton opened issue #14945:
This test:
target aarch64 function %f(i64, i64, i64, i64, i64, i64, i64, i128, i64) -> i64 system_v { block0(v0: i64, v1: i64, v2: i64, v3: i64, v4: i64, v5: i64, v6: i64, v7: i128, v8: i64): return v8 } function %f_apple(i64, i64, i64, i64, i64, i64, i64, i128, i64) -> i64 apple_aarch64 { block0(v0: i64, v1: i64, v2: i64, v3: i64, v4: i64, v5: i64, v6: i64, v7: i128, v8: i64): return v8 }reads the last argument from
x7:$ cargo run -p cranelift-tools -- compile --target aarch64 -D i128-ngrn.clif Disassembly of 20 bytes <%f>: 0: fd 7b bf a9 stp x29, x30, [sp, #-0x10]! 4: fd 03 00 91 mov x29, sp 8: e0 03 07 aa mov x0, x7 c: fd 7b c1 a8 ldp x29, x30, [sp], #0x10 10: c0 03 5f d6 ret Disassembly of 20 bytes <%f_apple>: 0: fd 7b bf a9 stp x29, x30, [sp, #-0x10]! 4: fd 03 00 91 mov x29, sp 8: e0 03 07 aa mov x0, x7 c: fd 7b c1 a8 ldp x29, x30, [sp], #0x10 10: c0 03 5f d6 retbut the equivalent C:
long f(long a0, long a1, long a2, long a3, long a4, long a5, long a6, __int128 b, long c) { return c; }reads it from the stack with both GCC and clang:
$ aarch64-linux-gnu-gcc -O2 -S -o - i128-ngrn.c f: ldr x0, [sp, 16] $ clang --target=arm64-apple-darwin -O2 -S -o - i128-ngrn.c _f: ldr x0, [sp, #16]<details>
<summary>Details</summary>AAPCS64 stage C: an
i128that doesn't fit in the remaining integer
registers goes on the stack, and C.13 then sets NGRN = 8, so every later
integer argument goes on the stack too. Clang does the same for Darwin. In
compute_arg_locs(cranelift/codegen/src/isa/aarch64/abi.rs), when the
register pair doesn't fit, thei128goes on the stack butnext_xregis
left at 7, so the followingi64getsx7. Settingnext_xreg = max_per_class_reg_valsin that case should fix both calling conventions.Cranelift-to-Cranelift calls agree with each other, so this only shows up
when such a signature is shared with C/Rust code (e.g. cranelift-jit,
cg_clif). Wasmtime never passesi128across a call boundary.</details>
alexcrichton added the bug label to Issue #14945.
alexcrichton added the cranelift label to Issue #14945.
alexcrichton added the cranelift:area:aarch64 label to Issue #14945.
cfallin closed issue #14945:
This test:
target aarch64 function %f(i64, i64, i64, i64, i64, i64, i64, i128, i64) -> i64 system_v { block0(v0: i64, v1: i64, v2: i64, v3: i64, v4: i64, v5: i64, v6: i64, v7: i128, v8: i64): return v8 } function %f_apple(i64, i64, i64, i64, i64, i64, i64, i128, i64) -> i64 apple_aarch64 { block0(v0: i64, v1: i64, v2: i64, v3: i64, v4: i64, v5: i64, v6: i64, v7: i128, v8: i64): return v8 }reads the last argument from
x7:$ cargo run -p cranelift-tools -- compile --target aarch64 -D i128-ngrn.clif Disassembly of 20 bytes <%f>: 0: fd 7b bf a9 stp x29, x30, [sp, #-0x10]! 4: fd 03 00 91 mov x29, sp 8: e0 03 07 aa mov x0, x7 c: fd 7b c1 a8 ldp x29, x30, [sp], #0x10 10: c0 03 5f d6 ret Disassembly of 20 bytes <%f_apple>: 0: fd 7b bf a9 stp x29, x30, [sp, #-0x10]! 4: fd 03 00 91 mov x29, sp 8: e0 03 07 aa mov x0, x7 c: fd 7b c1 a8 ldp x29, x30, [sp], #0x10 10: c0 03 5f d6 retbut the equivalent C:
long f(long a0, long a1, long a2, long a3, long a4, long a5, long a6, __int128 b, long c) { return c; }reads it from the stack with both GCC and clang:
$ aarch64-linux-gnu-gcc -O2 -S -o - i128-ngrn.c f: ldr x0, [sp, 16] $ clang --target=arm64-apple-darwin -O2 -S -o - i128-ngrn.c _f: ldr x0, [sp, #16]<details>
<summary>Details</summary>AAPCS64 stage C: an
i128that doesn't fit in the remaining integer
registers goes on the stack, and C.13 then sets NGRN = 8, so every later
integer argument goes on the stack too. Clang does the same for Darwin. In
compute_arg_locs(cranelift/codegen/src/isa/aarch64/abi.rs), when the
register pair doesn't fit, thei128goes on the stack butnext_xregis
left at 7, so the followingi64getsx7. Settingnext_xreg = max_per_class_reg_valsin that case should fix both calling conventions.Cranelift-to-Cranelift calls agree with each other, so this only shows up
when such a signature is shared with C/Rust code (e.g. cranelift-jit,
cg_clif). Wasmtime never passesi128across a call boundary.</details>
Last updated: Oct 31 2026 at 23:03 UTC