Skip to content

Commit 3b8bc83

Browse files
committed
Revert "[SimpleLoopUnswitch] unswitch selects"
Revert "Don't loop unswitch vector selects" Breaks msan. Details in D138526. This reverts commit bf08973. This reverts commit e479ed9.
1 parent 76fb334 commit 3b8bc83

File tree

4 files changed

+80
-516
lines changed

4 files changed

+80
-516
lines changed

llvm/lib/Transforms/Scalar/SimpleLoopUnswitch.cpp

Lines changed: 15 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,6 @@
1919
#include "llvm/Analysis/BlockFrequencyInfo.h"
2020
#include "llvm/Analysis/CFG.h"
2121
#include "llvm/Analysis/CodeMetrics.h"
22-
#include "llvm/Analysis/DomTreeUpdater.h"
2322
#include "llvm/Analysis/GuardUtils.h"
2423
#include "llvm/Analysis/LoopAnalysisManager.h"
2524
#include "llvm/Analysis/LoopInfo.h"
@@ -75,7 +74,6 @@ using namespace llvm::PatternMatch;
7574

7675
STATISTIC(NumBranches, "Number of branches unswitched");
7776
STATISTIC(NumSwitches, "Number of switches unswitched");
78-
STATISTIC(NumSelects, "Number of selects turned into branches for unswitching");
7977
STATISTIC(NumGuards, "Number of guards turned into branches for unswitching");
8078
STATISTIC(NumTrivial, "Number of unswitches that are trivial");
8179
STATISTIC(
@@ -2644,61 +2642,6 @@ static InstructionCost computeDomSubtreeCost(
26442642
return Cost;
26452643
}
26462644

2647-
/// Turns a select instruction into implicit control flow branch,
2648-
/// making the following replacement:
2649-
///
2650-
/// head:
2651-
/// --code before select--
2652-
/// select %cond, %trueval, %falseval
2653-
/// --code after select--
2654-
///
2655-
/// into
2656-
///
2657-
/// head:
2658-
/// --code before select--
2659-
/// br i1 %cond, label %then, label %tail
2660-
///
2661-
/// then:
2662-
/// br %tail
2663-
///
2664-
/// tail:
2665-
/// phi [ %trueval, %then ], [ %falseval, %head]
2666-
/// unreachable
2667-
///
2668-
/// It also makes all relevant DT and LI updates, so that all structures are in
2669-
/// valid state after this transform.
2670-
static BranchInst *turnSelectIntoBranch(SelectInst *SI, DominatorTree &DT,
2671-
LoopInfo &LI, MemorySSAUpdater *MSSAU,
2672-
AssumptionCache *AC) {
2673-
LLVM_DEBUG(dbgs() << "Turning " << *SI << " into a branch.\n");
2674-
BasicBlock *HeadBB = SI->getParent();
2675-
2676-
Value *Cond = SI->getCondition();
2677-
if (!isGuaranteedNotToBeUndefOrPoison(Cond, AC, SI, &DT))
2678-
Cond = new FreezeInst(Cond, Cond->getName() + ".fr", SI);
2679-
DomTreeUpdater DTU =
2680-
DomTreeUpdater(DT, DomTreeUpdater::UpdateStrategy::Eager);
2681-
SplitBlockAndInsertIfThen(SI->getCondition(), SI, false,
2682-
SI->getMetadata(LLVMContext::MD_prof), &DTU, &LI);
2683-
auto *CondBr = cast<BranchInst>(HeadBB->getTerminator());
2684-
BasicBlock *ThenBB = CondBr->getSuccessor(0),
2685-
*TailBB = CondBr->getSuccessor(1);
2686-
if (MSSAU)
2687-
MSSAU->moveAllAfterSpliceBlocks(HeadBB, TailBB, SI);
2688-
2689-
PHINode *Phi = PHINode::Create(SI->getType(), 2, "unswitched.select", SI);
2690-
Phi->addIncoming(SI->getTrueValue(), ThenBB);
2691-
Phi->addIncoming(SI->getFalseValue(), HeadBB);
2692-
SI->replaceAllUsesWith(Phi);
2693-
SI->eraseFromParent();
2694-
2695-
if (MSSAU && VerifyMemorySSA)
2696-
MSSAU->getMemorySSA()->verifyMemorySSA();
2697-
2698-
++NumSelects;
2699-
return CondBr;
2700-
}
2701-
27022645
/// Turns a llvm.experimental.guard intrinsic into implicit control flow branch,
27032646
/// making the following replacement:
27042647
///
@@ -2806,10 +2749,9 @@ static int CalculateUnswitchCostMultiplier(
28062749
const BasicBlock *CondBlock = TI.getParent();
28072750
if (DT.dominates(CondBlock, Latch) &&
28082751
(isGuard(&TI) ||
2809-
(TI.isTerminator() &&
2810-
llvm::count_if(successors(&TI), [&L](const BasicBlock *SuccBB) {
2811-
return L.contains(SuccBB);
2812-
}) <= 1))) {
2752+
llvm::count_if(successors(&TI), [&L](const BasicBlock *SuccBB) {
2753+
return L.contains(SuccBB);
2754+
}) <= 1)) {
28132755
NumCostMultiplierSkipped++;
28142756
return 1;
28152757
}
@@ -2818,17 +2760,12 @@ static int CalculateUnswitchCostMultiplier(
28182760
int SiblingsCount = (ParentL ? ParentL->getSubLoopsVector().size()
28192761
: std::distance(LI.begin(), LI.end()));
28202762
// Count amount of clones that all the candidates might cause during
2821-
// unswitching. Branch/guard/select counts as 1, switch counts as log2 of its
2822-
// cases.
2763+
// unswitching. Branch/guard counts as 1, switch counts as log2 of its cases.
28232764
int UnswitchedClones = 0;
28242765
for (const auto &Candidate : UnswitchCandidates) {
28252766
const Instruction *CI = Candidate.TI;
28262767
const BasicBlock *CondBlock = CI->getParent();
28272768
bool SkipExitingSuccessors = DT.dominates(CondBlock, Latch);
2828-
if (isa<SelectInst>(CI)) {
2829-
UnswitchedClones++;
2830-
continue;
2831-
}
28322769
if (isGuard(CI)) {
28332770
if (!SkipExitingSuccessors)
28342771
UnswitchedClones++;
@@ -2891,20 +2828,15 @@ static bool collectUnswitchCandidates(
28912828
if (LI.getLoopFor(BB) != &L)
28922829
continue;
28932830

2894-
for (auto &I : *BB) {
2895-
if (auto *SI = dyn_cast<SelectInst>(&I)) {
2896-
auto *Cond = SI->getCondition();
2897-
// restrict to simple boolean selects
2898-
if (!isa<Constant>(Cond) && L.isLoopInvariant(Cond) && Cond->getType()->isIntegerTy(1))
2899-
UnswitchCandidates.push_back({&I, {Cond}});
2900-
} else if (CollectGuards && isGuard(&I)) {
2901-
auto *Cond =
2902-
skipTrivialSelect(cast<IntrinsicInst>(&I)->getArgOperand(0));
2903-
// TODO: Support AND, OR conditions and partial unswitching.
2904-
if (!isa<Constant>(Cond) && L.isLoopInvariant(Cond))
2905-
UnswitchCandidates.push_back({&I, {Cond}});
2906-
}
2907-
}
2831+
if (CollectGuards)
2832+
for (auto &I : *BB)
2833+
if (isGuard(&I)) {
2834+
auto *Cond =
2835+
skipTrivialSelect(cast<IntrinsicInst>(&I)->getArgOperand(0));
2836+
// TODO: Support AND, OR conditions and partial unswitching.
2837+
if (!isa<Constant>(Cond) && L.isLoopInvariant(Cond))
2838+
UnswitchCandidates.push_back({&I, {Cond}});
2839+
}
29082840

29092841
if (auto *SI = dyn_cast<SwitchInst>(BB->getTerminator())) {
29102842
// We can only consider fully loop-invariant switch conditions as we need
@@ -3406,8 +3338,7 @@ static NonTrivialUnswitchCandidate findBestNonTrivialUnswitchCandidate(
34063338
// loop. This is computing the new cost of unswitching a condition.
34073339
// Note that guards always have 2 unique successors that are implicit and
34083340
// will be materialized if we decide to unswitch it.
3409-
int SuccessorsCount =
3410-
isGuard(&TI) || isa<SelectInst>(TI) ? 2 : Visited.size();
3341+
int SuccessorsCount = isGuard(&TI) ? 2 : Visited.size();
34113342
assert(SuccessorsCount > 1 &&
34123343
"Cannot unswitch a condition without multiple distinct successors!");
34133344
return (LoopCost - Cost) * (SuccessorsCount - 1);
@@ -3494,9 +3425,7 @@ static bool unswitchBestCondition(
34943425
PartialIVInfo.InstToDuplicate.clear();
34953426

34963427
// If the best candidate is a guard, turn it into a branch.
3497-
if (auto *SI = dyn_cast<SelectInst>(Best.TI))
3498-
Best.TI = turnSelectIntoBranch(SI, DT, LI, MSSAU, &AC);
3499-
else if (isGuard(Best.TI))
3428+
if (isGuard(Best.TI))
35003429
Best.TI =
35013430
turnGuardIntoBranch(cast<IntrinsicInst>(Best.TI), L, DT, LI, MSSAU);
35023431

llvm/test/Transforms/SimpleLoopUnswitch/nontrivial-unswitch-freeze.ll

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2332,26 +2332,21 @@ exit:
23322332
define i32 @test_partial_unswitch_all_conds_guaranteed_non_poison(i1 noundef %c.1, i1 noundef %c.2) {
23332333
; CHECK-LABEL: @test_partial_unswitch_all_conds_guaranteed_non_poison(
23342334
; CHECK-NEXT: entry:
2335-
; CHECK-NEXT: br i1 [[C_1:%.*]], label [[ENTRY_SPLIT_US:%.*]], label [[ENTRY_SPLIT:%.*]]
2335+
; CHECK-NEXT: [[TMP0:%.*]] = and i1 [[C_1:%.*]], [[C_2:%.*]]
2336+
; CHECK-NEXT: br i1 [[TMP0]], label [[ENTRY_SPLIT:%.*]], label [[ENTRY_SPLIT_US:%.*]]
23362337
; CHECK: entry.split.us:
23372338
; CHECK-NEXT: br label [[LOOP_US:%.*]]
23382339
; CHECK: loop.us:
2339-
; CHECK-NEXT: [[TMP0:%.*]] = call i32 @a()
2340-
; CHECK-NEXT: br label [[TMP1:%.*]]
2341-
; CHECK: 1:
2342-
; CHECK-NEXT: br label [[TMP2:%.*]]
2343-
; CHECK: 2:
2344-
; CHECK-NEXT: [[UNSWITCHED_SELECT_US:%.*]] = phi i1 [ [[C_2:%.*]], [[TMP1]] ]
2345-
; CHECK-NEXT: br i1 [[UNSWITCHED_SELECT_US]], label [[LOOP_US]], label [[EXIT_SPLIT_US:%.*]]
2340+
; CHECK-NEXT: [[TMP1:%.*]] = call i32 @a()
2341+
; CHECK-NEXT: br label [[EXIT_SPLIT_US:%.*]]
23462342
; CHECK: exit.split.us:
23472343
; CHECK-NEXT: br label [[EXIT:%.*]]
23482344
; CHECK: entry.split:
23492345
; CHECK-NEXT: br label [[LOOP:%.*]]
23502346
; CHECK: loop:
2351-
; CHECK-NEXT: [[TMP3:%.*]] = call i32 @a()
2352-
; CHECK-NEXT: br label [[TMP4:%.*]]
2353-
; CHECK: 4:
2354-
; CHECK-NEXT: br i1 false, label [[LOOP]], label [[EXIT_SPLIT:%.*]]
2347+
; CHECK-NEXT: [[TMP2:%.*]] = call i32 @a()
2348+
; CHECK-NEXT: [[SEL:%.*]] = select i1 true, i1 true, i1 false
2349+
; CHECK-NEXT: br i1 [[SEL]], label [[LOOP]], label [[EXIT_SPLIT:%.*]]
23552350
; CHECK: exit.split:
23562351
; CHECK-NEXT: br label [[EXIT]]
23572352
; CHECK: exit:

0 commit comments

Comments
 (0)