| //@ edition: 2021 |
| //@ check-fail |
| //@ needs-asm-support |
| #![feature(abi_custom)] |
| |
| #[unsafe(naked)] |
| extern "custom" fn must_be_unsafe(a: i64) -> i64 { |
| //~^ ERROR functions with the "custom" ABI must be unsafe |
| //~| ERROR invalid signature for `extern "custom"` function |
| std::arch::naked_asm!("") |
| } |
| |
| #[unsafe(naked)] |
| unsafe extern "custom" fn no_parameters(a: i64) { |
| //~^ ERROR invalid signature for `extern "custom"` function |
| std::arch::naked_asm!("") |
| } |
| |
| #[unsafe(naked)] |
| unsafe extern "custom" fn no_return_type() -> i64 { |
| //~^ ERROR invalid signature for `extern "custom"` function |
| std::arch::naked_asm!("") |
| } |
| |
| unsafe extern "custom" fn double(a: i64) -> i64 { |
| //~^ ERROR items with the "custom" ABI can only be declared externally or defined via naked functions |
| //~| ERROR invalid signature for `extern "custom"` function |
| unimplemented!() |
| } |
| |
| struct Thing(i64); |
| |
| impl Thing { |
| unsafe extern "custom" fn is_even(self) -> bool { |
| //~^ ERROR items with the "custom" ABI can only be declared externally or defined via naked functions |
| //~| ERROR invalid signature for `extern "custom"` function |
| unimplemented!() |
| } |
| } |
| |
| trait BitwiseNot { |
| unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { |
| //~^ ERROR items with the "custom" ABI can only be declared externally or defined via naked functions |
| //~| ERROR invalid signature for `extern "custom"` function |
| unimplemented!() |
| } |
| } |
| |
| impl BitwiseNot for Thing {} |
| |
| trait Negate { |
| extern "custom" fn negate(a: i64) -> i64; |
| //~^ ERROR functions with the "custom" ABI must be unsafe |
| //~| ERROR invalid signature for `extern "custom"` function |
| } |
| |
| impl Negate for Thing { |
| extern "custom" fn negate(a: i64) -> i64 { |
| //~^ ERROR items with the "custom" ABI can only be declared externally or defined via naked functions |
| //~| ERROR functions with the "custom" ABI must be unsafe |
| //~| ERROR invalid signature for `extern "custom"` function |
| -a |
| } |
| } |
| |
| unsafe extern "custom" { |
| fn increment(a: i64) -> i64; |
| //~^ ERROR invalid signature for `extern "custom"` function |
| |
| safe fn extern_cannot_be_safe(); |
| //~^ ERROR foreign functions with the "custom" ABI cannot be safe |
| } |
| |
| fn caller(f: unsafe extern "custom" fn(i64) -> i64, mut x: i64) -> i64 { |
| unsafe { f(x) } |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| } |
| |
| fn caller_by_ref(f: &unsafe extern "custom" fn(i64) -> i64, mut x: i64) -> i64 { |
| unsafe { f(x) } |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| } |
| |
| type Custom = unsafe extern "custom" fn(i64) -> i64; |
| |
| fn caller_alias(f: Custom, mut x: i64) -> i64 { |
| unsafe { f(x) } |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| } |
| |
| #[unsafe(naked)] |
| const unsafe extern "custom" fn no_const_fn() { |
| std::arch::naked_asm!("") |
| //~^ ERROR inline assembly is not allowed in constant functions |
| } |
| |
| async unsafe extern "custom" fn no_async_fn() { |
| //~^ ERROR items with the "custom" ABI can only be declared externally or defined via naked functions |
| //~| ERROR functions with the "custom" ABI cannot be `async` |
| } |
| |
| fn no_promotion_to_fn_trait(f: unsafe extern "custom" fn()) -> impl Fn() { |
| //~^ ERROR expected a `Fn()` closure, found `unsafe extern "custom" fn()` |
| f |
| } |
| |
| pub fn main() { |
| unsafe { |
| assert_eq!(double(21), 42); |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| |
| assert_eq!(unsafe { increment(41) }, 42); |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| |
| assert!(Thing(41).is_even()); |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| |
| assert_eq!(Thing::bitwise_not(42), !42); |
| //~^ ERROR functions with the "custom" ABI cannot be called |
| } |
| } |