Skip to content

Commit 2b792fe

Browse files
committed
[InstCombine] Fold its select user into select
Fold select if the user of its select user indicates the condition Fix #83225
1 parent 60e7ae3 commit 2b792fe

File tree

2 files changed

+68
-0
lines changed

2 files changed

+68
-0
lines changed

llvm/lib/Transforms/InstCombine/InstCombineSelect.cpp

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -500,6 +500,42 @@ static bool isSelect01(const APInt &C1I, const APInt &C2I) {
500500
return C1I.isOne() || C1I.isAllOnes() || C2I.isOne() || C2I.isAllOnes();
501501
}
502502

503+
/// Try to simplify a select instruction when the user of its select user
504+
/// indicates the condition.
505+
static bool simplifySeqSelectWithSameCond(SelectInst &SI,
506+
const SimplifyQuery &SQ,
507+
InstCombinerImpl &IC) {
508+
Value *CondVal = SI.getCondition();
509+
Type *CondType = CondVal->getType();
510+
511+
SelectInst *SINext = &SI;
512+
Type *SelType = SINext->getType();
513+
Value *FalseVal = SINext->getFalseValue();
514+
Value *CondNext;
515+
Value *FalseNext;
516+
while (match(FalseVal,
517+
m_Select(m_Value(CondNext), m_Value(), m_Value(FalseNext)))) {
518+
// If the type of select is not an integer type or if the condition and
519+
// the selection type are not both scalar nor both vector types, there is no
520+
// point in attempting to match these patterns.
521+
if (!isa<Constant>(CondVal) && SelType->isIntOrIntVectorTy() &&
522+
CondType->isVectorTy() == SelType->isVectorTy())
523+
if (CondNext == CondVal) {
524+
if (Value *S = simplifyWithOpReplaced(
525+
FalseVal, CondVal, ConstantInt::getFalse(CondType), SQ,
526+
/* AllowRefinement */ true)) {
527+
IC.replaceOperand(*SINext, 2, S);
528+
return true;
529+
}
530+
}
531+
532+
SINext = cast<SelectInst>(FalseVal);
533+
FalseVal = SINext->getFalseValue();
534+
}
535+
536+
return false;
537+
}
538+
503539
/// Try to fold the select into one of the operands to allow further
504540
/// optimization.
505541
Instruction *InstCombinerImpl::foldSelectIntoOp(SelectInst &SI, Value *TrueVal,
@@ -557,6 +593,9 @@ Instruction *InstCombinerImpl::foldSelectIntoOp(SelectInst &SI, Value *TrueVal,
557593
if (Instruction *R = TryFoldSelectIntoOp(SI, FalseVal, TrueVal, true))
558594
return R;
559595

596+
if (simplifySeqSelectWithSameCond(SI, SQ, *this))
597+
return &SI;
598+
560599
return nullptr;
561600
}
562601

llvm/test/Transforms/InstCombine/select.ll

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3672,3 +3672,32 @@ define i32 @src_select_xxory_eq0_xorxy_y(i32 %x, i32 %y) {
36723672
%cond = select i1 %xor0, i32 %xor, i32 %y
36733673
ret i32 %cond
36743674
}
3675+
3676+
define i32 @sequence_select_with_same_cond (i1 %c1, i1 %c2){
3677+
; CHECK-LABEL: @sequence_select_with_same_cond(
3678+
; CHECK-NEXT: [[S2:%.*]] = select i1 [[C2:%.*]], i32 666, i32 45
3679+
; CHECK-NEXT: [[S3:%.*]] = select i1 [[C1:%.*]], i32 789, i32 [[S2]]
3680+
; CHECK-NEXT: ret i32 [[S3]]
3681+
;
3682+
%s1 = select i1 %c1, i32 23, i32 45
3683+
%s2 = select i1 %c2, i32 666, i32 %s1
3684+
%s3 = select i1 %c1, i32 789, i32 %s2
3685+
ret i32 %s3
3686+
}
3687+
3688+
declare void @use32(i32)
3689+
3690+
define i32 @sequence_select_with_same_cond_extra_use (i1 %c1, i1 %c2){
3691+
; CHECK-LABEL: @sequence_select_with_same_cond_extra_use(
3692+
; CHECK-NEXT: [[S1:%.*]] = select i1 [[C1:%.*]], i32 23, i32 45
3693+
; CHECK-NEXT: call void @use32(i32 [[S1]])
3694+
; CHECK-NEXT: [[S2:%.*]] = select i1 [[C2:%.*]], i32 666, i32 45
3695+
; CHECK-NEXT: [[S3:%.*]] = select i1 [[C1]], i32 789, i32 [[S2]]
3696+
; CHECK-NEXT: ret i32 [[S3]]
3697+
;
3698+
%s1 = select i1 %c1, i32 23, i32 45
3699+
call void @use32(i32 %s1)
3700+
%s2 = select i1 %c2, i32 666, i32 %s1
3701+
%s3 = select i1 %c1, i32 789, i32 %s2
3702+
ret i32 %s3
3703+
}

0 commit comments

Comments
 (0)