Skip to content

Commit d00bc58

Browse files
committed
[IVDescriptors] Don't require nsz/nnan for (min|max)num.
We do not need to require nsz or nnan for FP reductions with minnum and maxnum. NaNs and nsz are handled consistently with the vector versions of minnum and maxnum. vector.reduce.(fmin|fmax) also matches the minnum/maxnum semantics for comparisons. IIUC this was also the conclusion when support for minimum/maximum was added (https://reviews.llvm.org/D151482?id=531021#inline-1481555). Alive2 agrees that maxnum/minnum can be re-ordered (scalar version: https://alive2.llvm.org/ce/z/GVmgBX) and also verifies the vectorized code end-to-end, with a tweak to replace llvm.reduce.fmax with a scalar maxnum, as Alive2 doesn't support llvm.reduce.fmax: https://alive2.llvm.org/ce/z/EwJKeJ . Note that verification requires a higher timeout than available in the online version.
1 parent 237ed0c commit d00bc58

File tree

2 files changed

+10
-5
lines changed

2 files changed

+10
-5
lines changed

llvm/lib/Analysis/IVDescriptors.cpp

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -892,10 +892,13 @@ RecurrenceDescriptor::InstDesc RecurrenceDescriptor::isRecurrenceInstr(
892892
return true;
893893
if (isa<FPMathOperator>(I) && I->hasNoNaNs() && I->hasNoSignedZeros())
894894
return true;
895-
// minimum and maximum intrinsics do not require nsz and nnan flags since
896-
// NaN and signed zeroes are propagated in the intrinsic implementation.
895+
// minimum/minnum and maximum/maxnum intrinsics do not require nsz and nnan
896+
// flags since NaN and signed zeroes are propagated in the intrinsic
897+
// implementation.
897898
return match(I, m_Intrinsic<Intrinsic::minimum>(m_Value(), m_Value())) ||
898-
match(I, m_Intrinsic<Intrinsic::maximum>(m_Value(), m_Value()));
899+
match(I, m_Intrinsic<Intrinsic::maximum>(m_Value(), m_Value())) ||
900+
match(I, m_Intrinsic<Intrinsic::minnum>(m_Value(), m_Value())) ||
901+
match(I, m_Intrinsic<Intrinsic::maxnum>(m_Value(), m_Value()));
899902
};
900903
if (isIntMinMaxRecurrenceKind(Kind) ||
901904
(HasRequiredFMF() && isFPMinMaxRecurrenceKind(Kind)))

llvm/test/Transforms/LoopVectorize/minmax_reduction.ll

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1002,7 +1002,8 @@ for.body: ; preds = %entry, %for.body
10021002
}
10031003

10041004
; CHECK-LABEL: @fmin_intrinsic_nofast(
1005-
; CHECK-NOT: <2 x float> @llvm.minnum.v2f32
1005+
; CHECK: call <2 x float> @llvm.minnum.v2f32
1006+
; CHECK: call float @llvm.vector.reduce.fmin.v2f32
10061007
define float @fmin_intrinsic_nofast(ptr nocapture readonly %x) {
10071008
entry:
10081009
br label %for.body
@@ -1022,7 +1023,8 @@ for.body: ; preds = %entry, %for.body
10221023
}
10231024

10241025
; CHECK-LABEL: @fmax_intrinsic_nofast(
1025-
; CHECK-NOT: <2 x float> @llvm.maxnum.v2f32
1026+
; CHECK: call <2 x float> @llvm.maxnum.v2f32
1027+
; CHECK: call float @llvm.vector.reduce.fmax.v2f32
10261028
define float @fmax_intrinsic_nofast(ptr nocapture readonly %x) {
10271029
entry:
10281030
br label %for.body

0 commit comments

Comments
 (0)