Skip to content

Commit 81a4466

Browse files
committed
simd_fmin/fmax: make semantics and name consistent with scalar intrinsics
1 parent a3903b1 commit 81a4466

18 files changed

Lines changed: 95 additions & 79 deletions

File tree

compiler/rustc_codegen_cranelift/example/float-minmax-pass.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -33,24 +33,24 @@ fn main() {
3333
let n = f32x4([nan, nan, nan, nan]);
3434

3535
unsafe {
36-
let min0 = simd_fmin(x, y);
37-
let min1 = simd_fmin(y, x);
36+
let min0 = simd_minimum_number_nsz(x, y);
37+
let min1 = simd_minimum_number_nsz(y, x);
3838
assert_eq!(min0.into_array(), min1.into_array());
3939
let e = f32x4([1.0, 1.0, 3.0, 3.0]);
4040
assert_eq!(min0.into_array(), e.into_array());
41-
let minn = simd_fmin(x, n);
41+
let minn = simd_minimum_number_nsz(x, n);
4242
assert_eq!(minn.into_array(), x.into_array());
43-
let minn = simd_fmin(y, n);
43+
let minn = simd_minimum_number_nsz(y, n);
4444
assert_eq!(minn.into_array(), y.into_array());
4545

46-
let max0 = simd_fmax(x, y);
47-
let max1 = simd_fmax(y, x);
46+
let max0 = simd_maximum_number_nsz(x, y);
47+
let max1 = simd_maximum_number_nsz(y, x);
4848
assert_eq!(max0.into_array(), max1.into_array());
4949
let e = f32x4([2.0, 2.0, 4.0, 4.0]);
5050
assert_eq!(max0.into_array(), e.into_array());
51-
let maxn = simd_fmax(x, n);
51+
let maxn = simd_maximum_number_nsz(x, n);
5252
assert_eq!(maxn.into_array(), x.into_array());
53-
let maxn = simd_fmax(y, n);
53+
let maxn = simd_maximum_number_nsz(y, n);
5454
assert_eq!(maxn.into_array(), y.into_array());
5555
}
5656
}

compiler/rustc_codegen_cranelift/src/intrinsics/simd.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -493,7 +493,7 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>(
493493
}
494494
}
495495

496-
sym::simd_fmin | sym::simd_fmax => {
496+
sym::simd_minimum_number_nsz | sym::simd_maximum_number_nsz => {
497497
intrinsic_args!(fx, args => (x, y); intrinsic);
498498

499499
if !x.layout().ty.is_simd() {
@@ -508,8 +508,12 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>(
508508
_ => unreachable!("{:?}", lane_ty),
509509
}
510510
match intrinsic {
511-
sym::simd_fmin => crate::num::codegen_float_min(fx, x_lane, y_lane),
512-
sym::simd_fmax => crate::num::codegen_float_max(fx, x_lane, y_lane),
511+
sym::simd_minimum_number_nsz => {
512+
crate::num::codegen_float_min(fx, x_lane, y_lane)
513+
}
514+
sym::simd_maximum_number_nsz => {
515+
crate::num::codegen_float_max(fx, x_lane, y_lane)
516+
}
513517
_ => unreachable!(),
514518
}
515519
});

compiler/rustc_codegen_cranelift/src/num.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -500,8 +500,8 @@ fn codegen_ptr_binop<'tcx>(
500500

501501
// In Rust floating point min and max don't propagate NaN (not even SNaN). In Cranelift they do
502502
// however. For this reason it is necessary to use `a.is_nan() ? b : (a >= b ? b : a)` for
503-
// `minnumf*` and `a.is_nan() ? b : (a <= b ? b : a)` for `maxnumf*`. NaN checks are done by
504-
// comparing a float against itself. Only in case of NaN is it not equal to itself.
503+
// `minimum_number_nsz` and `a.is_nan() ? b : (a <= b ? b : a)` for `maximum_number_nsz`. NaN checks
504+
// are done by comparing a float against itself. Only in case of NaN is it not equal to itself.
505505
pub(crate) fn codegen_float_min(fx: &mut FunctionCx<'_, '_, '_>, a: Value, b: Value) -> Value {
506506
// FIXME(bytecodealliance/wasmtime#8312): Replace with Cranelift `fcmp` once
507507
// `f16`/`f128` backend lowerings have been added to Cranelift.

compiler/rustc_codegen_gcc/src/builder.rs

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2278,6 +2278,8 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
22782278
})
22792279
}
22802280

2281+
/// Emits a SIMD min/max operation for floats. The semantics for each lane are: if one
2282+
/// side is NaN (QNaN or SNaN), the other side is returned.
22812283
fn vector_extremum(
22822284
&mut self,
22832285
a: RValue<'gcc>,
@@ -2286,8 +2288,9 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
22862288
) -> RValue<'gcc> {
22872289
let vector_type = a.get_type();
22882290

2289-
// mask out the NaNs in b and replace them with the corresponding lane in a, so when a and
2290-
// b get compared & spliced together, we get the numeric values instead of NaNs.
2291+
// Mask out the NaNs (both QNaN and SNaN) in b and replace them with the corresponding lane
2292+
// in a, so when a and b get compared & spliced together, we get the numeric values instead
2293+
// of NaNs.
22912294
let b_nan_mask = self.context.new_comparison(self.location, ComparisonOp::NotEquals, b, b);
22922295
let mask_type = b_nan_mask.get_type();
22932296
let b_nan_mask_inverted =
@@ -2309,7 +2312,7 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
23092312
self.context.new_bitcast(self.location, res, vector_type)
23102313
}
23112314

2312-
pub fn vector_fmin(&mut self, a: RValue<'gcc>, b: RValue<'gcc>) -> RValue<'gcc> {
2315+
pub fn vector_minimum_number_nsz(&mut self, a: RValue<'gcc>, b: RValue<'gcc>) -> RValue<'gcc> {
23132316
self.vector_extremum(a, b, ExtremumOperation::Min)
23142317
}
23152318

@@ -2341,7 +2344,7 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
23412344
unimplemented!();
23422345
}
23432346

2344-
pub fn vector_fmax(&mut self, a: RValue<'gcc>, b: RValue<'gcc>) -> RValue<'gcc> {
2347+
pub fn vector_maximum_number_nsz(&mut self, a: RValue<'gcc>, b: RValue<'gcc>) -> RValue<'gcc> {
23452348
self.vector_extremum(a, b, ExtremumOperation::Max)
23462349
}
23472350

compiler/rustc_codegen_gcc/src/intrinsic/simd.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1222,8 +1222,8 @@ pub fn generic_simd_intrinsic<'a, 'gcc, 'tcx>(
12221222
simd_and: Uint, Int => and;
12231223
simd_or: Uint, Int => or; // FIXME(antoyo): calling `or` might not work on vectors.
12241224
simd_xor: Uint, Int => xor;
1225-
simd_fmin: Float => vector_fmin;
1226-
simd_fmax: Float => vector_fmax;
1225+
simd_minimum_number_nsz: Float => vector_minimum_number_nsz;
1226+
simd_maximum_number_nsz: Float => vector_maximum_number_nsz;
12271227
}
12281228

12291229
macro_rules! arith_unary {

compiler/rustc_codegen_llvm/src/builder.rs

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1605,12 +1605,16 @@ impl<'a, 'll, 'tcx> Builder<'a, 'll, 'tcx> {
16051605
*self = Self::build(self.cx, next_bb);
16061606
}
16071607

1608-
pub(crate) fn minnum(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
1609-
self.call_intrinsic("llvm.minnum", &[self.val_ty(lhs)], &[lhs, rhs])
1608+
pub(crate) fn minimum_number_nsz(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
1609+
let call = self.call_intrinsic("llvm.minimumnum", &[self.val_ty(lhs)], &[lhs, rhs]);
1610+
unsafe { llvm::LLVMRustSetNoSignedZeros(call) };
1611+
call
16101612
}
16111613

1612-
pub(crate) fn maxnum(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
1613-
self.call_intrinsic("llvm.maxnum", &[self.val_ty(lhs)], &[lhs, rhs])
1614+
pub(crate) fn maximum_number_nsz(&mut self, lhs: &'ll Value, rhs: &'ll Value) -> &'ll Value {
1615+
let call = self.call_intrinsic("llvm.maximumnum", &[self.val_ty(lhs)], &[lhs, rhs]);
1616+
unsafe { llvm::LLVMRustSetNoSignedZeros(call) };
1617+
call
16141618
}
16151619

16161620
pub(crate) fn insert_element(

compiler/rustc_codegen_llvm/src/intrinsic.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2770,8 +2770,8 @@ fn generic_simd_intrinsic<'ll, 'tcx>(
27702770
simd_and: Uint, Int => and;
27712771
simd_or: Uint, Int => or;
27722772
simd_xor: Uint, Int => xor;
2773-
simd_fmax: Float => maxnum;
2774-
simd_fmin: Float => minnum;
2773+
simd_maximum_number_nsz: Float => maximum_number_nsz;
2774+
simd_minimum_number_nsz: Float => minimum_number_nsz;
27752775

27762776
}
27772777
macro_rules! arith_unary {

compiler/rustc_const_eval/src/interpret/intrinsics/simd.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -174,8 +174,8 @@ impl<'tcx, M: Machine<'tcx>> InterpCx<'tcx, M> {
174174
| sym::simd_le
175175
| sym::simd_gt
176176
| sym::simd_ge
177-
| sym::simd_fmax
178-
| sym::simd_fmin
177+
| sym::simd_maximum_number_nsz
178+
| sym::simd_minimum_number_nsz
179179
| sym::simd_saturating_add
180180
| sym::simd_saturating_sub
181181
| sym::simd_arith_offset => {
@@ -211,8 +211,8 @@ impl<'tcx, M: Machine<'tcx>> InterpCx<'tcx, M> {
211211
sym::simd_le => Op::MirOp(BinOp::Le),
212212
sym::simd_gt => Op::MirOp(BinOp::Gt),
213213
sym::simd_ge => Op::MirOp(BinOp::Ge),
214-
sym::simd_fmax => Op::FMinMax(MinMax::MaximumNumberNsz),
215-
sym::simd_fmin => Op::FMinMax(MinMax::MinimumNumberNsz),
214+
sym::simd_maximum_number_nsz => Op::FMinMax(MinMax::MaximumNumberNsz),
215+
sym::simd_minimum_number_nsz => Op::FMinMax(MinMax::MinimumNumberNsz),
216216
sym::simd_saturating_add => Op::SaturatingOp(BinOp::Add),
217217
sym::simd_saturating_sub => Op::SaturatingOp(BinOp::Sub),
218218
sym::simd_arith_offset => Op::WrappingOffset,

compiler/rustc_hir_analysis/src/check/intrinsic.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -726,8 +726,8 @@ pub(crate) fn check_intrinsic_type(
726726
| sym::simd_and
727727
| sym::simd_or
728728
| sym::simd_xor
729-
| sym::simd_fmin
730-
| sym::simd_fmax
729+
| sym::simd_minimum_number_nsz
730+
| sym::simd_maximum_number_nsz
731731
| sym::simd_saturating_add
732732
| sym::simd_saturating_sub
733733
| sym::simd_carryless_mul => (1, 0, vec![param(0), param(0)], param(0)),

compiler/rustc_span/src/symbol.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1850,8 +1850,8 @@ symbols! {
18501850
simd_flog10,
18511851
simd_floor,
18521852
simd_fma,
1853-
simd_fmax,
1854-
simd_fmin,
1853+
simd_maximum_number_nsz,
1854+
simd_minimum_number_nsz,
18551855
simd_fsin,
18561856
simd_fsqrt,
18571857
simd_funnel_shl,

0 commit comments

Comments
 (0)