|
1 |
| -//@ revisions: other other-linux x86_64-pc-windows-gnu s390x-linux sparc64-linux powerpc-linux |
2 | 1 | //@ normalize-stderr-test: "(abi|pref|unadjusted_abi_align): Align\([1-8] bytes\)" -> "$1: $$SOME_ALIGN"
|
3 |
| -// ZSTs are only not ignored when the target_env is "gnu", "musl" or "uclibc". However, Rust does |
4 |
| -// not currently support any other target_env on these architectures. |
5 |
| - |
6 |
| -// Ignore the ZST revisions |
7 |
| -//@[other] ignore-x86_64-pc-windows-gnu |
8 |
| -//@[other] ignore-linux |
9 |
| -//@[other-linux] only-linux |
10 |
| -//@[other-linux] ignore-s390x |
11 |
| -//@[other-linux] ignore-sparc64 |
12 |
| -//@[other-linux] ignore-powerpc |
13 |
| - |
14 |
| -// Pass the ZST indirectly revisions |
15 |
| -//@[x86_64-pc-windows-gnu] only-x86_64-pc-windows-gnu |
16 |
| -//@[s390x-linux] only-s390x |
17 |
| -//@[s390x-linux] only-linux |
18 |
| -//@[sparc64-linux] only-sparc64 |
19 |
| -//@[sparc64-linux] only-linux |
20 |
| -//@[powerpc-linux] only-powerpc |
21 |
| -//@[powerpc-linux] only-linux |
22 |
| - |
23 |
| -#![feature(rustc_attrs)] |
| 2 | +/*! |
| 3 | +C doesn't have zero-sized types... except it does. |
| 4 | +
|
| 5 | +Standard C doesn't, but some C compilers, like GCC, implement ZSTs as a compiler extension. |
| 6 | +This historically has wound up interacting with processor-specific ABIs in fairly ad-hoc ways. |
| 7 | +e.g. despite being "zero-sized", sometimes C compilers decide ZSTs consume registers. |
| 8 | +
|
| 9 | +That means these two function signatures may not be compatible: |
| 10 | +
|
| 11 | +``` |
| 12 | +extern "C" fn((), i32, i32); |
| 13 | +extern "C" fn(i32, (), i32); |
| 14 | +``` |
| 15 | +*/ |
| 16 | + |
| 17 | +/* |
| 18 | + * NO ZST IN "C" |
| 19 | + */ |
| 20 | + |
| 21 | +//@ revisions: aarch64-darwin |
| 22 | +//@[aarch64-darwin] compile-flags: --target aarch64-apple-darwin |
| 23 | +//@[aarch64-darwin] needs-llvm-components: aarch64 |
| 24 | + |
| 25 | +//@ revisions: x86_64-linux |
| 26 | +//@[x86_64-linux] compile-flags: --target x86_64-unknown-linux-gnu |
| 27 | +//@[x86_64-linux] needs-llvm-components: x86 |
| 28 | + |
| 29 | + |
| 30 | +/* |
| 31 | + * ZST IN "C" IS PASS-BY-POINTER |
| 32 | + */ |
| 33 | + |
| 34 | +// according to the SRV4 ABI, an aggregate is always passed in registers, |
| 35 | +// and it so happens the GCC extension for ZSTs considers them as structs. |
| 36 | +//@ revisions: powerpc-linux |
| 37 | +//@[powerpc-linux] compile-flags: --target powerpc-unknown-linux-gnu |
| 38 | +//@[powerpc-linux] needs-llvm-components: powerpc |
| 39 | + |
| 40 | +//@ revisions: s390x-linux |
| 41 | +//@[s390x-linux] compile-flags: --target s390x-unknown-linux-gnu |
| 42 | +//@[s390x-linux] needs-llvm-components: systemz |
| 43 | + |
| 44 | +//@ revisions: sparc64-linux |
| 45 | +//@[sparc64-linux] compile-flags: --target sparc64-unknown-linux-gnu |
| 46 | +//@[sparc64-linux] needs-llvm-components: sparc |
| 47 | + |
| 48 | +// The Win64 ABI uses slightly different handling for power-of-2 sizes in the ABI, |
| 49 | +// so GCC decided that ZSTs are pass-by-pointer, as `0.is_power_of_two() == false` |
| 50 | +//@ revisions: x86_64-pc-windows-gnu |
| 51 | +//@[x86_64-pc-windows-gnu] compile-flags: --target x86_64-pc-windows-gnu |
| 52 | +//@[x86_64-pc-windows-gnu] needs-llvm-components: x86 |
| 53 | + |
| 54 | + |
| 55 | +#![feature(lang_items, no_core, rustc_attrs)] |
| 56 | +#![no_core] |
24 | 57 | #![crate_type = "lib"]
|
25 | 58 |
|
| 59 | +#[lang = "sized"] |
| 60 | +trait Sized {} |
| 61 | + |
26 | 62 | #[rustc_abi(debug)]
|
27 | 63 | extern "C" fn pass_zst(_: ()) {} //~ ERROR: fn_abi
|
0 commit comments