1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-11-22 02:33:06 +01:00

[NewPM][SimpleLoopUnswitch] Add option to not trivially unswitch

To help with debugging non-trivial unswitching issues.

Don't care about the legacy pass, nobody is using it.

If a pass's string params are empty (e.g. "simple-loop-unswitch"), don't
default to the empty constructor for the pass params. We should still
let the parser take care of it in case the parser has its own defaults.

Reviewed By: asbirlea

Differential Revision: https://reviews.llvm.org/D105933
This commit is contained in:
Arthur Eubanks 2021-07-13 12:50:34 -07:00
parent 74be1319be
commit 78dcef41e1
6 changed files with 45 additions and 15 deletions

View File

@ -61,9 +61,11 @@ namespace llvm {
/// not currently implement that in any mode.
class SimpleLoopUnswitchPass : public PassInfoMixin<SimpleLoopUnswitchPass> {
bool NonTrivial;
bool Trivial;
public:
SimpleLoopUnswitchPass(bool NonTrivial = false) : NonTrivial(NonTrivial) {}
SimpleLoopUnswitchPass(bool NonTrivial = false, bool Trivial = true)
: NonTrivial(NonTrivial), Trivial(Trivial) {}
PreservedAnalyses run(Loop &L, LoopAnalysisManager &AM,
LoopStandardAnalysisResults &AR, LPMUpdater &U);

View File

@ -2091,9 +2091,8 @@ auto parsePassParameters(ParametersParseCallableT &&Parser, StringRef Name,
assert(false &&
"unable to strip pass name from parametrized pass specification");
}
if (Params.empty())
return ParametersT{};
if (!Params.consume_front("<") || !Params.consume_back(">")) {
if (!Params.empty() &&
(!Params.consume_front("<") || !Params.consume_back(">"))) {
assert(false && "invalid format for parametrized pass name");
}
@ -2234,15 +2233,17 @@ Expected<LoopVectorizeOptions> parseLoopVectorizeOptions(StringRef Params) {
return Opts;
}
Expected<bool> parseLoopUnswitchOptions(StringRef Params) {
bool Result = false;
Expected<std::pair<bool, bool>> parseLoopUnswitchOptions(StringRef Params) {
std::pair<bool, bool> Result = {false, true};
while (!Params.empty()) {
StringRef ParamName;
std::tie(ParamName, Params) = Params.split(';');
bool Enable = !ParamName.consume_front("no-");
if (ParamName == "nontrivial") {
Result = Enable;
Result.first = Enable;
} else if (ParamName == "trivial") {
Result.second = Enable;
} else {
return make_error<StringError>(
formatv("invalid LoopUnswitch pass parameter '{0}' ", ParamName)

View File

@ -445,9 +445,9 @@ LOOP_PASS("loop-versioning-licm", LoopVersioningLICMPass())
#endif
LOOP_PASS_WITH_PARAMS("simple-loop-unswitch",
"SimpleLoopUnswitchPass",
[](bool NonTrivial) {
return SimpleLoopUnswitchPass(NonTrivial);
[](std::pair<bool, bool> Params) {
return SimpleLoopUnswitchPass(Params.first, Params.second);
},
parseLoopUnswitchOptions,
"no-nontrivial;nontrivial")
"nontrivial;no-nontrivial;trivial;no-trivial")
#undef LOOP_PASS_WITH_PARAMS

View File

@ -2984,7 +2984,8 @@ static bool unswitchBestCondition(
/// done.
static bool
unswitchLoop(Loop &L, DominatorTree &DT, LoopInfo &LI, AssumptionCache &AC,
AAResults &AA, TargetTransformInfo &TTI, bool NonTrivial,
AAResults &AA, TargetTransformInfo &TTI, bool Trivial,
bool NonTrivial,
function_ref<void(bool, bool, ArrayRef<Loop *>)> UnswitchCB,
ScalarEvolution *SE, MemorySSAUpdater *MSSAU) {
assert(L.isRecursivelyLCSSAForm(DT, LI) &&
@ -2995,7 +2996,7 @@ unswitchLoop(Loop &L, DominatorTree &DT, LoopInfo &LI, AssumptionCache &AC,
return false;
// Try trivial unswitch first before loop over other basic blocks in the loop.
if (unswitchAllTrivialConditions(L, DT, LI, SE, MSSAU)) {
if (Trivial && unswitchAllTrivialConditions(L, DT, LI, SE, MSSAU)) {
// If we unswitched successfully we will want to clean up the loop before
// processing it further so just mark it as unswitched and return.
UnswitchCB(/*CurrentLoopValid*/ true, false, {});
@ -3087,7 +3088,7 @@ PreservedAnalyses SimpleLoopUnswitchPass::run(Loop &L, LoopAnalysisManager &AM,
if (VerifyMemorySSA)
AR.MSSA->verifyMemorySSA();
}
if (!unswitchLoop(L, AR.DT, AR.LI, AR.AC, AR.AA, AR.TTI, NonTrivial,
if (!unswitchLoop(L, AR.DT, AR.LI, AR.AC, AR.AA, AR.TTI, Trivial, NonTrivial,
UnswitchCB, &AR.SE,
MSSAU.hasValue() ? MSSAU.getPointer() : nullptr))
return PreservedAnalyses::all();
@ -3181,7 +3182,7 @@ bool SimpleLoopUnswitchLegacyPass::runOnLoop(Loop *L, LPPassManager &LPM) {
MSSA->verifyMemorySSA();
bool Changed =
unswitchLoop(*L, DT, LI, AC, AA, TTI, NonTrivial, UnswitchCB, SE,
unswitchLoop(*L, DT, LI, AC, AA, TTI, true, NonTrivial, UnswitchCB, SE,
MSSAU.hasValue() ? MSSAU.getPointer() : nullptr);
if (MSSA && VerifyMemorySSA)

View File

@ -21,6 +21,6 @@
; CHECK: Loop passes:
; CHECK: no-op-loop
; CHECK: Loop passes with params:
; CHECK: simple-loop-unswitch<no-nontrivial;nontrivial>
; CHECK: simple-loop-unswitch<nontrivial;no-nontrivial;trivial;no-trivial>
; CHECK: Loop analyses:
; CHECK: no-op-loop

View File

@ -0,0 +1,26 @@
; RUN: opt -passes='simple-loop-unswitch<no-trivial>' -S < %s | FileCheck %s --check-prefix=NOTRIVIAL
; RUN: opt -passes='simple-loop-unswitch' -S < %s | FileCheck %s --check-prefix=TRIVIAL
; RUN: opt -passes='simple-loop-unswitch<trivial>' -S < %s | FileCheck %s --check-prefix=TRIVIAL
declare void @some_func() noreturn
; NOTRIVIAL-NOT: split
; TRIVIAL: split
define i32 @test1(i32* %var, i1 %cond1, i1 %cond2) {
entry:
br label %loop_begin
loop_begin:
br i1 %cond1, label %continue, label %loop_exit ; first trivial condition
continue:
%var_val = load i32, i32* %var
br i1 %cond2, label %do_something, label %loop_exit ; second trivial condition
do_something:
call void @some_func() noreturn nounwind
br label %loop_begin
loop_exit:
ret i32 0
}