Revert "[MLGO][IR2Vec] Integrating IR2Vec with MLInliner (#143479)" (#145418)

This reverts commit af2c06ecd6 as it
causes failure of lit test (Transforms/Inline/ML/interactive-mode.ll)
This commit is contained in:
S. VenkataKeerthy
2025-06-24 00:48:16 +02:00
committed by GitHub
parent 92a7f6fbbe
commit d37325ea95
8 changed files with 11 additions and 326 deletions

View File

@@ -15,7 +15,6 @@
#define LLVM_ANALYSIS_FUNCTIONPROPERTIESANALYSIS_H
#include "llvm/ADT/DenseSet.h"
#include "llvm/Analysis/IR2Vec.h"
#include "llvm/IR/Dominators.h"
#include "llvm/IR/PassManager.h"
#include "llvm/Support/Compiler.h"
@@ -33,19 +32,17 @@ class FunctionPropertiesInfo {
void updateAggregateStats(const Function &F, const LoopInfo &LI);
void reIncludeBB(const BasicBlock &BB);
ir2vec::Embedding FunctionEmbedding = ir2vec::Embedding(0.0);
std::optional<ir2vec::Vocab> IR2VecVocab;
public:
LLVM_ABI static FunctionPropertiesInfo
getFunctionPropertiesInfo(const Function &F, const DominatorTree &DT,
const LoopInfo &LI,
const IR2VecVocabResult *VocabResult);
const LoopInfo &LI);
LLVM_ABI static FunctionPropertiesInfo
getFunctionPropertiesInfo(Function &F, FunctionAnalysisManager &FAM);
bool operator==(const FunctionPropertiesInfo &FPI) const;
bool operator==(const FunctionPropertiesInfo &FPI) const {
return std::memcmp(this, &FPI, sizeof(FunctionPropertiesInfo)) == 0;
}
bool operator!=(const FunctionPropertiesInfo &FPI) const {
return !(*this == FPI);
@@ -140,19 +137,6 @@ public:
int64_t CallReturnsVectorPointerCount = 0;
int64_t CallWithManyArgumentsCount = 0;
int64_t CallWithPointerArgumentCount = 0;
const ir2vec::Embedding &getFunctionEmbedding() const {
return FunctionEmbedding;
}
const std::optional<ir2vec::Vocab> &getIR2VecVocab() const {
return IR2VecVocab;
}
// Helper intended to be useful for unittests
void setFunctionEmbeddingForTest(const ir2vec::Embedding &Embedding) {
FunctionEmbedding = Embedding;
}
};
// Analysis pass
@@ -208,7 +192,7 @@ private:
DominatorTree &getUpdatedDominatorTree(FunctionAnalysisManager &FAM) const;
DenseSet<const BasicBlock *> Successors, CallUsers;
DenseSet<const BasicBlock *> Successors;
// Edges we might potentially need to remove from the dominator tree.
SmallVector<DominatorTree::UpdateType, 2> DomTreeUpdates;

View File

@@ -331,10 +331,6 @@ public:
};
Result run(Module &M, ModuleAnalysisManager &MAM) { return Result(M, MAM); }
private:
static bool initializeIR2VecVocabIfRequested(Module &M,
ModuleAnalysisManager &MAM);
};
/// Printer pass for the InlineAdvisorAnalysis results.

View File

@@ -142,12 +142,6 @@ enum class FeatureIndex : size_t {
INLINE_FEATURE_ITERATOR(POPULATE_INDICES)
#undef POPULATE_INDICES
// IR2Vec embeddings
// Dimensions of embeddings are not known in the compile time (until vocab is
// read). Hence macros cannot be used here.
callee_embedding,
caller_embedding,
NumberOfFeatures
};
// clang-format on
@@ -160,7 +154,7 @@ inlineCostFeatureToMlFeature(InlineCostFeatureIndex Feature) {
constexpr size_t NumberOfFeatures =
static_cast<size_t>(FeatureIndex::NumberOfFeatures);
LLVM_ABI extern std::vector<TensorSpec> FeatureMap;
LLVM_ABI extern const std::vector<TensorSpec> FeatureMap;
LLVM_ABI extern const char *const DecisionName;
LLVM_ABI extern const TensorSpec InlineDecisionSpec;

View File

@@ -82,7 +82,6 @@ private:
int64_t NodeCount = 0;
int64_t EdgeCount = 0;
int64_t EdgesOfLastSeenNodes = 0;
const bool UseIR2Vec;
std::map<const LazyCallGraph::Node *, unsigned> FunctionLevels;
const int32_t InitialIRSize = 0;

View File

@@ -199,29 +199,6 @@ void FunctionPropertiesInfo::updateForBB(const BasicBlock &BB,
#undef CHECK_OPERAND
}
}
if (IR2VecVocab) {
// We instantiate the IR2Vec embedder each time, as having an unique
// pointer to the embedder as member of the class would make it
// non-copyable. Instantiating the embedder in itself is not costly.
auto EmbOrErr = ir2vec::Embedder::create(IR2VecKind::Symbolic,
*BB.getParent(), *IR2VecVocab);
if (Error Err = EmbOrErr.takeError()) {
handleAllErrors(std::move(Err), [&](const ErrorInfoBase &EI) {
BB.getContext().emitError("Error creating IR2Vec embeddings: " +
EI.message());
});
return;
}
auto Embedder = std::move(*EmbOrErr);
const auto &BBEmbedding = Embedder->getBBVector(BB);
// Subtract BBEmbedding from Function embedding if the direction is -1,
// and add it if the direction is +1.
if (Direction == -1)
FunctionEmbedding -= BBEmbedding;
else
FunctionEmbedding += BBEmbedding;
}
}
void FunctionPropertiesInfo::updateAggregateStats(const Function &F,
@@ -243,24 +220,14 @@ void FunctionPropertiesInfo::updateAggregateStats(const Function &F,
FunctionPropertiesInfo FunctionPropertiesInfo::getFunctionPropertiesInfo(
Function &F, FunctionAnalysisManager &FAM) {
// We use the cached result of the IR2VecVocabAnalysis run by
// InlineAdvisorAnalysis. If the IR2VecVocabAnalysis is not run, we don't
// use IR2Vec embeddings.
auto VocabResult = FAM.getResult<ModuleAnalysisManagerFunctionProxy>(F)
.getCachedResult<IR2VecVocabAnalysis>(*F.getParent());
return getFunctionPropertiesInfo(F, FAM.getResult<DominatorTreeAnalysis>(F),
FAM.getResult<LoopAnalysis>(F), VocabResult);
FAM.getResult<LoopAnalysis>(F));
}
FunctionPropertiesInfo FunctionPropertiesInfo::getFunctionPropertiesInfo(
const Function &F, const DominatorTree &DT, const LoopInfo &LI,
const IR2VecVocabResult *VocabResult) {
const Function &F, const DominatorTree &DT, const LoopInfo &LI) {
FunctionPropertiesInfo FPI;
if (VocabResult && VocabResult->isValid()) {
FPI.IR2VecVocab = VocabResult->getVocabulary();
FPI.FunctionEmbedding = ir2vec::Embedding(VocabResult->getDimension(), 0.0);
}
for (const auto &BB : F)
if (DT.isReachableFromEntry(&BB))
FPI.reIncludeBB(BB);
@@ -268,66 +235,6 @@ FunctionPropertiesInfo FunctionPropertiesInfo::getFunctionPropertiesInfo(
return FPI;
}
bool FunctionPropertiesInfo::operator==(
const FunctionPropertiesInfo &FPI) const {
if (BasicBlockCount != FPI.BasicBlockCount ||
BlocksReachedFromConditionalInstruction !=
FPI.BlocksReachedFromConditionalInstruction ||
Uses != FPI.Uses ||
DirectCallsToDefinedFunctions != FPI.DirectCallsToDefinedFunctions ||
LoadInstCount != FPI.LoadInstCount ||
StoreInstCount != FPI.StoreInstCount ||
MaxLoopDepth != FPI.MaxLoopDepth ||
TopLevelLoopCount != FPI.TopLevelLoopCount ||
TotalInstructionCount != FPI.TotalInstructionCount ||
BasicBlocksWithSingleSuccessor != FPI.BasicBlocksWithSingleSuccessor ||
BasicBlocksWithTwoSuccessors != FPI.BasicBlocksWithTwoSuccessors ||
BasicBlocksWithMoreThanTwoSuccessors !=
FPI.BasicBlocksWithMoreThanTwoSuccessors ||
BasicBlocksWithSinglePredecessor !=
FPI.BasicBlocksWithSinglePredecessor ||
BasicBlocksWithTwoPredecessors != FPI.BasicBlocksWithTwoPredecessors ||
BasicBlocksWithMoreThanTwoPredecessors !=
FPI.BasicBlocksWithMoreThanTwoPredecessors ||
BigBasicBlocks != FPI.BigBasicBlocks ||
MediumBasicBlocks != FPI.MediumBasicBlocks ||
SmallBasicBlocks != FPI.SmallBasicBlocks ||
CastInstructionCount != FPI.CastInstructionCount ||
FloatingPointInstructionCount != FPI.FloatingPointInstructionCount ||
IntegerInstructionCount != FPI.IntegerInstructionCount ||
ConstantIntOperandCount != FPI.ConstantIntOperandCount ||
ConstantFPOperandCount != FPI.ConstantFPOperandCount ||
ConstantOperandCount != FPI.ConstantOperandCount ||
InstructionOperandCount != FPI.InstructionOperandCount ||
BasicBlockOperandCount != FPI.BasicBlockOperandCount ||
GlobalValueOperandCount != FPI.GlobalValueOperandCount ||
InlineAsmOperandCount != FPI.InlineAsmOperandCount ||
ArgumentOperandCount != FPI.ArgumentOperandCount ||
UnknownOperandCount != FPI.UnknownOperandCount ||
CriticalEdgeCount != FPI.CriticalEdgeCount ||
ControlFlowEdgeCount != FPI.ControlFlowEdgeCount ||
UnconditionalBranchCount != FPI.UnconditionalBranchCount ||
IntrinsicCount != FPI.IntrinsicCount ||
DirectCallCount != FPI.DirectCallCount ||
IndirectCallCount != FPI.IndirectCallCount ||
CallReturnsIntegerCount != FPI.CallReturnsIntegerCount ||
CallReturnsFloatCount != FPI.CallReturnsFloatCount ||
CallReturnsPointerCount != FPI.CallReturnsPointerCount ||
CallReturnsVectorIntCount != FPI.CallReturnsVectorIntCount ||
CallReturnsVectorFloatCount != FPI.CallReturnsVectorFloatCount ||
CallReturnsVectorPointerCount != FPI.CallReturnsVectorPointerCount ||
CallWithManyArgumentsCount != FPI.CallWithManyArgumentsCount ||
CallWithPointerArgumentCount != FPI.CallWithPointerArgumentCount) {
return false;
}
// Check the equality of the function embeddings. We don't check the equality
// of Vocabulary as it remains the same.
if (!FunctionEmbedding.approximatelyEquals(FPI.FunctionEmbedding))
return false;
return true;
}
void FunctionPropertiesInfo::print(raw_ostream &OS) const {
#define PRINT_PROPERTY(PROP_NAME) OS << #PROP_NAME ": " << PROP_NAME << "\n";
@@ -415,16 +322,6 @@ FunctionPropertiesUpdater::FunctionPropertiesUpdater(
// The caller's entry BB may change due to new alloca instructions.
LikelyToChangeBBs.insert(&*Caller.begin());
// The users of the value returned by call instruction can change
// leading to the change in embeddings being computed, when used.
// We conservatively add the BBs with such uses to LikelyToChangeBBs.
for (const auto *User : CB.users())
CallUsers.insert(dyn_cast<Instruction>(User)->getParent());
// CallSiteBB can be removed from CallUsers if present, it's taken care
// separately.
CallUsers.erase(&CallSiteBB);
LikelyToChangeBBs.insert_range(CallUsers);
// The successors may become unreachable in the case of `invoke` inlining.
// We track successors separately, too, because they form a boundary, together
// with the CB BB ('Entry') between which the inlined callee will be pasted.
@@ -538,9 +435,6 @@ void FunctionPropertiesUpdater::finish(FunctionAnalysisManager &FAM) const {
if (&CallSiteBB != &*Caller.begin())
Reinclude.insert(&*Caller.begin());
// Reinclude the BBs which use the values returned by call instruction
Reinclude.insert_range(CallUsers);
// Distribute the successors to the 2 buckets.
for (const auto *Succ : Successors)
if (DT.isReachableFromEntry(Succ))
@@ -592,9 +486,6 @@ bool FunctionPropertiesUpdater::isUpdateValid(Function &F,
return false;
DominatorTree DT(F);
LoopInfo LI(DT);
auto VocabResult = FAM.getResult<ModuleAnalysisManagerFunctionProxy>(F)
.getCachedResult<IR2VecVocabAnalysis>(*F.getParent());
auto Fresh =
FunctionPropertiesInfo::getFunctionPropertiesInfo(F, DT, LI, VocabResult);
auto Fresh = FunctionPropertiesInfo::getFunctionPropertiesInfo(F, DT, LI);
return FPI == Fresh;
}

View File

@@ -16,7 +16,6 @@
#include "llvm/ADT/StringExtras.h"
#include "llvm/Analysis/AssumptionCache.h"
#include "llvm/Analysis/EphemeralValuesCache.h"
#include "llvm/Analysis/IR2Vec.h"
#include "llvm/Analysis/InlineCost.h"
#include "llvm/Analysis/OptimizationRemarkEmitter.h"
#include "llvm/Analysis/ProfileSummaryInfo.h"
@@ -65,13 +64,6 @@ static cl::opt<bool>
cl::desc("If true, annotate inline advisor remarks "
"with LTO and pass information."));
// This flag is used to enable IR2Vec embeddings in the ML inliner; Only valid
// with ML inliner. The vocab file is used to initialize the embeddings.
static cl::opt<std::string> IR2VecVocabFile(
"ml-inliner-ir2vec-vocab-file", cl::Hidden,
cl::desc("Vocab file for IR2Vec; Setting this enables "
"configuring the model to use IR2Vec embeddings."));
namespace llvm {
extern cl::opt<InlinerFunctionImportStatsOpts> InlinerFunctionImportStats;
} // namespace llvm
@@ -214,20 +206,6 @@ void InlineAdvice::recordInliningWithCalleeDeleted() {
AnalysisKey InlineAdvisorAnalysis::Key;
AnalysisKey PluginInlineAdvisorAnalysis::Key;
bool InlineAdvisorAnalysis::initializeIR2VecVocabIfRequested(
Module &M, ModuleAnalysisManager &MAM) {
if (!IR2VecVocabFile.empty()) {
auto IR2VecVocabResult = MAM.getResult<IR2VecVocabAnalysis>(M);
if (!IR2VecVocabResult.isValid()) {
M.getContext().emitError("Failed to load IR2Vec vocabulary");
return false;
}
}
// No vocab file specified is OK; We just don't use IR2Vec
// embeddings.
return true;
}
bool InlineAdvisorAnalysis::Result::tryCreate(
InlineParams Params, InliningAdvisorMode Mode,
const ReplayInlinerSettings &ReplaySettings, InlineContext IC) {
@@ -253,21 +231,14 @@ bool InlineAdvisorAnalysis::Result::tryCreate(
/* EmitRemarks =*/true, IC);
}
break;
// Run IR2VecVocabAnalysis once per module to get the vocabulary.
// We run it here because it is immutable and we want to avoid running it
// multiple times.
case InliningAdvisorMode::Development:
#ifdef LLVM_HAVE_TFLITE
LLVM_DEBUG(dbgs() << "Using development-mode inliner policy.\n");
if (!InlineAdvisorAnalysis::initializeIR2VecVocabIfRequested(M, MAM))
return false;
Advisor = llvm::getDevelopmentModeAdvisor(M, MAM, GetDefaultAdvice);
#endif
break;
case InliningAdvisorMode::Release:
LLVM_DEBUG(dbgs() << "Using release-mode inliner policy.\n");
if (!InlineAdvisorAnalysis::initializeIR2VecVocabIfRequested(M, MAM))
return false;
Advisor = llvm::getReleaseModeAdvisor(M, MAM, GetDefaultAdvice);
break;
}

View File

@@ -107,7 +107,7 @@ static cl::opt<bool> KeepFPICache(
cl::init(false));
// clang-format off
std::vector<TensorSpec> llvm::FeatureMap{
const std::vector<TensorSpec> llvm::FeatureMap{
#define POPULATE_NAMES(DTYPE, SHAPE, NAME, __) TensorSpec::createSpec<DTYPE>(#NAME, SHAPE),
// InlineCost features - these must come first
INLINE_COST_FEATURE_ITERATOR(POPULATE_NAMES)
@@ -144,7 +144,6 @@ MLInlineAdvisor::MLInlineAdvisor(
M, MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager()),
ModelRunner(std::move(Runner)), GetDefaultAdvice(GetDefaultAdvice),
CG(MAM.getResult<LazyCallGraphAnalysis>(M)),
UseIR2Vec(MAM.getCachedResult<IR2VecVocabAnalysis>(M) != nullptr),
InitialIRSize(getModuleIRSize()), CurrentIRSize(InitialIRSize),
PSI(MAM.getResult<ProfileSummaryAnalysis>(M)) {
assert(ModelRunner);
@@ -187,19 +186,6 @@ MLInlineAdvisor::MLInlineAdvisor(
EdgeCount += getLocalCalls(KVP.first->getFunction());
}
NodeCount = AllNodes.size();
if (auto IR2VecVocabResult = MAM.getCachedResult<IR2VecVocabAnalysis>(M)) {
if (!IR2VecVocabResult->isValid()) {
M.getContext().emitError("IR2VecVocabAnalysis is not valid");
return;
}
// Add the IR2Vec features to the feature map
auto IR2VecDim = IR2VecVocabResult->getDimension();
FeatureMap.push_back(
TensorSpec::createSpec<float>("callee_embedding", {IR2VecDim}));
FeatureMap.push_back(
TensorSpec::createSpec<float>("caller_embedding", {IR2VecDim}));
}
}
unsigned MLInlineAdvisor::getInitialFunctionLevel(const Function &F) const {
@@ -447,24 +433,6 @@ std::unique_ptr<InlineAdvice> MLInlineAdvisor::getAdviceImpl(CallBase &CB) {
*ModelRunner->getTensor<int64_t>(FeatureIndex::is_caller_avail_external) =
Caller.hasAvailableExternallyLinkage();
if (UseIR2Vec) {
// Python side expects float embeddings. The IR2Vec embeddings are doubles
// as of now due to the restriction of fromJSON method used by the
// readVocabulary method in ir2vec::Embeddings.
auto setEmbedding = [&](const ir2vec::Embedding &Embedding,
FeatureIndex Index) {
auto Embedding_float =
std::vector<float>(Embedding.begin(), Embedding.end());
std::memcpy(ModelRunner->getTensor<float>(Index), Embedding_float.data(),
Embedding.size() * sizeof(float));
};
setEmbedding(CalleeBefore.getFunctionEmbedding(),
FeatureIndex::callee_embedding);
setEmbedding(CallerBefore.getFunctionEmbedding(),
FeatureIndex::caller_embedding);
}
// Add the cost features
for (size_t I = 0;
I < static_cast<size_t>(InlineCostFeatureIndex::NumberOfFeatures); ++I) {

View File

@@ -8,7 +8,6 @@
#include "llvm/Analysis/FunctionPropertiesAnalysis.h"
#include "llvm/Analysis/AliasAnalysis.h"
#include "llvm/Analysis/IR2Vec.h"
#include "llvm/Analysis/LoopInfo.h"
#include "llvm/AsmParser/Parser.h"
#include "llvm/IR/Dominators.h"
@@ -21,20 +20,15 @@
#include "llvm/Support/Compiler.h"
#include "llvm/Support/SourceMgr.h"
#include "llvm/Transforms/Utils/Cloning.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include <cstring>
using namespace llvm;
using namespace testing;
namespace llvm {
LLVM_ABI extern cl::opt<bool> EnableDetailedFunctionProperties;
LLVM_ABI extern cl::opt<bool> BigBasicBlockInstructionThreshold;
LLVM_ABI extern cl::opt<bool> MediumBasicBlockInstrutionThreshold;
LLVM_ABI extern cl::opt<float> ir2vec::OpcWeight;
LLVM_ABI extern cl::opt<float> ir2vec::TypeWeight;
LLVM_ABI extern cl::opt<float> ir2vec::ArgWeight;
} // namespace llvm
namespace {
@@ -42,65 +36,17 @@ namespace {
class FunctionPropertiesAnalysisTest : public testing::Test {
public:
FunctionPropertiesAnalysisTest() {
createTestVocabulary(1);
MAM.registerPass([&] { return IR2VecVocabAnalysis(Vocabulary); });
MAM.registerPass([&] { return PassInstrumentationAnalysis(); });
FAM.registerPass([&] { return ModuleAnalysisManagerFunctionProxy(MAM); });
FAM.registerPass([&] { return DominatorTreeAnalysis(); });
FAM.registerPass([&] { return LoopAnalysis(); });
FAM.registerPass([&] { return PassInstrumentationAnalysis(); });
ir2vec::OpcWeight = 1.0;
ir2vec::TypeWeight = 1.0;
ir2vec::ArgWeight = 1.0;
}
private:
float OriginalOpcWeight = ir2vec::OpcWeight;
float OriginalTypeWeight = ir2vec::TypeWeight;
float OriginalArgWeight = ir2vec::ArgWeight;
void createTestVocabulary(unsigned Dim) {
llvm::SmallVector<std::string, 32> SampleEntities = {
"add", "sub", "mul", "icmp", "br",
"ret", "store", "load", "alloca", "phi",
"call", "voidTy", "floatTy", "integerTy", "functionTy",
"structTy", "arrayTy", "pointerTy", "vectorTy", "emptyTy",
"labelTy", "tokenTy", "metadataTy", "unknownTy", "function",
"pointer", "constant", "variable", "getelementptr", "invoke",
"landingpad", "resume", "catch", "cleanup"};
float EmbVal = 0.1;
// Helper lambda to add entries to the vocabulary
auto addEntry = [&](std::string key) {
Vocabulary[key] = ir2vec::Embedding(Dim, EmbVal);
EmbVal += 0.1;
};
for (auto &Name : SampleEntities)
addEntry(Name);
return;
}
protected:
std::unique_ptr<DominatorTree> DT;
std::unique_ptr<LoopInfo> LI;
FunctionAnalysisManager FAM;
ModuleAnalysisManager MAM;
ir2vec::Vocab Vocabulary;
void TearDown() override {
// Restore original IR2Vec weights
ir2vec::OpcWeight = OriginalOpcWeight;
ir2vec::TypeWeight = OriginalTypeWeight;
ir2vec::ArgWeight = OriginalArgWeight;
}
FunctionPropertiesInfo buildFPI(Function &F) {
// FunctionPropertiesInfo assumes IR2VecVocabAnalysis has been run to
// use IR2Vec.
auto VocabResult = MAM.getResult<IR2VecVocabAnalysis>(*F.getParent());
(void)VocabResult;
return FunctionPropertiesInfo::getFunctionPropertiesInfo(F, FAM);
}
@@ -125,13 +71,6 @@ protected:
return CB;
return nullptr;
}
std::unique_ptr<ir2vec::Embedder> createEmbedder(const Function &F) {
auto EmbResult =
ir2vec::Embedder::create(IR2VecKind::Symbolic, F, Vocabulary);
EXPECT_TRUE(static_cast<bool>(EmbResult));
return std::move(*EmbResult);
}
};
TEST_F(FunctionPropertiesAnalysisTest, BasicTest) {
@@ -174,8 +113,6 @@ define internal i32 @top() {
EXPECT_EQ(BranchesFeatures.StoreInstCount, 0);
EXPECT_EQ(BranchesFeatures.MaxLoopDepth, 0);
EXPECT_EQ(BranchesFeatures.TopLevelLoopCount, 0);
EXPECT_TRUE(BranchesFeatures.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*BranchesFunction)->getFunctionVector()));
Function *TopFunction = M->getFunction("top");
FunctionPropertiesInfo TopFeatures = buildFPI(*TopFunction);
@@ -183,8 +120,6 @@ define internal i32 @top() {
EXPECT_EQ(TopFeatures.BlocksReachedFromConditionalInstruction, 0);
EXPECT_EQ(TopFeatures.Uses, 0);
EXPECT_EQ(TopFeatures.DirectCallsToDefinedFunctions, 1);
EXPECT_TRUE(TopFeatures.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*TopFunction)->getFunctionVector()));
EXPECT_EQ(BranchesFeatures.LoadInstCount, 0);
EXPECT_EQ(BranchesFeatures.StoreInstCount, 0);
EXPECT_EQ(BranchesFeatures.MaxLoopDepth, 0);
@@ -224,9 +159,6 @@ define internal i32 @top() {
EXPECT_EQ(DetailedBranchesFeatures.CallReturnsPointerCount, 0);
EXPECT_EQ(DetailedBranchesFeatures.CallWithManyArgumentsCount, 0);
EXPECT_EQ(DetailedBranchesFeatures.CallWithPointerArgumentCount, 0);
EXPECT_TRUE(
DetailedBranchesFeatures.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*BranchesFunction)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -278,8 +210,6 @@ finally:
EXPECT_EQ(DetailedF1Properties.CallReturnsPointerCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithManyArgumentsCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithPointerArgumentCount, 0);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -310,8 +240,6 @@ define i32 @f2(i32 %a) {
ExpectedInitial.TotalInstructionCount = 3;
ExpectedInitial.Uses = 1;
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal = ExpectedInitial;
ExpectedFinal.DirectCallsToDefinedFunctions = 0;
@@ -324,9 +252,6 @@ define i32 @f2(i32 %a) {
auto IR = llvm::InlineFunction(*CB, IFI);
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_TRUE(FPU.finishAndTest(FAM));
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -369,8 +294,6 @@ define i32 @f2(i32 %a) {
ExpectedInitial.TotalInstructionCount = 9;
ExpectedInitial.Uses = 1;
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal = ExpectedInitial;
ExpectedFinal.DirectCallsToDefinedFunctions = 0;
@@ -384,9 +307,6 @@ define i32 @f2(i32 %a) {
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
EXPECT_TRUE(FPU.finishAndTest(FAM));
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -436,8 +356,6 @@ exit:
ExpectedInitial.TotalInstructionCount = 9;
ExpectedInitial.Uses = 1;
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal;
ExpectedFinal.BasicBlockCount = 6;
@@ -456,9 +374,6 @@ exit:
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
EXPECT_TRUE(FPU.finishAndTest(FAM));
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -507,8 +422,6 @@ declare i32 @__gxx_personality_v0(...)
EXPECT_EQ(static_cast<size_t>(FPI.BasicBlockCount), F1->size());
EXPECT_EQ(static_cast<size_t>(FPI.TotalInstructionCount),
F1->getInstructionCount());
EXPECT_TRUE(FPI.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
}
TEST_F(FunctionPropertiesAnalysisTest, InvokeUnreachableHandler) {
@@ -562,8 +475,6 @@ declare i32 @__gxx_personality_v0(...)
EXPECT_EQ(static_cast<size_t>(FPI.BasicBlockCount), F1->size() - 1);
EXPECT_EQ(static_cast<size_t>(FPI.TotalInstructionCount),
F1->getInstructionCount() - 2);
EXPECT_TRUE(FPI.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EXPECT_EQ(FPI, FunctionPropertiesInfo::getFunctionPropertiesInfo(*F1, FAM));
}
@@ -670,8 +581,6 @@ lpad:
EXPECT_EQ(static_cast<size_t>(FPI.BasicBlockCount), F1->size() - 1);
EXPECT_EQ(static_cast<size_t>(FPI.TotalInstructionCount),
F1->getInstructionCount() - 2);
EXPECT_TRUE(FPI.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EXPECT_EQ(FPI, FunctionPropertiesInfo::getFunctionPropertiesInfo(*F1, FAM));
}
@@ -728,8 +637,6 @@ lpad:
EXPECT_EQ(static_cast<size_t>(FPI.BasicBlockCount), F1->size() - 1);
EXPECT_EQ(static_cast<size_t>(FPI.TotalInstructionCount),
F1->getInstructionCount() - 2);
EXPECT_TRUE(FPI.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EXPECT_EQ(FPI, FunctionPropertiesInfo::getFunctionPropertiesInfo(*F1, FAM));
}
@@ -782,8 +689,6 @@ end:
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.MaxLoopDepth = 1;
ExpectedInitial.TopLevelLoopCount = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal = ExpectedInitial;
ExpectedFinal.BasicBlockCount = 6;
@@ -800,9 +705,6 @@ end:
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
EXPECT_TRUE(FPU.finishAndTest(FAM));
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -831,7 +733,7 @@ extra:
extra2:
br label %cond.end
cond.end: ; preds = %extra2, %cond.true
cond.end: ; preds = %cond.false, %cond.true
%cond = phi i64 [ %conv2, %cond.true ], [ %call3, %extra ]
ret i64 %cond
}
@@ -855,8 +757,6 @@ declare void @llvm.trap()
ExpectedInitial.BlocksReachedFromConditionalInstruction = 2;
ExpectedInitial.Uses = 1;
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal = ExpectedInitial;
ExpectedFinal.BasicBlockCount = 4;
@@ -872,9 +772,6 @@ declare void @llvm.trap()
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
EXPECT_TRUE(FPU.finishAndTest(FAM));
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -920,8 +817,6 @@ declare void @f3()
ExpectedInitial.BlocksReachedFromConditionalInstruction = 0;
ExpectedInitial.Uses = 1;
ExpectedInitial.DirectCallsToDefinedFunctions = 1;
ExpectedInitial.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
FunctionPropertiesInfo ExpectedFinal = ExpectedInitial;
ExpectedFinal.BasicBlockCount = 6;
@@ -937,9 +832,6 @@ declare void @f3()
EXPECT_TRUE(IR.isSuccess());
invalidate(*F1);
EXPECT_TRUE(FPU.finishAndTest(FAM));
ExpectedFinal.setFunctionEmbeddingForTest(
createEmbedder(*F1)->getFunctionVector());
EXPECT_EQ(FPI, ExpectedFinal);
}
@@ -993,8 +885,6 @@ define i64 @f1(i64 %e) {
EXPECT_EQ(DetailedF1Properties.CallReturnsPointerCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithManyArgumentsCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithPointerArgumentCount, 0);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -1020,8 +910,6 @@ declare float @llvm.cos.f32(float)
EXPECT_EQ(DetailedF1Properties.CallReturnsPointerCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithManyArgumentsCount, 0);
EXPECT_EQ(DetailedF1Properties.CallWithPointerArgumentCount, 0);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -1055,8 +943,6 @@ declare float @f5()
EXPECT_EQ(DetailedF1Properties.CallReturnsPointerCount, 1);
EXPECT_EQ(DetailedF1Properties.CallWithManyArgumentsCount, 1);
EXPECT_EQ(DetailedF1Properties.CallWithPointerArgumentCount, 1);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -1086,8 +972,6 @@ BottomBlock2:
EnableDetailedFunctionProperties.setValue(true);
FunctionPropertiesInfo DetailedF1Properties = buildFPI(*F1);
EXPECT_EQ(DetailedF1Properties.CriticalEdgeCount, 1);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}
@@ -1113,8 +997,6 @@ declare <4 x ptr> @f4()
EXPECT_EQ(DetailedF1Properties.CallReturnsVectorIntCount, 1);
EXPECT_EQ(DetailedF1Properties.CallReturnsVectorFloatCount, 1);
EXPECT_EQ(DetailedF1Properties.CallReturnsVectorPointerCount, 1);
EXPECT_TRUE(DetailedF1Properties.getFunctionEmbedding().approximatelyEquals(
createEmbedder(*F1)->getFunctionVector()));
EnableDetailedFunctionProperties.setValue(false);
}