1f5b5ccf2SYuanfang Chen //===- llvm/unittest/CodeGen/PassManager.cpp - PassManager tests ----------===//
2f5b5ccf2SYuanfang Chen //
3f5b5ccf2SYuanfang Chen // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4f5b5ccf2SYuanfang Chen // See https://llvm.org/LICENSE.txt for license information.
5f5b5ccf2SYuanfang Chen // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6f5b5ccf2SYuanfang Chen //
7f5b5ccf2SYuanfang Chen //===----------------------------------------------------------------------===//
8f5b5ccf2SYuanfang Chen
9f5b5ccf2SYuanfang Chen #include "llvm/ADT/Triple.h"
10f5b5ccf2SYuanfang Chen #include "llvm/Analysis/CGSCCPassManager.h"
11f5b5ccf2SYuanfang Chen #include "llvm/Analysis/LoopAnalysisManager.h"
12f5b5ccf2SYuanfang Chen #include "llvm/AsmParser/Parser.h"
13*989f1c72Sserge-sans-paille #include "llvm/CodeGen/MachineFunction.h"
14f5b5ccf2SYuanfang Chen #include "llvm/CodeGen/MachineModuleInfo.h"
15f5b5ccf2SYuanfang Chen #include "llvm/CodeGen/MachinePassManager.h"
16f5b5ccf2SYuanfang Chen #include "llvm/IR/LLVMContext.h"
17f5b5ccf2SYuanfang Chen #include "llvm/IR/Module.h"
1889b57061SReid Kleckner #include "llvm/MC/TargetRegistry.h"
19f5b5ccf2SYuanfang Chen #include "llvm/Passes/PassBuilder.h"
20f5b5ccf2SYuanfang Chen #include "llvm/Support/Host.h"
21f5b5ccf2SYuanfang Chen #include "llvm/Support/SourceMgr.h"
22f5b5ccf2SYuanfang Chen #include "llvm/Support/TargetSelect.h"
23f5b5ccf2SYuanfang Chen #include "llvm/Target/TargetMachine.h"
24f5b5ccf2SYuanfang Chen #include "gtest/gtest.h"
25f5b5ccf2SYuanfang Chen
26f5b5ccf2SYuanfang Chen using namespace llvm;
27f5b5ccf2SYuanfang Chen
28f5b5ccf2SYuanfang Chen namespace {
29f5b5ccf2SYuanfang Chen
30f5b5ccf2SYuanfang Chen class TestFunctionAnalysis : public AnalysisInfoMixin<TestFunctionAnalysis> {
31f5b5ccf2SYuanfang Chen public:
32f5b5ccf2SYuanfang Chen struct Result {
Result__anone157d1f20111::TestFunctionAnalysis::Result33f5b5ccf2SYuanfang Chen Result(int Count) : InstructionCount(Count) {}
34f5b5ccf2SYuanfang Chen int InstructionCount;
35f5b5ccf2SYuanfang Chen };
36f5b5ccf2SYuanfang Chen
37f5b5ccf2SYuanfang Chen /// Run the analysis pass over the function and return a result.
run(Function & F,FunctionAnalysisManager & AM)38f5b5ccf2SYuanfang Chen Result run(Function &F, FunctionAnalysisManager &AM) {
39f5b5ccf2SYuanfang Chen int Count = 0;
40f5b5ccf2SYuanfang Chen for (Function::iterator BBI = F.begin(), BBE = F.end(); BBI != BBE; ++BBI)
41f5b5ccf2SYuanfang Chen for (BasicBlock::iterator II = BBI->begin(), IE = BBI->end(); II != IE;
42f5b5ccf2SYuanfang Chen ++II)
43f5b5ccf2SYuanfang Chen ++Count;
44f5b5ccf2SYuanfang Chen return Result(Count);
45f5b5ccf2SYuanfang Chen }
46f5b5ccf2SYuanfang Chen
47f5b5ccf2SYuanfang Chen private:
48f5b5ccf2SYuanfang Chen friend AnalysisInfoMixin<TestFunctionAnalysis>;
49f5b5ccf2SYuanfang Chen static AnalysisKey Key;
50f5b5ccf2SYuanfang Chen };
51f5b5ccf2SYuanfang Chen
52f5b5ccf2SYuanfang Chen AnalysisKey TestFunctionAnalysis::Key;
53f5b5ccf2SYuanfang Chen
54f5b5ccf2SYuanfang Chen class TestMachineFunctionAnalysis
55f5b5ccf2SYuanfang Chen : public AnalysisInfoMixin<TestMachineFunctionAnalysis> {
56f5b5ccf2SYuanfang Chen public:
57f5b5ccf2SYuanfang Chen struct Result {
Result__anone157d1f20111::TestMachineFunctionAnalysis::Result58f5b5ccf2SYuanfang Chen Result(int Count) : InstructionCount(Count) {}
59f5b5ccf2SYuanfang Chen int InstructionCount;
60f5b5ccf2SYuanfang Chen };
61f5b5ccf2SYuanfang Chen
62f5b5ccf2SYuanfang Chen /// Run the analysis pass over the machine function and return a result.
run(MachineFunction & MF,MachineFunctionAnalysisManager::Base & AM)63f5b5ccf2SYuanfang Chen Result run(MachineFunction &MF, MachineFunctionAnalysisManager::Base &AM) {
64f5b5ccf2SYuanfang Chen auto &MFAM = static_cast<MachineFunctionAnalysisManager &>(AM);
65f5b5ccf2SYuanfang Chen // Query function analysis result.
66f5b5ccf2SYuanfang Chen TestFunctionAnalysis::Result &FAR =
67f5b5ccf2SYuanfang Chen MFAM.getResult<TestFunctionAnalysis>(MF.getFunction());
68f5b5ccf2SYuanfang Chen // + 5
69f5b5ccf2SYuanfang Chen return FAR.InstructionCount;
70f5b5ccf2SYuanfang Chen }
71f5b5ccf2SYuanfang Chen
72f5b5ccf2SYuanfang Chen private:
73f5b5ccf2SYuanfang Chen friend AnalysisInfoMixin<TestMachineFunctionAnalysis>;
74f5b5ccf2SYuanfang Chen static AnalysisKey Key;
75f5b5ccf2SYuanfang Chen };
76f5b5ccf2SYuanfang Chen
77f5b5ccf2SYuanfang Chen AnalysisKey TestMachineFunctionAnalysis::Key;
78f5b5ccf2SYuanfang Chen
79f5b5ccf2SYuanfang Chen const std::string DoInitErrMsg = "doInitialization failed";
80f5b5ccf2SYuanfang Chen const std::string DoFinalErrMsg = "doFinalization failed";
81f5b5ccf2SYuanfang Chen
82f5b5ccf2SYuanfang Chen struct TestMachineFunctionPass : public PassInfoMixin<TestMachineFunctionPass> {
TestMachineFunctionPass__anone157d1f20111::TestMachineFunctionPass83f5b5ccf2SYuanfang Chen TestMachineFunctionPass(int &Count, std::vector<int> &BeforeInitialization,
84f5b5ccf2SYuanfang Chen std::vector<int> &BeforeFinalization,
85f5b5ccf2SYuanfang Chen std::vector<int> &MachineFunctionPassCount)
86f5b5ccf2SYuanfang Chen : Count(Count), BeforeInitialization(BeforeInitialization),
87f5b5ccf2SYuanfang Chen BeforeFinalization(BeforeFinalization),
88f5b5ccf2SYuanfang Chen MachineFunctionPassCount(MachineFunctionPassCount) {}
89f5b5ccf2SYuanfang Chen
doInitialization__anone157d1f20111::TestMachineFunctionPass90f5b5ccf2SYuanfang Chen Error doInitialization(Module &M, MachineFunctionAnalysisManager &MFAM) {
91f5b5ccf2SYuanfang Chen // Force doInitialization fail by starting with big `Count`.
92f5b5ccf2SYuanfang Chen if (Count > 10000)
93f5b5ccf2SYuanfang Chen return make_error<StringError>(DoInitErrMsg, inconvertibleErrorCode());
94f5b5ccf2SYuanfang Chen
95f5b5ccf2SYuanfang Chen // + 1
96f5b5ccf2SYuanfang Chen ++Count;
97f5b5ccf2SYuanfang Chen BeforeInitialization.push_back(Count);
98f5b5ccf2SYuanfang Chen return Error::success();
99f5b5ccf2SYuanfang Chen }
doFinalization__anone157d1f20111::TestMachineFunctionPass100f5b5ccf2SYuanfang Chen Error doFinalization(Module &M, MachineFunctionAnalysisManager &MFAM) {
101f5b5ccf2SYuanfang Chen // Force doFinalization fail by starting with big `Count`.
102f5b5ccf2SYuanfang Chen if (Count > 1000)
103f5b5ccf2SYuanfang Chen return make_error<StringError>(DoFinalErrMsg, inconvertibleErrorCode());
104f5b5ccf2SYuanfang Chen
105f5b5ccf2SYuanfang Chen // + 1
106f5b5ccf2SYuanfang Chen ++Count;
107f5b5ccf2SYuanfang Chen BeforeFinalization.push_back(Count);
108f5b5ccf2SYuanfang Chen return Error::success();
109f5b5ccf2SYuanfang Chen }
110f5b5ccf2SYuanfang Chen
run__anone157d1f20111::TestMachineFunctionPass111f5b5ccf2SYuanfang Chen PreservedAnalyses run(MachineFunction &MF,
112f5b5ccf2SYuanfang Chen MachineFunctionAnalysisManager &MFAM) {
113f5b5ccf2SYuanfang Chen // Query function analysis result.
114f5b5ccf2SYuanfang Chen TestFunctionAnalysis::Result &FAR =
115f5b5ccf2SYuanfang Chen MFAM.getResult<TestFunctionAnalysis>(MF.getFunction());
116f5b5ccf2SYuanfang Chen // 3 + 1 + 1 = 5
117f5b5ccf2SYuanfang Chen Count += FAR.InstructionCount;
118f5b5ccf2SYuanfang Chen
119f5b5ccf2SYuanfang Chen // Query module analysis result.
120f5b5ccf2SYuanfang Chen MachineModuleInfo &MMI =
121f5b5ccf2SYuanfang Chen MFAM.getResult<MachineModuleAnalysis>(*MF.getFunction().getParent());
122f5b5ccf2SYuanfang Chen // 1 + 1 + 1 = 3
123f5b5ccf2SYuanfang Chen Count += (MMI.getModule() == MF.getFunction().getParent());
124f5b5ccf2SYuanfang Chen
125f5b5ccf2SYuanfang Chen // Query machine function analysis result.
126f5b5ccf2SYuanfang Chen TestMachineFunctionAnalysis::Result &MFAR =
127f5b5ccf2SYuanfang Chen MFAM.getResult<TestMachineFunctionAnalysis>(MF);
128f5b5ccf2SYuanfang Chen // 3 + 1 + 1 = 5
129f5b5ccf2SYuanfang Chen Count += MFAR.InstructionCount;
130f5b5ccf2SYuanfang Chen
131f5b5ccf2SYuanfang Chen MachineFunctionPassCount.push_back(Count);
132f5b5ccf2SYuanfang Chen
133f5b5ccf2SYuanfang Chen return PreservedAnalyses::none();
134f5b5ccf2SYuanfang Chen }
135f5b5ccf2SYuanfang Chen
136f5b5ccf2SYuanfang Chen int &Count;
137f5b5ccf2SYuanfang Chen std::vector<int> &BeforeInitialization;
138f5b5ccf2SYuanfang Chen std::vector<int> &BeforeFinalization;
139f5b5ccf2SYuanfang Chen std::vector<int> &MachineFunctionPassCount;
140f5b5ccf2SYuanfang Chen };
141f5b5ccf2SYuanfang Chen
142f5b5ccf2SYuanfang Chen struct TestMachineModulePass : public PassInfoMixin<TestMachineModulePass> {
TestMachineModulePass__anone157d1f20111::TestMachineModulePass143f5b5ccf2SYuanfang Chen TestMachineModulePass(int &Count, std::vector<int> &MachineModulePassCount)
144f5b5ccf2SYuanfang Chen : Count(Count), MachineModulePassCount(MachineModulePassCount) {}
145f5b5ccf2SYuanfang Chen
run__anone157d1f20111::TestMachineModulePass146f5b5ccf2SYuanfang Chen Error run(Module &M, MachineFunctionAnalysisManager &MFAM) {
147f5b5ccf2SYuanfang Chen MachineModuleInfo &MMI = MFAM.getResult<MachineModuleAnalysis>(M);
148f5b5ccf2SYuanfang Chen // + 1
149f5b5ccf2SYuanfang Chen Count += (MMI.getModule() == &M);
150f5b5ccf2SYuanfang Chen MachineModulePassCount.push_back(Count);
151f5b5ccf2SYuanfang Chen return Error::success();
152f5b5ccf2SYuanfang Chen }
153f5b5ccf2SYuanfang Chen
run__anone157d1f20111::TestMachineModulePass154f5b5ccf2SYuanfang Chen PreservedAnalyses run(MachineFunction &MF,
155f5b5ccf2SYuanfang Chen MachineFunctionAnalysisManager &AM) {
156f5b5ccf2SYuanfang Chen llvm_unreachable(
157f5b5ccf2SYuanfang Chen "This should never be reached because this is machine module pass");
158f5b5ccf2SYuanfang Chen }
159f5b5ccf2SYuanfang Chen
160f5b5ccf2SYuanfang Chen int &Count;
161f5b5ccf2SYuanfang Chen std::vector<int> &MachineModulePassCount;
162f5b5ccf2SYuanfang Chen };
163f5b5ccf2SYuanfang Chen
parseIR(LLVMContext & Context,const char * IR)164f5b5ccf2SYuanfang Chen std::unique_ptr<Module> parseIR(LLVMContext &Context, const char *IR) {
165f5b5ccf2SYuanfang Chen SMDiagnostic Err;
166f5b5ccf2SYuanfang Chen return parseAssemblyString(IR, Err, Context);
167f5b5ccf2SYuanfang Chen }
168f5b5ccf2SYuanfang Chen
169f5b5ccf2SYuanfang Chen class PassManagerTest : public ::testing::Test {
170f5b5ccf2SYuanfang Chen protected:
171f5b5ccf2SYuanfang Chen LLVMContext Context;
172f5b5ccf2SYuanfang Chen std::unique_ptr<Module> M;
173f5b5ccf2SYuanfang Chen std::unique_ptr<TargetMachine> TM;
174f5b5ccf2SYuanfang Chen
175f5b5ccf2SYuanfang Chen public:
PassManagerTest()176f5b5ccf2SYuanfang Chen PassManagerTest()
177f5b5ccf2SYuanfang Chen : M(parseIR(Context, "define void @f() {\n"
178f5b5ccf2SYuanfang Chen "entry:\n"
179f5b5ccf2SYuanfang Chen " call void @g()\n"
180f5b5ccf2SYuanfang Chen " call void @h()\n"
181f5b5ccf2SYuanfang Chen " ret void\n"
182f5b5ccf2SYuanfang Chen "}\n"
183f5b5ccf2SYuanfang Chen "define void @g() {\n"
184f5b5ccf2SYuanfang Chen " ret void\n"
185f5b5ccf2SYuanfang Chen "}\n"
186f5b5ccf2SYuanfang Chen "define void @h() {\n"
187f5b5ccf2SYuanfang Chen " ret void\n"
188f5b5ccf2SYuanfang Chen "}\n")) {
189f5b5ccf2SYuanfang Chen // MachineModuleAnalysis needs a TargetMachine instance.
190f5b5ccf2SYuanfang Chen llvm::InitializeAllTargets();
191f5b5ccf2SYuanfang Chen
192f5b5ccf2SYuanfang Chen std::string TripleName = Triple::normalize(sys::getDefaultTargetTriple());
193f5b5ccf2SYuanfang Chen std::string Error;
194f5b5ccf2SYuanfang Chen const Target *TheTarget =
195f5b5ccf2SYuanfang Chen TargetRegistry::lookupTarget(TripleName, Error);
196f5b5ccf2SYuanfang Chen if (!TheTarget)
197f5b5ccf2SYuanfang Chen return;
198f5b5ccf2SYuanfang Chen
199f5b5ccf2SYuanfang Chen TargetOptions Options;
200f5b5ccf2SYuanfang Chen TM.reset(TheTarget->createTargetMachine(TripleName, "", "",
201f5b5ccf2SYuanfang Chen Options, None));
202f5b5ccf2SYuanfang Chen }
203f5b5ccf2SYuanfang Chen };
204f5b5ccf2SYuanfang Chen
TEST_F(PassManagerTest,Basic)205f5b5ccf2SYuanfang Chen TEST_F(PassManagerTest, Basic) {
206f5b5ccf2SYuanfang Chen if (!TM)
2075bbf1feaSIgor Kudrin GTEST_SKIP();
208f5b5ccf2SYuanfang Chen
209f5b5ccf2SYuanfang Chen LLVMTargetMachine *LLVMTM = static_cast<LLVMTargetMachine *>(TM.get());
210f5b5ccf2SYuanfang Chen M->setDataLayout(TM->createDataLayout());
211f5b5ccf2SYuanfang Chen
2126f713100SArthur Eubanks LoopAnalysisManager LAM;
2136f713100SArthur Eubanks FunctionAnalysisManager FAM;
2146f713100SArthur Eubanks CGSCCAnalysisManager CGAM;
2156f713100SArthur Eubanks ModuleAnalysisManager MAM;
216f5b5ccf2SYuanfang Chen PassBuilder PB(TM.get());
217f5b5ccf2SYuanfang Chen PB.registerModuleAnalyses(MAM);
218f5b5ccf2SYuanfang Chen PB.registerFunctionAnalyses(FAM);
219f5b5ccf2SYuanfang Chen PB.crossRegisterProxies(LAM, FAM, CGAM, MAM);
220f5b5ccf2SYuanfang Chen
221f5b5ccf2SYuanfang Chen FAM.registerPass([&] { return TestFunctionAnalysis(); });
222f5b5ccf2SYuanfang Chen FAM.registerPass([&] { return PassInstrumentationAnalysis(); });
223f5b5ccf2SYuanfang Chen MAM.registerPass([&] { return MachineModuleAnalysis(LLVMTM); });
224f5b5ccf2SYuanfang Chen MAM.registerPass([&] { return PassInstrumentationAnalysis(); });
225f5b5ccf2SYuanfang Chen
226f5b5ccf2SYuanfang Chen MachineFunctionAnalysisManager MFAM;
227f5b5ccf2SYuanfang Chen {
228f5b5ccf2SYuanfang Chen // Test move assignment.
2296f713100SArthur Eubanks MachineFunctionAnalysisManager NestedMFAM(FAM, MAM);
230f5b5ccf2SYuanfang Chen NestedMFAM.registerPass([&] { return PassInstrumentationAnalysis(); });
231f5b5ccf2SYuanfang Chen NestedMFAM.registerPass([&] { return TestMachineFunctionAnalysis(); });
232f5b5ccf2SYuanfang Chen MFAM = std::move(NestedMFAM);
233f5b5ccf2SYuanfang Chen }
234f5b5ccf2SYuanfang Chen
235f5b5ccf2SYuanfang Chen int Count = 0;
236f5b5ccf2SYuanfang Chen std::vector<int> BeforeInitialization[2];
237f5b5ccf2SYuanfang Chen std::vector<int> BeforeFinalization[2];
238f5b5ccf2SYuanfang Chen std::vector<int> TestMachineFunctionCount[2];
239f5b5ccf2SYuanfang Chen std::vector<int> TestMachineModuleCount[2];
240f5b5ccf2SYuanfang Chen
241f5b5ccf2SYuanfang Chen MachineFunctionPassManager MFPM;
242f5b5ccf2SYuanfang Chen {
243f5b5ccf2SYuanfang Chen // Test move assignment.
2446f713100SArthur Eubanks MachineFunctionPassManager NestedMFPM;
245f5b5ccf2SYuanfang Chen NestedMFPM.addPass(TestMachineModulePass(Count, TestMachineModuleCount[0]));
246f5b5ccf2SYuanfang Chen NestedMFPM.addPass(TestMachineFunctionPass(Count, BeforeInitialization[0],
247f5b5ccf2SYuanfang Chen BeforeFinalization[0],
248f5b5ccf2SYuanfang Chen TestMachineFunctionCount[0]));
249f5b5ccf2SYuanfang Chen NestedMFPM.addPass(TestMachineModulePass(Count, TestMachineModuleCount[1]));
250f5b5ccf2SYuanfang Chen NestedMFPM.addPass(TestMachineFunctionPass(Count, BeforeInitialization[1],
251f5b5ccf2SYuanfang Chen BeforeFinalization[1],
252f5b5ccf2SYuanfang Chen TestMachineFunctionCount[1]));
253f5b5ccf2SYuanfang Chen MFPM = std::move(NestedMFPM);
254f5b5ccf2SYuanfang Chen }
255f5b5ccf2SYuanfang Chen
256f5b5ccf2SYuanfang Chen ASSERT_FALSE(errorToBool(MFPM.run(*M, MFAM)));
257f5b5ccf2SYuanfang Chen
258f5b5ccf2SYuanfang Chen // Check first machine module pass
259f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, TestMachineModuleCount[0].size());
260f5b5ccf2SYuanfang Chen EXPECT_EQ(3, TestMachineModuleCount[0][0]);
261f5b5ccf2SYuanfang Chen
262f5b5ccf2SYuanfang Chen // Check first machine function pass
263f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, BeforeInitialization[0].size());
264f5b5ccf2SYuanfang Chen EXPECT_EQ(1, BeforeInitialization[0][0]);
265f5b5ccf2SYuanfang Chen EXPECT_EQ(3u, TestMachineFunctionCount[0].size());
266f5b5ccf2SYuanfang Chen EXPECT_EQ(10, TestMachineFunctionCount[0][0]);
267f5b5ccf2SYuanfang Chen EXPECT_EQ(13, TestMachineFunctionCount[0][1]);
268f5b5ccf2SYuanfang Chen EXPECT_EQ(16, TestMachineFunctionCount[0][2]);
269f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, BeforeFinalization[0].size());
270f5b5ccf2SYuanfang Chen EXPECT_EQ(31, BeforeFinalization[0][0]);
271f5b5ccf2SYuanfang Chen
272f5b5ccf2SYuanfang Chen // Check second machine module pass
273f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, TestMachineModuleCount[1].size());
274f5b5ccf2SYuanfang Chen EXPECT_EQ(17, TestMachineModuleCount[1][0]);
275f5b5ccf2SYuanfang Chen
276f5b5ccf2SYuanfang Chen // Check second machine function pass
277f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, BeforeInitialization[1].size());
278f5b5ccf2SYuanfang Chen EXPECT_EQ(2, BeforeInitialization[1][0]);
279f5b5ccf2SYuanfang Chen EXPECT_EQ(3u, TestMachineFunctionCount[1].size());
280f5b5ccf2SYuanfang Chen EXPECT_EQ(24, TestMachineFunctionCount[1][0]);
281f5b5ccf2SYuanfang Chen EXPECT_EQ(27, TestMachineFunctionCount[1][1]);
282f5b5ccf2SYuanfang Chen EXPECT_EQ(30, TestMachineFunctionCount[1][2]);
283f5b5ccf2SYuanfang Chen EXPECT_EQ(1u, BeforeFinalization[1].size());
284f5b5ccf2SYuanfang Chen EXPECT_EQ(32, BeforeFinalization[1][0]);
285f5b5ccf2SYuanfang Chen
286f5b5ccf2SYuanfang Chen EXPECT_EQ(32, Count);
287f5b5ccf2SYuanfang Chen
288f5b5ccf2SYuanfang Chen // doInitialization returns error
289f5b5ccf2SYuanfang Chen Count = 10000;
290f5b5ccf2SYuanfang Chen MFPM.addPass(TestMachineFunctionPass(Count, BeforeInitialization[1],
291f5b5ccf2SYuanfang Chen BeforeFinalization[1],
292f5b5ccf2SYuanfang Chen TestMachineFunctionCount[1]));
293f5b5ccf2SYuanfang Chen std::string Message;
294f5b5ccf2SYuanfang Chen llvm::handleAllErrors(MFPM.run(*M, MFAM), [&](llvm::StringError &Error) {
295f5b5ccf2SYuanfang Chen Message = Error.getMessage();
296f5b5ccf2SYuanfang Chen });
297f5b5ccf2SYuanfang Chen EXPECT_EQ(Message, DoInitErrMsg);
298f5b5ccf2SYuanfang Chen
299f5b5ccf2SYuanfang Chen // doFinalization returns error
300f5b5ccf2SYuanfang Chen Count = 1000;
301f5b5ccf2SYuanfang Chen MFPM.addPass(TestMachineFunctionPass(Count, BeforeInitialization[1],
302f5b5ccf2SYuanfang Chen BeforeFinalization[1],
303f5b5ccf2SYuanfang Chen TestMachineFunctionCount[1]));
304f5b5ccf2SYuanfang Chen llvm::handleAllErrors(MFPM.run(*M, MFAM), [&](llvm::StringError &Error) {
305f5b5ccf2SYuanfang Chen Message = Error.getMessage();
306f5b5ccf2SYuanfang Chen });
307f5b5ccf2SYuanfang Chen EXPECT_EQ(Message, DoFinalErrMsg);
308f5b5ccf2SYuanfang Chen }
309f5b5ccf2SYuanfang Chen
310f5b5ccf2SYuanfang Chen } // namespace
311