1 //===- FunctionPropertiesAnalysisTest.cpp - Function Properties Unit Tests-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "llvm/Analysis/FunctionPropertiesAnalysis.h" 10 #include "llvm/AsmParser/Parser.h" 11 #include "llvm/IR/Instructions.h" 12 #include "llvm/IR/LLVMContext.h" 13 #include "llvm/IR/Module.h" 14 #include "llvm/Support/SourceMgr.h" 15 #include "gtest/gtest.h" 16 17 using namespace llvm; 18 19 static std::unique_ptr<Module> parseIR(LLVMContext &C, const char *IR) { 20 SMDiagnostic Err; 21 std::unique_ptr<Module> Mod = parseAssemblyString(IR, Err, C); 22 if (!Mod) 23 Err.print("MLAnalysisTests", errs()); 24 return Mod; 25 } 26 27 TEST(FunctionPropertiesTest, BasicTest) { 28 LLVMContext C; 29 std::unique_ptr<Module> M = parseIR(C, 30 R"IR( 31 target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" 32 target triple = "x86_64-pc-linux-gnu" 33 34 declare i32 @f1(i32) 35 declare i32 @f2(i32) 36 37 define i32 @branches(i32) { 38 %cond = icmp slt i32 %0, 3 39 br i1 %cond, label %then, label %else 40 41 then: 42 %ret.1 = call i32 @f1(i32 %0) 43 br label %last.block 44 45 else: 46 %ret.2 = call i32 @f2(i32 %0) 47 br label %last.block 48 49 last.block: 50 %ret = phi i32 [%ret.1, %then], [%ret.2, %else] 51 ret i32 %ret 52 } 53 54 define internal i32 @top() { 55 %1 = call i32 @branches(i32 2) 56 %2 = call i32 @f1(i32 %1) 57 ret i32 %2 58 } 59 )IR"); 60 61 FunctionAnalysisManager FAM; 62 FunctionPropertiesAnalysis FPA; 63 64 auto BranchesFeatures = FPA.run(*M->getFunction("branches"), FAM); 65 EXPECT_EQ(BranchesFeatures.BasicBlockCount, 4); 66 EXPECT_EQ(BranchesFeatures.BlocksReachedFromConditionalInstruction, 2); 67 EXPECT_EQ(BranchesFeatures.DirectCallsToDefinedFunctions, 0); 68 // 2 Users: top is one. The other is added because @branches is not internal, 69 // so it may have external callers. 70 EXPECT_EQ(BranchesFeatures.Uses, 2); 71 72 auto TopFeatures = FPA.run(*M->getFunction("top"), FAM); 73 EXPECT_EQ(TopFeatures.BasicBlockCount, 1); 74 EXPECT_EQ(TopFeatures.BlocksReachedFromConditionalInstruction, 0); 75 EXPECT_EQ(TopFeatures.DirectCallsToDefinedFunctions, 1); 76 EXPECT_EQ(TopFeatures.Uses, 0); 77 } 78