diff --git a/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp b/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp --- a/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp @@ -2277,7 +2277,8 @@ // Match select ?, TC, FC where the constants are equal but negated. // TODO: Generalize to handle a negated variable operand? const APFloat *TC, *FC; - if (!match(TVal, m_APFloat(TC)) || !match(FVal, m_APFloat(FC)) || + if (!match(TVal, m_APFloatAllowUndef(TC)) || + !match(FVal, m_APFloatAllowUndef(FC)) || !abs(*TC).bitwiseIsEqual(abs(*FC))) return nullptr; diff --git a/llvm/test/Transforms/InstCombine/select.ll b/llvm/test/Transforms/InstCombine/select.ll --- a/llvm/test/Transforms/InstCombine/select.ll +++ b/llvm/test/Transforms/InstCombine/select.ll @@ -1689,13 +1689,10 @@ ret float %r } -; TODO: Allow undefs when matching vectors. - define <2 x float> @copysign4(<2 x float> %x) { ; CHECK-LABEL: @copysign4( -; CHECK-NEXT: [[I:%.*]] = bitcast <2 x float> [[X:%.*]] to <2 x i32> -; CHECK-NEXT: [[ISNEG:%.*]] = icmp slt <2 x i32> [[I]], zeroinitializer -; CHECK-NEXT: [[R:%.*]] = select nnan arcp <2 x i1> [[ISNEG]], <2 x float> , <2 x float> +; CHECK-NEXT: [[TMP1:%.*]] = fneg <2 x float> [[X:%.*]] +; CHECK-NEXT: [[R:%.*]] = call <2 x float> @llvm.copysign.v2f32(<2 x float> , <2 x float> [[TMP1]]) ; CHECK-NEXT: ret <2 x float> [[R]] ; %i = bitcast <2 x float> %x to <2 x i32>