Skip to content

Commit c49a606

Browse files
author
git apple-llvm automerger
committed
Merge commit '67a58fa3a687' from llvm.org/main into next
2 parents c305b7e + 67a58fa commit c49a606

File tree

2 files changed

+66
-3
lines changed

2 files changed

+66
-3
lines changed

llvm/lib/Transforms/IPO/FunctionSpecialization.cpp

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -789,12 +789,27 @@ bool llvm::runFunctionSpecialization(
789789
Solver.trackValueOfGlobalVariable(&G);
790790
}
791791

792+
auto &TrackedFuncs = Solver.getArgumentTrackedFunctions();
793+
SmallVector<Function *, 16> FuncDecls(TrackedFuncs.begin(),
794+
TrackedFuncs.end());
795+
796+
// No tracked functions, so nothing to do: don't run the solver and remove
797+
// the ssa_copy intrinsics that may have been introduced.
798+
if (TrackedFuncs.empty()) {
799+
removeSSACopy(M);
800+
return false;
801+
}
802+
792803
// Solve for constants.
793804
auto RunSCCPSolver = [&](auto &WorkList) {
794805
bool ResolvedUndefs = true;
795806

796807
while (ResolvedUndefs) {
808+
// Not running the solver unnecessary is checked in regression test
809+
// nothing-to-do.ll, so if this debug message is changed, this regression
810+
// test needs updating too.
797811
LLVM_DEBUG(dbgs() << "FnSpecialization: Running solver\n");
812+
798813
Solver.solve();
799814
LLVM_DEBUG(dbgs() << "FnSpecialization: Resolving undefs\n");
800815
ResolvedUndefs = false;
@@ -815,9 +830,6 @@ bool llvm::runFunctionSpecialization(
815830
}
816831
};
817832

818-
auto &TrackedFuncs = Solver.getArgumentTrackedFunctions();
819-
SmallVector<Function *, 16> FuncDecls(TrackedFuncs.begin(),
820-
TrackedFuncs.end());
821833
#ifndef NDEBUG
822834
LLVM_DEBUG(dbgs() << "FnSpecialization: Worklist fn decls:\n");
823835
for (auto *F : FuncDecls)
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
; REQUIRES: asserts
2+
; RUN: opt -function-specialization -debug -S < %s 2>&1 | FileCheck %s
3+
4+
; The purpose of this test is to check that we don't run the solver as there's
5+
; nothing to do here. For a test that doesn't trigger function specialisation,
6+
; it is intentionally 'big' because we also want to check that the ssa.copy
7+
; intrinsics that are introduced by the solver are cleaned up if we bail
8+
; early. Thus, first check the debug messages for the introduction of these
9+
; intrinsics:
10+
11+
; CHECK: FnSpecialization: Analysing decl: foo
12+
; CHECK: Found replacement{{.*}} call i32 @llvm.ssa.copy.i32
13+
; CHECK: Found replacement{{.*}} call i32 @llvm.ssa.copy.i32
14+
15+
; Then, make sure the solver didn't run:
16+
17+
; CHECK-NOT: Running solver
18+
19+
; Finally, check the absence and thus removal of these intrinsics:
20+
21+
; CHECK-LABEL: @foo
22+
; CHECK-NOT: call i32 @llvm.ssa.copy.i32
23+
24+
@N = external dso_local global i32, align 4
25+
@B = external dso_local global i32*, align 8
26+
@A = external dso_local global i32*, align 8
27+
28+
define dso_local i32 @foo() {
29+
entry:
30+
br label %for.cond
31+
32+
for.cond:
33+
%i.0 = phi i32 [ 0, %entry ], [ %inc, %for.body ]
34+
%0 = load i32, i32* @N, align 4
35+
%cmp = icmp slt i32 %i.0, %0
36+
br i1 %cmp, label %for.body, label %for.cond.cleanup
37+
38+
for.cond.cleanup:
39+
ret i32 undef
40+
41+
for.body:
42+
%1 = load i32*, i32** @B, align 8
43+
%idxprom = sext i32 %i.0 to i64
44+
%arrayidx = getelementptr inbounds i32, i32* %1, i64 %idxprom
45+
%2 = load i32, i32* %arrayidx, align 4
46+
%3 = load i32*, i32** @A, align 8
47+
%arrayidx2 = getelementptr inbounds i32, i32* %3, i64 %idxprom
48+
store i32 %2, i32* %arrayidx2, align 4
49+
%inc = add nsw i32 %i.0, 1
50+
br label %for.cond
51+
}

0 commit comments

Comments
 (0)