diff --git a/compiler/rustc_target/src/spec/abi_map.rs b/compiler/rustc_target/src/spec/abi_map.rs index ce1bdcbb8acc5..e5ff3f2c31d46 100644 --- a/compiler/rustc_target/src/spec/abi_map.rs +++ b/compiler/rustc_target/src/spec/abi_map.rs @@ -85,11 +85,16 @@ impl AbiMap { (ExternAbi::System { .. }, _) => CanonAbi::C, // fallible lowerings + /* multi-platform */ + // always and forever + (ExternAbi::RustInvalid, _) => return AbiMapping::Invalid, + (ExternAbi::EfiApi, Arch::Arm(..)) => CanonAbi::Arm(ArmCall::Aapcs), (ExternAbi::EfiApi, Arch::X86_64) => CanonAbi::X86(X86Call::Win64), (ExternAbi::EfiApi, Arch::Aarch64 | Arch::Riscv | Arch::X86) => CanonAbi::C, (ExternAbi::EfiApi, _) => return AbiMapping::Invalid, + /* arm */ (ExternAbi::Aapcs { .. }, Arch::Arm(..)) => CanonAbi::Arm(ArmCall::Aapcs), (ExternAbi::Aapcs { .. }, _) => return AbiMapping::Invalid, @@ -103,6 +108,12 @@ impl AbiMap { return AbiMapping::Invalid; } + /* gpu */ + (ExternAbi::PtxKernel, Arch::Nvptx) => CanonAbi::GpuKernel, + (ExternAbi::GpuKernel, Arch::Amdgpu | Arch::Nvptx) => CanonAbi::GpuKernel, + (ExternAbi::PtxKernel | ExternAbi::GpuKernel, _) => return AbiMapping::Invalid, + + /* x86 */ (ExternAbi::Cdecl { .. }, Arch::X86) => CanonAbi::C, (ExternAbi::Cdecl { .. }, _) => return AbiMapping::Deprecated(CanonAbi::C), @@ -130,10 +141,7 @@ impl AbiMap { (ExternAbi::Win64 { .. }, Arch::X86_64) => CanonAbi::X86(X86Call::Win64), (ExternAbi::SysV64 { .. } | ExternAbi::Win64 { .. }, _) => return AbiMapping::Invalid, - (ExternAbi::PtxKernel, Arch::Nvptx) => CanonAbi::GpuKernel, - (ExternAbi::GpuKernel, Arch::Amdgpu | Arch::Nvptx) => CanonAbi::GpuKernel, - (ExternAbi::PtxKernel | ExternAbi::GpuKernel, _) => return AbiMapping::Invalid, - + /* interrupts */ (ExternAbi::AvrInterrupt, Arch::Avr) => CanonAbi::Interrupt(InterruptKind::Avr), (ExternAbi::AvrNonBlockingInterrupt, Arch::Avr) => { CanonAbi::Interrupt(InterruptKind::AvrNonBlocking) @@ -156,8 +164,7 @@ impl AbiMap { | ExternAbi::Msp430Interrupt | ExternAbi::RiscvInterruptM | ExternAbi::RiscvInterruptS - | ExternAbi::X86Interrupt - | ExternAbi::RustInvalid, + | ExternAbi::X86Interrupt, _, ) => return AbiMapping::Invalid, }; diff --git a/src/doc/rustc-dev-guide/src/tests/ui.md b/src/doc/rustc-dev-guide/src/tests/ui.md index 8f4467a5551e1..09dc476d68eea 100644 --- a/src/doc/rustc-dev-guide/src/tests/ui.md +++ b/src/doc/rustc-dev-guide/src/tests/ui.md @@ -59,6 +59,11 @@ The output is normalized to ignore unwanted differences, see the [Normalization](#normalization) section. If the file is missing, then compiletest expects the corresponding output to be empty. +A common reason to use normalization, revisions, and most of the other following tools, +is to account for platform differences. Consider alternatives to these tools, like +e.g. using the `extern "rust-invalid"` ABI that is invalid on every platform +instead of fixing the test to use cross-compilation and testing every possibly-invalid ABI. + There can be multiple stdout/stderr files. The general form is: ```text diff --git a/tests/ui/SUMMARY.md b/tests/ui/SUMMARY.md index d807e38dab284..e44959e3564b0 100644 --- a/tests/ui/SUMMARY.md +++ b/tests/ui/SUMMARY.md @@ -8,6 +8,8 @@ For now, only immediate subdirectories under `tests/ui/` are described, but thes These tests deal with *Application Binary Interfaces* (ABI), mostly relating to function name mangling (and the `#[no_mangle]` attribute), calling conventions, or compiler flags which affect ABI. +Tests for unsupported ABIs can be made cross-platform by using the `extern "rust-invalid"` ABI, which is considered unsupported on every platform. + ## `tests/ui/allocator` These tests exercise `#![feature(allocator_api)]` and the `#[global_allocator]` attribute. diff --git a/tests/ui/abi/unsupported-abi-transmute.rs b/tests/ui/abi/unsupported-abi-transmute.rs index 31501bc6d1089..42aa180e1fd85 100644 --- a/tests/ui/abi/unsupported-abi-transmute.rs +++ b/tests/ui/abi/unsupported-abi-transmute.rs @@ -1,15 +1,12 @@ -//@ add-core-stubs -//@ compile-flags: --crate-type=lib --target x86_64-unknown-none -//@ needs-llvm-components: x86 +// Check we error before unsupported ABIs reach codegen stages. + //@ edition: 2018 -#![no_core] -#![feature(no_core, lang_items)] -extern crate minicore; -use minicore::*; +//@ compile-flags: --crate-type=lib +#![feature(rustc_attrs)] -// Check we error before unsupported ABIs reach codegen stages. +use core::mem; fn anything() { - let a = unsafe { mem::transmute::(4) }(2); + let a = unsafe { mem::transmute::(4) }(2); //~^ ERROR: is not a supported ABI for the current target [E0570] } diff --git a/tests/ui/abi/unsupported-abi-transmute.stderr b/tests/ui/abi/unsupported-abi-transmute.stderr index 63056180c71c3..f1d202b1a1c73 100644 --- a/tests/ui/abi/unsupported-abi-transmute.stderr +++ b/tests/ui/abi/unsupported-abi-transmute.stderr @@ -1,8 +1,8 @@ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported-abi-transmute.rs:13:53 +error[E0570]: "rust-invalid" is not a supported ABI for the current target + --> $DIR/unsupported-abi-transmute.rs:10:53 | -LL | let a = unsafe { mem::transmute::(4) }(2); - | ^^^^^^^^^^ +LL | let a = unsafe { mem::transmute::(4) }(2); + | ^^^^^^^^^^^^^^ error: aborting due to 1 previous error diff --git a/tests/ui/abi/unsupported-in-impls.rs b/tests/ui/abi/unsupported-in-impls.rs new file mode 100644 index 0000000000000..71797954865a3 --- /dev/null +++ b/tests/ui/abi/unsupported-in-impls.rs @@ -0,0 +1,36 @@ +// Test for https://github.com/rust-lang/rust/issues/86232 +// Due to AST-to-HIR lowering nuances, we used to allow unsupported ABIs to "leak" into the HIR +// without being checked, as we would check after generating the ExternAbi. +// Checking afterwards only works if we examine every HIR construct that contains an ExternAbi, +// and those may be very different in HIR, even if they read the same in source. +// This made it very easy to make mistakes. +// +// Here we test that an unsupported ABI in various impl-related positions will be rejected, +// both in the original declarations and the actual implementations. + +#![feature(rustc_attrs)] +//@ compile-flags: --crate-type lib + +pub struct FnPtrBearer { + pub ptr: extern "rust-invalid" fn(), + //~^ ERROR: is not a supported ABI +} + +impl FnPtrBearer { + pub extern "rust-invalid" fn inherent_fn(self) { + //~^ ERROR: is not a supported ABI + (self.ptr)() + } +} + +pub trait Trait { + extern "rust-invalid" fn trait_fn(self); + //~^ ERROR: is not a supported ABI +} + +impl Trait for FnPtrBearer { + extern "rust-invalid" fn trait_fn(self) { + //~^ ERROR: is not a supported ABI + self.inherent_fn() + } +} diff --git a/tests/ui/abi/unsupported-in-impls.stderr b/tests/ui/abi/unsupported-in-impls.stderr new file mode 100644 index 0000000000000..d7a188f8a0406 --- /dev/null +++ b/tests/ui/abi/unsupported-in-impls.stderr @@ -0,0 +1,27 @@ +error[E0570]: "rust-invalid" is not a supported ABI for the current target + --> $DIR/unsupported-in-impls.rs:15:21 + | +LL | pub ptr: extern "rust-invalid" fn(), + | ^^^^^^^^^^^^^^ + +error[E0570]: "rust-invalid" is not a supported ABI for the current target + --> $DIR/unsupported-in-impls.rs:20:16 + | +LL | pub extern "rust-invalid" fn inherent_fn(self) { + | ^^^^^^^^^^^^^^ + +error[E0570]: "rust-invalid" is not a supported ABI for the current target + --> $DIR/unsupported-in-impls.rs:27:12 + | +LL | extern "rust-invalid" fn trait_fn(self); + | ^^^^^^^^^^^^^^ + +error[E0570]: "rust-invalid" is not a supported ABI for the current target + --> $DIR/unsupported-in-impls.rs:32:12 + | +LL | extern "rust-invalid" fn trait_fn(self) { + | ^^^^^^^^^^^^^^ + +error: aborting due to 4 previous errors + +For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported-varargs-fnptr.rs b/tests/ui/abi/unsupported-varargs-fnptr.rs index 733e16c7e4bd8..1d23916d03902 100644 --- a/tests/ui/abi/unsupported-varargs-fnptr.rs +++ b/tests/ui/abi/unsupported-varargs-fnptr.rs @@ -1,5 +1,6 @@ // FIXME(workingjubilee): add revisions and generalize to other platform-specific varargs ABIs, // preferably after the only-arch directive is enhanced with an "or pattern" syntax +// NOTE: This deliberately tests an ABI that supports varargs, so no `extern "rust-invalid"` //@ only-x86_64 // We have to use this flag to force ABI computation of an invalid ABI diff --git a/tests/ui/abi/unsupported-varargs-fnptr.stderr b/tests/ui/abi/unsupported-varargs-fnptr.stderr index 445e57df9d861..238f2b3133044 100644 --- a/tests/ui/abi/unsupported-varargs-fnptr.stderr +++ b/tests/ui/abi/unsupported-varargs-fnptr.stderr @@ -1,5 +1,5 @@ error[E0570]: "aapcs" is not a supported ABI for the current target - --> $DIR/unsupported-varargs-fnptr.rs:13:20 + --> $DIR/unsupported-varargs-fnptr.rs:14:20 | LL | fn aapcs(f: extern "aapcs" fn(usize, ...)) { | ^^^^^^^ diff --git a/tests/ui/abi/unsupported.aarch64.stderr b/tests/ui/abi/unsupported.aarch64.stderr index 85e251a65d20e..b89f7359b3f04 100644 --- a/tests/ui/abi/unsupported.aarch64.stderr +++ b/tests/ui/abi/unsupported.aarch64.stderr @@ -156,30 +156,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "cdecl" is not a supported ABI for the current target --> $DIR/unsupported.rs:99:17 | @@ -221,6 +197,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 29 previous errors; 4 warnings emitted +error: aborting due to 25 previous errors; 4 warnings emitted For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported.arm.stderr b/tests/ui/abi/unsupported.arm.stderr index a4274d0ac6038..173cbf9715b69 100644 --- a/tests/ui/abi/unsupported.arm.stderr +++ b/tests/ui/abi/unsupported.arm.stderr @@ -138,30 +138,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "cdecl" is not a supported ABI for the current target --> $DIR/unsupported.rs:99:17 | @@ -203,6 +179,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 26 previous errors; 4 warnings emitted +error: aborting due to 22 previous errors; 4 warnings emitted For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported.riscv32.stderr b/tests/ui/abi/unsupported.riscv32.stderr index 7ef7cae5057ef..cb9b758a73046 100644 --- a/tests/ui/abi/unsupported.riscv32.stderr +++ b/tests/ui/abi/unsupported.riscv32.stderr @@ -150,30 +150,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "cdecl" is not a supported ABI for the current target --> $DIR/unsupported.rs:99:17 | @@ -215,6 +191,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 28 previous errors; 4 warnings emitted +error: aborting due to 24 previous errors; 4 warnings emitted For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported.riscv64.stderr b/tests/ui/abi/unsupported.riscv64.stderr index 7ef7cae5057ef..cb9b758a73046 100644 --- a/tests/ui/abi/unsupported.riscv64.stderr +++ b/tests/ui/abi/unsupported.riscv64.stderr @@ -150,30 +150,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "cdecl" is not a supported ABI for the current target --> $DIR/unsupported.rs:99:17 | @@ -215,6 +191,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 28 previous errors; 4 warnings emitted +error: aborting due to 24 previous errors; 4 warnings emitted For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported.rs b/tests/ui/abi/unsupported.rs index 4bb732c94ac36..0ee310676baab 100644 --- a/tests/ui/abi/unsupported.rs +++ b/tests/ui/abi/unsupported.rs @@ -136,27 +136,3 @@ extern "C-cmse-nonsecure-entry" {} extern "cdecl" {} //[x64_win]~^ WARN unsupported_calling_conventions //[x64_win]~^^ WARN this was previously accepted - -struct FnPtrBearer { - ptr: extern "thiscall" fn(), - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ ERROR: is not a supported ABI -} - -impl FnPtrBearer { - pub extern "thiscall" fn inherent_fn(self) { - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ ERROR: is not a supported ABI - (self.ptr)() - } -} - -trait Trait { - extern "thiscall" fn trait_fn(self); - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ ERROR: is not a supported ABI -} - -impl Trait for FnPtrBearer { - extern "thiscall" fn trait_fn(self) { - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ ERROR: is not a supported ABI - self.inherent_fn() - } -} diff --git a/tests/ui/abi/unsupported.x64.stderr b/tests/ui/abi/unsupported.x64.stderr index 7b021dff7c900..1a7b01375cfb4 100644 --- a/tests/ui/abi/unsupported.x64.stderr +++ b/tests/ui/abi/unsupported.x64.stderr @@ -132,30 +132,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "cdecl" is not a supported ABI for the current target --> $DIR/unsupported.rs:99:17 | @@ -197,6 +173,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 25 previous errors; 4 warnings emitted +error: aborting due to 21 previous errors; 4 warnings emitted For more information about this error, try `rustc --explain E0570`. diff --git a/tests/ui/abi/unsupported.x64_win.stderr b/tests/ui/abi/unsupported.x64_win.stderr index 4ce5b3340d123..82b64e45b01f0 100644 --- a/tests/ui/abi/unsupported.x64_win.stderr +++ b/tests/ui/abi/unsupported.x64_win.stderr @@ -100,30 +100,6 @@ error[E0570]: "C-cmse-nonsecure-entry" is not a supported ABI for the current ta LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:17 - | -LL | ptr: extern "thiscall" fn(), - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:146:16 - | -LL | pub extern "thiscall" fn inherent_fn(self) { - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:153:12 - | -LL | extern "thiscall" fn trait_fn(self); - | ^^^^^^^^^^ - -error[E0570]: "thiscall" is not a supported ABI for the current target - --> $DIR/unsupported.rs:158:12 - | -LL | extern "thiscall" fn trait_fn(self) { - | ^^^^^^^^^^ - warning: "stdcall" is not a supported ABI for the current target --> $DIR/unsupported.rs:81:19 | @@ -215,6 +191,6 @@ LL | extern "cdecl" fn cdecl() {} = note: for more information, see issue #137018 = help: use `extern "C"` instead -error: aborting due to 21 previous errors; 9 warnings emitted +error: aborting due to 17 previous errors; 9 warnings emitted For more information about this error, try `rustc --explain E0570`.