diff options
| author | Matthias Krüger <matthias.krueger@famsik.de> | 2024-07-31 15:36:31 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2024-07-31 15:36:31 +0200 |
| commit | 5c6336328432d37e0ce3d83a4e4a0620a6f13c65 (patch) | |
| tree | 89e4ee9cda742e81ae4e455de85bc97e36622b38 | |
| parent | 22dbf88744649ebd3d1ba951c74739056931f4eb (diff) | |
| parent | fe6478cc539cfe17b4f5fc10f46928c6b16e6ef0 (diff) | |
| download | rust-5c6336328432d37e0ce3d83a4e4a0620a6f13c65.tar.gz rust-5c6336328432d37e0ce3d83a4e4a0620a6f13c65.zip | |
Rollup merge of #128388 - beetrees:f16-f128-slightly-improve-windows-abi, r=tgross35
Match LLVM ABI in `extern "C"` functions for `f128` on Windows As MSVC doesn't support `_Float128`, x86-64 Windows doesn't have a defined ABI for `f128`. Currently, Rust will pass and return `f128` indirectly for `extern "C"` functions. This is inconsistent with LLVM, which passes and returns `f128` in XMM registers, meaning that e.g. the ABI of `extern "C"` compiler builtins won't match. This PR fixes this discrepancy by making the x86-64 Windows `extern "C"` ABI pass `f128` directly through to LLVM, so that Rust will follow whatever LLVM does. This still leaves the difference between LLVM and GCC (https://gcc.gnu.org/bugzilla/show_bug.cgi?id=115054) but this PR is still an improvement as at least Rust is now consistent with it's primary codegen backend and compiler builtins from `compiler-builtins` will now work. I've also fixed the x86-64 Windows `has_reliable_f16` match arm in `std` `build.rs` to refer to the correct target, and added an equivalent match arm to `has_reliable_f128` as the LLVM-GCC ABI difference affects both `f16` and `f128`. Tracking issue: #116909 try-job: x86_64-msvc try-job: x86_64-mingw
| -rw-r--r-- | compiler/rustc_target/src/abi/call/x86_win64.rs | 10 | ||||
| -rw-r--r-- | library/std/build.rs | 4 | ||||
| -rw-r--r-- | tests/assembly/x86_64-windows-float-abi.rs | 39 |
3 files changed, 49 insertions, 4 deletions
diff --git a/compiler/rustc_target/src/abi/call/x86_win64.rs b/compiler/rustc_target/src/abi/call/x86_win64.rs index 90de1a42bc0..4e19460bd28 100644 --- a/compiler/rustc_target/src/abi/call/x86_win64.rs +++ b/compiler/rustc_target/src/abi/call/x86_win64.rs @@ -1,5 +1,5 @@ use crate::abi::call::{ArgAbi, FnAbi, Reg}; -use crate::abi::Abi; +use crate::abi::{Abi, Float, Primitive}; // Win64 ABI: https://docs.microsoft.com/en-us/cpp/build/parameter-passing @@ -18,8 +18,12 @@ pub fn compute_abi_info<Ty>(fn_abi: &mut FnAbi<'_, Ty>) { // FIXME(eddyb) there should be a size cap here // (probably what clang calls "illegal vectors"). } - Abi::Scalar(_) => { - if a.layout.size.bytes() > 8 { + Abi::Scalar(scalar) => { + // Match what LLVM does for `f128` so that `compiler-builtins` builtins match up + // with what LLVM expects. + if a.layout.size.bytes() > 8 + && !matches!(scalar.primitive(), Primitive::Float(Float::F128)) + { a.make_indirect(); } else { a.extend_integer_width_to(32); diff --git a/library/std/build.rs b/library/std/build.rs index c542ba81eed..9b58dd53ba2 100644 --- a/library/std/build.rs +++ b/library/std/build.rs @@ -94,7 +94,7 @@ fn main() { // Unsupported <https://github.com/llvm/llvm-project/issues/94434> ("arm64ec", _) => false, // MinGW ABI bugs <https://gcc.gnu.org/bugzilla/show_bug.cgi?id=115054> - ("x86", "windows") => false, + ("x86_64", "windows") => false, // x86 has ABI bugs that show up with optimizations. This should be partially fixed with // the compiler-builtins update. <https://github.com/rust-lang/rust/issues/123885> ("x86" | "x86_64", _) => false, @@ -122,6 +122,8 @@ fn main() { ("nvptx64", _) => false, // ABI unsupported <https://github.com/llvm/llvm-project/issues/41838> ("sparc", _) => false, + // MinGW ABI bugs <https://gcc.gnu.org/bugzilla/show_bug.cgi?id=115054> + ("x86_64", "windows") => false, // 64-bit Linux is about the only platform to have f128 symbols by default (_, "linux") if target_pointer_width == 64 => true, // Same as for f16, except MacOS is also missing f128 symbols. diff --git a/tests/assembly/x86_64-windows-float-abi.rs b/tests/assembly/x86_64-windows-float-abi.rs new file mode 100644 index 00000000000..1381d492fa5 --- /dev/null +++ b/tests/assembly/x86_64-windows-float-abi.rs @@ -0,0 +1,39 @@ +//@ assembly-output: emit-asm +//@ compile-flags: -O +//@ only-windows +//@ only-x86_64 + +#![feature(f16, f128)] +#![crate_type = "lib"] + +// CHECK-LABEL: second_f16 +// CHECK: movaps %xmm1, %xmm0 +// CHECK-NEXT: retq +#[no_mangle] +pub extern "C" fn second_f16(_: f16, x: f16) -> f16 { + x +} + +// CHECK-LABEL: second_f32 +// CHECK: movaps %xmm1, %xmm0 +// CHECK-NEXT: retq +#[no_mangle] +pub extern "C" fn second_f32(_: f32, x: f32) -> f32 { + x +} + +// CHECK-LABEL: second_f64 +// CHECK: movaps %xmm1, %xmm0 +// CHECK-NEXT: retq +#[no_mangle] +pub extern "C" fn second_f64(_: f64, x: f64) -> f64 { + x +} + +// CHECK-LABEL: second_f128 +// CHECK: movaps %xmm1, %xmm0 +// CHECK-NEXT: retq +#[no_mangle] +pub extern "C" fn second_f128(_: f128, x: f128) -> f128 { + x +} |
