You've already forked linux-packaging-mono
Imported Upstream version 5.18.0.167
Former-commit-id: 289509151e0fee68a1b591a20c9f109c3c789d3a
This commit is contained in:
parent
e19d552987
commit
b084638f15
73
external/llvm/tools/opt/AnalysisWrappers.cpp
vendored
73
external/llvm/tools/opt/AnalysisWrappers.cpp
vendored
@ -1,73 +0,0 @@
|
||||
//===- AnalysisWrappers.cpp - Wrappers around non-pass analyses -----------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file defines pass wrappers around LLVM analyses that don't make sense to
|
||||
// be passes. It provides a nice standard pass interface to these classes so
|
||||
// that they can be printed out by analyze.
|
||||
//
|
||||
// These classes are separated out of analyze.cpp so that it is more clear which
|
||||
// code is the integral part of the analyze tool, and which part of the code is
|
||||
// just making it so more passes are available.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/Analysis/CallGraph.h"
|
||||
#include "llvm/IR/CallSite.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/Pass.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
/// ExternalFunctionsPassedConstants - This pass prints out call sites to
|
||||
/// external functions that are called with constant arguments. This can be
|
||||
/// useful when looking for standard library functions we should constant fold
|
||||
/// or handle in alias analyses.
|
||||
struct ExternalFunctionsPassedConstants : public ModulePass {
|
||||
static char ID; // Pass ID, replacement for typeid
|
||||
ExternalFunctionsPassedConstants() : ModulePass(ID) {}
|
||||
bool runOnModule(Module &M) override {
|
||||
for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I) {
|
||||
if (!I->isDeclaration()) continue;
|
||||
|
||||
bool PrintedFn = false;
|
||||
for (User *U : I->users()) {
|
||||
Instruction *UI = dyn_cast<Instruction>(U);
|
||||
if (!UI) continue;
|
||||
|
||||
CallSite CS(cast<Value>(UI));
|
||||
if (!CS) continue;
|
||||
|
||||
for (CallSite::arg_iterator AI = CS.arg_begin(),
|
||||
E = CS.arg_end(); AI != E; ++AI) {
|
||||
if (!isa<Constant>(*AI)) continue;
|
||||
|
||||
if (!PrintedFn) {
|
||||
errs() << "Function '" << I->getName() << "':\n";
|
||||
PrintedFn = true;
|
||||
}
|
||||
errs() << *UI;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
char ExternalFunctionsPassedConstants::ID = 0;
|
||||
static RegisterPass<ExternalFunctionsPassedConstants>
|
||||
P1("print-externalfnconstants",
|
||||
"Print external fn callsites passed constants");
|
72
external/llvm/tools/opt/BreakpointPrinter.cpp
vendored
72
external/llvm/tools/opt/BreakpointPrinter.cpp
vendored
@ -1,72 +0,0 @@
|
||||
//===- BreakpointPrinter.cpp - Breakpoint location printer ----------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
///
|
||||
/// \file
|
||||
/// \brief Breakpoint location printer.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
#include "BreakpointPrinter.h"
|
||||
#include "llvm/ADT/StringSet.h"
|
||||
#include "llvm/IR/DebugInfo.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/Pass.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
|
||||
struct BreakpointPrinter : public ModulePass {
|
||||
raw_ostream &Out;
|
||||
static char ID;
|
||||
|
||||
BreakpointPrinter(raw_ostream &out) : ModulePass(ID), Out(out) {}
|
||||
|
||||
void getContextName(const DIScope *Context, std::string &N) {
|
||||
if (auto *NS = dyn_cast<DINamespace>(Context)) {
|
||||
if (!NS->getName().empty()) {
|
||||
getContextName(NS->getScope(), N);
|
||||
N = N + NS->getName().str() + "::";
|
||||
}
|
||||
} else if (auto *TY = dyn_cast<DIType>(Context)) {
|
||||
if (!TY->getName().empty()) {
|
||||
getContextName(TY->getScope().resolve(), N);
|
||||
N = N + TY->getName().str() + "::";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool runOnModule(Module &M) override {
|
||||
StringSet<> Processed;
|
||||
if (NamedMDNode *NMD = M.getNamedMetadata("llvm.dbg.sp"))
|
||||
for (unsigned i = 0, e = NMD->getNumOperands(); i != e; ++i) {
|
||||
std::string Name;
|
||||
auto *SP = cast_or_null<DISubprogram>(NMD->getOperand(i));
|
||||
if (!SP)
|
||||
continue;
|
||||
getContextName(SP->getScope().resolve(), Name);
|
||||
Name = Name + SP->getName().str();
|
||||
if (!Name.empty() && Processed.insert(Name).second) {
|
||||
Out << Name << "\n";
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char BreakpointPrinter::ID = 0;
|
||||
}
|
||||
|
||||
ModulePass *llvm::createBreakpointPrinter(raw_ostream &out) {
|
||||
return new BreakpointPrinter(out);
|
||||
}
|
25
external/llvm/tools/opt/BreakpointPrinter.h
vendored
25
external/llvm/tools/opt/BreakpointPrinter.h
vendored
@ -1,25 +0,0 @@
|
||||
//===- BreakpointPrinter.h - Breakpoint location printer ------------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
///
|
||||
/// \file
|
||||
/// \brief Breakpoint location printer.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
#ifndef LLVM_TOOLS_OPT_BREAKPOINTPRINTER_H
|
||||
#define LLVM_TOOLS_OPT_BREAKPOINTPRINTER_H
|
||||
|
||||
namespace llvm {
|
||||
|
||||
class ModulePass;
|
||||
class raw_ostream;
|
||||
|
||||
ModulePass *createBreakpointPrinter(raw_ostream &out);
|
||||
}
|
||||
|
||||
#endif // LLVM_TOOLS_OPT_BREAKPOINTPRINTER_H
|
42
external/llvm/tools/opt/CMakeLists.txt
vendored
42
external/llvm/tools/opt/CMakeLists.txt
vendored
@ -1,42 +0,0 @@
|
||||
set(LLVM_LINK_COMPONENTS
|
||||
${LLVM_TARGETS_TO_BUILD}
|
||||
Analysis
|
||||
BitWriter
|
||||
CodeGen
|
||||
Core
|
||||
Coroutines
|
||||
IPO
|
||||
IRReader
|
||||
InstCombine
|
||||
Instrumentation
|
||||
MC
|
||||
ObjCARCOpts
|
||||
ScalarOpts
|
||||
Support
|
||||
Target
|
||||
TransformUtils
|
||||
Vectorize
|
||||
Passes
|
||||
)
|
||||
|
||||
# Support plugins.
|
||||
set(LLVM_NO_DEAD_STRIP 1)
|
||||
|
||||
add_llvm_tool(opt
|
||||
AnalysisWrappers.cpp
|
||||
BreakpointPrinter.cpp
|
||||
Debugify.cpp
|
||||
GraphPrinters.cpp
|
||||
NewPMDriver.cpp
|
||||
PassPrinters.cpp
|
||||
PrintSCC.cpp
|
||||
opt.cpp
|
||||
|
||||
DEPENDS
|
||||
intrinsics_gen
|
||||
)
|
||||
export_executable_symbols(opt)
|
||||
|
||||
if(WITH_POLLY AND LINK_POLLY_INTO_TOOLS)
|
||||
target_link_libraries(opt PRIVATE Polly)
|
||||
endif(WITH_POLLY AND LINK_POLLY_INTO_TOOLS)
|
212
external/llvm/tools/opt/Debugify.cpp
vendored
212
external/llvm/tools/opt/Debugify.cpp
vendored
@ -1,212 +0,0 @@
|
||||
//===- Debugify.cpp - Attach synthetic debug info to everything -----------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
///
|
||||
/// \file This pass attaches synthetic debug info to everything. It can be used
|
||||
/// to create targeted tests for debug info preservation.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/BitVector.h"
|
||||
#include "llvm/ADT/StringExtras.h"
|
||||
#include "llvm/IR/BasicBlock.h"
|
||||
#include "llvm/IR/Constants.h"
|
||||
#include "llvm/IR/DIBuilder.h"
|
||||
#include "llvm/IR/DebugInfo.h"
|
||||
#include "llvm/IR/Function.h"
|
||||
#include "llvm/IR/GlobalVariable.h"
|
||||
#include "llvm/IR/InstIterator.h"
|
||||
#include "llvm/IR/Instruction.h"
|
||||
#include "llvm/IR/Instructions.h"
|
||||
#include "llvm/IR/IntrinsicInst.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/IR/Type.h"
|
||||
#include "llvm/Pass.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include "llvm/Transforms/IPO.h"
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
|
||||
bool applyDebugifyMetadata(Module &M) {
|
||||
// Skip modules with debug info.
|
||||
if (M.getNamedMetadata("llvm.dbg.cu")) {
|
||||
errs() << "Debugify: Skipping module with debug info\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
DIBuilder DIB(M);
|
||||
LLVMContext &Ctx = M.getContext();
|
||||
|
||||
// Get a DIType which corresponds to Ty.
|
||||
DenseMap<uint64_t, DIType *> TypeCache;
|
||||
auto getCachedDIType = [&](Type *Ty) -> DIType * {
|
||||
uint64_t Size = M.getDataLayout().getTypeAllocSizeInBits(Ty);
|
||||
DIType *&DTy = TypeCache[Size];
|
||||
if (!DTy) {
|
||||
std::string Name = "ty" + utostr(Size);
|
||||
DTy = DIB.createBasicType(Name, Size, dwarf::DW_ATE_unsigned);
|
||||
}
|
||||
return DTy;
|
||||
};
|
||||
|
||||
unsigned NextLine = 1;
|
||||
unsigned NextVar = 1;
|
||||
auto File = DIB.createFile(M.getName(), "/");
|
||||
auto CU =
|
||||
DIB.createCompileUnit(dwarf::DW_LANG_C, DIB.createFile(M.getName(), "/"),
|
||||
"debugify", /*isOptimized=*/true, "", 0);
|
||||
|
||||
// Visit each instruction.
|
||||
for (Function &F : M) {
|
||||
if (F.isDeclaration())
|
||||
continue;
|
||||
|
||||
auto SPType = DIB.createSubroutineType(DIB.getOrCreateTypeArray(None));
|
||||
bool IsLocalToUnit = F.hasPrivateLinkage() || F.hasInternalLinkage();
|
||||
auto SP =
|
||||
DIB.createFunction(CU, F.getName(), F.getName(), File, NextLine, SPType,
|
||||
IsLocalToUnit, F.hasExactDefinition(), NextLine,
|
||||
DINode::FlagZero, /*isOptimized=*/true);
|
||||
F.setSubprogram(SP);
|
||||
for (BasicBlock &BB : F) {
|
||||
// Attach debug locations.
|
||||
for (Instruction &I : BB)
|
||||
I.setDebugLoc(DILocation::get(Ctx, NextLine++, 1, SP));
|
||||
|
||||
// Attach debug values.
|
||||
for (Instruction &I : BB) {
|
||||
// Skip void-valued instructions.
|
||||
if (I.getType()->isVoidTy())
|
||||
continue;
|
||||
|
||||
// Skip the terminator instruction and any just-inserted intrinsics.
|
||||
if (isa<TerminatorInst>(&I) || isa<DbgValueInst>(&I))
|
||||
break;
|
||||
|
||||
std::string Name = utostr(NextVar++);
|
||||
const DILocation *Loc = I.getDebugLoc().get();
|
||||
auto LocalVar = DIB.createAutoVariable(SP, Name, File, Loc->getLine(),
|
||||
getCachedDIType(I.getType()),
|
||||
/*AlwaysPreserve=*/true);
|
||||
DIB.insertDbgValueIntrinsic(&I, LocalVar, DIB.createExpression(), Loc,
|
||||
BB.getTerminator());
|
||||
}
|
||||
}
|
||||
DIB.finalizeSubprogram(SP);
|
||||
}
|
||||
DIB.finalize();
|
||||
|
||||
// Track the number of distinct lines and variables.
|
||||
NamedMDNode *NMD = M.getOrInsertNamedMetadata("llvm.debugify");
|
||||
auto *IntTy = Type::getInt32Ty(Ctx);
|
||||
auto addDebugifyOperand = [&](unsigned N) {
|
||||
NMD->addOperand(MDNode::get(
|
||||
Ctx, ValueAsMetadata::getConstant(ConstantInt::get(IntTy, N))));
|
||||
};
|
||||
addDebugifyOperand(NextLine - 1); // Original number of lines.
|
||||
addDebugifyOperand(NextVar - 1); // Original number of variables.
|
||||
return true;
|
||||
}
|
||||
|
||||
void checkDebugifyMetadata(Module &M) {
|
||||
// Skip modules without debugify metadata.
|
||||
NamedMDNode *NMD = M.getNamedMetadata("llvm.debugify");
|
||||
if (!NMD)
|
||||
return;
|
||||
|
||||
auto getDebugifyOperand = [&](unsigned Idx) -> unsigned {
|
||||
return mdconst::extract<ConstantInt>(NMD->getOperand(Idx)->getOperand(0))
|
||||
->getZExtValue();
|
||||
};
|
||||
unsigned OriginalNumLines = getDebugifyOperand(0);
|
||||
unsigned OriginalNumVars = getDebugifyOperand(1);
|
||||
bool HasErrors = false;
|
||||
|
||||
// Find missing lines.
|
||||
BitVector MissingLines{OriginalNumLines, true};
|
||||
for (Function &F : M) {
|
||||
for (Instruction &I : instructions(F)) {
|
||||
if (isa<DbgValueInst>(&I))
|
||||
continue;
|
||||
|
||||
auto DL = I.getDebugLoc();
|
||||
if (DL) {
|
||||
MissingLines.reset(DL.getLine() - 1);
|
||||
continue;
|
||||
}
|
||||
|
||||
outs() << "ERROR: Instruction with empty DebugLoc -- ";
|
||||
I.print(outs());
|
||||
outs() << "\n";
|
||||
HasErrors = true;
|
||||
}
|
||||
}
|
||||
for (unsigned Idx : MissingLines.set_bits())
|
||||
outs() << "WARNING: Missing line " << Idx + 1 << "\n";
|
||||
|
||||
// Find missing variables.
|
||||
BitVector MissingVars{OriginalNumVars, true};
|
||||
for (Function &F : M) {
|
||||
for (Instruction &I : instructions(F)) {
|
||||
auto *DVI = dyn_cast<DbgValueInst>(&I);
|
||||
if (!DVI)
|
||||
continue;
|
||||
|
||||
unsigned Var = ~0U;
|
||||
(void)to_integer(DVI->getVariable()->getName(), Var, 10);
|
||||
assert(Var <= OriginalNumVars && "Unexpected name for DILocalVariable");
|
||||
MissingVars.reset(Var - 1);
|
||||
}
|
||||
}
|
||||
for (unsigned Idx : MissingVars.set_bits())
|
||||
outs() << "ERROR: Missing variable " << Idx + 1 << "\n";
|
||||
HasErrors |= MissingVars.count() > 0;
|
||||
|
||||
outs() << "CheckDebugify: " << (HasErrors ? "FAIL" : "PASS") << "\n";
|
||||
}
|
||||
|
||||
/// Attach synthetic debug info to everything.
|
||||
struct DebugifyPass : public ModulePass {
|
||||
bool runOnModule(Module &M) override { return applyDebugifyMetadata(M); }
|
||||
|
||||
DebugifyPass() : ModulePass(ID) {}
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
|
||||
static char ID; // Pass identification.
|
||||
};
|
||||
|
||||
/// Check debug info inserted by -debugify for completeness.
|
||||
struct CheckDebugifyPass : public ModulePass {
|
||||
bool runOnModule(Module &M) override {
|
||||
checkDebugifyMetadata(M);
|
||||
return false;
|
||||
}
|
||||
|
||||
CheckDebugifyPass() : ModulePass(ID) {}
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
|
||||
static char ID; // Pass identification.
|
||||
};
|
||||
|
||||
} // end anonymous namespace
|
||||
|
||||
char DebugifyPass::ID = 0;
|
||||
static RegisterPass<DebugifyPass> X("debugify",
|
||||
"Attach debug info to everything");
|
||||
|
||||
char CheckDebugifyPass::ID = 0;
|
||||
static RegisterPass<CheckDebugifyPass> Y("check-debugify",
|
||||
"Check debug info from -debugify");
|
46
external/llvm/tools/opt/GraphPrinters.cpp
vendored
46
external/llvm/tools/opt/GraphPrinters.cpp
vendored
@ -1,46 +0,0 @@
|
||||
//===- GraphPrinters.cpp - DOT printers for various graph types -----------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file defines several printers for various different types of graphs used
|
||||
// by the LLVM infrastructure. It uses the generic graph interface to convert
|
||||
// the graph into a .dot graph. These graphs can then be processed with the
|
||||
// "dot" tool to convert them to postscript or some other suitable format.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/IR/Dominators.h"
|
||||
#include "llvm/Pass.h"
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// DomInfoPrinter Pass
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
namespace {
|
||||
class DomInfoPrinter : public FunctionPass {
|
||||
public:
|
||||
static char ID; // Pass identification, replacement for typeid
|
||||
DomInfoPrinter() : FunctionPass(ID) {}
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
AU.addRequired<DominatorTreeWrapperPass>();
|
||||
}
|
||||
|
||||
bool runOnFunction(Function &F) override {
|
||||
getAnalysis<DominatorTreeWrapperPass>().print(dbgs());
|
||||
return false;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
char DomInfoPrinter::ID = 0;
|
||||
static RegisterPass<DomInfoPrinter>
|
||||
DIP("print-dom-info", "Dominator Info Printer", true, true);
|
33
external/llvm/tools/opt/LLVMBuild.txt
vendored
33
external/llvm/tools/opt/LLVMBuild.txt
vendored
@ -1,33 +0,0 @@
|
||||
;===- ./tools/opt/LLVMBuild.txt --------------------------------*- Conf -*--===;
|
||||
;
|
||||
; The LLVM Compiler Infrastructure
|
||||
;
|
||||
; This file is distributed under the University of Illinois Open Source
|
||||
; License. See LICENSE.TXT for details.
|
||||
;
|
||||
;===------------------------------------------------------------------------===;
|
||||
;
|
||||
; This is an LLVMBuild description file for the components in this subdirectory.
|
||||
;
|
||||
; For more information on the LLVMBuild system, please see:
|
||||
;
|
||||
; http://llvm.org/docs/LLVMBuild.html
|
||||
;
|
||||
;===------------------------------------------------------------------------===;
|
||||
|
||||
[component_0]
|
||||
type = Tool
|
||||
name = opt
|
||||
parent = Tools
|
||||
required_libraries =
|
||||
AsmParser
|
||||
BitReader
|
||||
BitWriter
|
||||
CodeGen
|
||||
IRReader
|
||||
IPO
|
||||
Instrumentation
|
||||
Scalar
|
||||
ObjCARC
|
||||
Passes
|
||||
all-targets
|
274
external/llvm/tools/opt/NewPMDriver.cpp
vendored
274
external/llvm/tools/opt/NewPMDriver.cpp
vendored
@ -1,274 +0,0 @@
|
||||
//===- NewPMDriver.cpp - Driver for opt with new PM -----------------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
/// \file
|
||||
///
|
||||
/// This file is just a split of the code that logically belongs in opt.cpp but
|
||||
/// that includes the new pass manager headers.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "NewPMDriver.h"
|
||||
#include "llvm/ADT/StringRef.h"
|
||||
#include "llvm/Analysis/AliasAnalysis.h"
|
||||
#include "llvm/Analysis/CGSCCPassManager.h"
|
||||
#include "llvm/Bitcode/BitcodeWriterPass.h"
|
||||
#include "llvm/Config/config.h"
|
||||
#include "llvm/IR/Dominators.h"
|
||||
#include "llvm/IR/IRPrintingPasses.h"
|
||||
#include "llvm/IR/LLVMContext.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/IR/PassManager.h"
|
||||
#include "llvm/IR/Verifier.h"
|
||||
#include "llvm/Passes/PassBuilder.h"
|
||||
#include "llvm/Support/CommandLine.h"
|
||||
#include "llvm/Support/ErrorHandling.h"
|
||||
#include "llvm/Support/ToolOutputFile.h"
|
||||
#include "llvm/Target/TargetMachine.h"
|
||||
#include "llvm/Transforms/IPO/ThinLTOBitcodeWriter.h"
|
||||
#include "llvm/Transforms/Scalar/LoopPassManager.h"
|
||||
|
||||
using namespace llvm;
|
||||
using namespace opt_tool;
|
||||
|
||||
static cl::opt<bool>
|
||||
DebugPM("debug-pass-manager", cl::Hidden,
|
||||
cl::desc("Print pass management debugging information"));
|
||||
|
||||
// This flag specifies a textual description of the alias analysis pipeline to
|
||||
// use when querying for aliasing information. It only works in concert with
|
||||
// the "passes" flag above.
|
||||
static cl::opt<std::string>
|
||||
AAPipeline("aa-pipeline",
|
||||
cl::desc("A textual description of the alias analysis "
|
||||
"pipeline for handling managed aliasing queries"),
|
||||
cl::Hidden);
|
||||
|
||||
/// {{@ These options accept textual pipeline descriptions which will be
|
||||
/// inserted into default pipelines at the respective extension points
|
||||
static cl::opt<std::string> PeepholeEPPipeline(
|
||||
"passes-ep-peephole",
|
||||
cl::desc("A textual description of the function pass pipeline inserted at "
|
||||
"the Peephole extension points into default pipelines"),
|
||||
cl::Hidden);
|
||||
static cl::opt<std::string> LateLoopOptimizationsEPPipeline(
|
||||
"passes-ep-late-loop-optimizations",
|
||||
cl::desc(
|
||||
"A textual description of the loop pass pipeline inserted at "
|
||||
"the LateLoopOptimizations extension point into default pipelines"),
|
||||
cl::Hidden);
|
||||
static cl::opt<std::string> LoopOptimizerEndEPPipeline(
|
||||
"passes-ep-loop-optimizer-end",
|
||||
cl::desc("A textual description of the loop pass pipeline inserted at "
|
||||
"the LoopOptimizerEnd extension point into default pipelines"),
|
||||
cl::Hidden);
|
||||
static cl::opt<std::string> ScalarOptimizerLateEPPipeline(
|
||||
"passes-ep-scalar-optimizer-late",
|
||||
cl::desc("A textual description of the function pass pipeline inserted at "
|
||||
"the ScalarOptimizerLate extension point into default pipelines"),
|
||||
cl::Hidden);
|
||||
static cl::opt<std::string> CGSCCOptimizerLateEPPipeline(
|
||||
"passes-ep-cgscc-optimizer-late",
|
||||
cl::desc("A textual description of the cgscc pass pipeline inserted at "
|
||||
"the CGSCCOptimizerLate extension point into default pipelines"),
|
||||
cl::Hidden);
|
||||
static cl::opt<std::string> VectorizerStartEPPipeline(
|
||||
"passes-ep-vectorizer-start",
|
||||
cl::desc("A textual description of the function pass pipeline inserted at "
|
||||
"the VectorizerStart extension point into default pipelines"),
|
||||
cl::Hidden);
|
||||
enum PGOKind { NoPGO, InstrGen, InstrUse, SampleUse };
|
||||
static cl::opt<PGOKind> PGOKindFlag(
|
||||
"pgo-kind", cl::init(NoPGO), cl::Hidden,
|
||||
cl::desc("The kind of profile guided optimization"),
|
||||
cl::values(clEnumValN(NoPGO, "nopgo", "Do not use PGO."),
|
||||
clEnumValN(InstrGen, "new-pm-pgo-instr-gen-pipeline",
|
||||
"Instrument the IR to generate profile."),
|
||||
clEnumValN(InstrUse, "new-pm-pgo-instr-use-pipeline",
|
||||
"Use instrumented profile to guide PGO."),
|
||||
clEnumValN(SampleUse, "new-pm-pgo-sample-use-pipeline",
|
||||
"Use sampled profile to guide PGO.")));
|
||||
static cl::opt<std::string> ProfileFile(
|
||||
"profile-file", cl::desc("Path to the profile."), cl::Hidden);
|
||||
static cl::opt<bool> DebugInfoForProfiling(
|
||||
"new-pm-debug-info-for-profiling", cl::init(false), cl::Hidden,
|
||||
cl::desc("Emit special debug info to enable PGO profile generation."));
|
||||
/// @}}
|
||||
|
||||
template <typename PassManagerT>
|
||||
bool tryParsePipelineText(PassBuilder &PB, StringRef PipelineText) {
|
||||
if (PipelineText.empty())
|
||||
return false;
|
||||
|
||||
// Verify the pipeline is parseable:
|
||||
PassManagerT PM;
|
||||
if (PB.parsePassPipeline(PM, PipelineText))
|
||||
return true;
|
||||
|
||||
errs() << "Could not parse pipeline '" << PipelineText
|
||||
<< "'. I'm going to igore it.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
/// If one of the EPPipeline command line options was given, register callbacks
|
||||
/// for parsing and inserting the given pipeline
|
||||
static void registerEPCallbacks(PassBuilder &PB, bool VerifyEachPass,
|
||||
bool DebugLogging) {
|
||||
if (tryParsePipelineText<FunctionPassManager>(PB, PeepholeEPPipeline))
|
||||
PB.registerPeepholeEPCallback([&PB, VerifyEachPass, DebugLogging](
|
||||
FunctionPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, PeepholeEPPipeline, VerifyEachPass,
|
||||
DebugLogging);
|
||||
});
|
||||
if (tryParsePipelineText<LoopPassManager>(PB,
|
||||
LateLoopOptimizationsEPPipeline))
|
||||
PB.registerLateLoopOptimizationsEPCallback(
|
||||
[&PB, VerifyEachPass, DebugLogging](
|
||||
LoopPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, LateLoopOptimizationsEPPipeline,
|
||||
VerifyEachPass, DebugLogging);
|
||||
});
|
||||
if (tryParsePipelineText<LoopPassManager>(PB, LoopOptimizerEndEPPipeline))
|
||||
PB.registerLoopOptimizerEndEPCallback([&PB, VerifyEachPass, DebugLogging](
|
||||
LoopPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, LoopOptimizerEndEPPipeline, VerifyEachPass,
|
||||
DebugLogging);
|
||||
});
|
||||
if (tryParsePipelineText<FunctionPassManager>(PB,
|
||||
ScalarOptimizerLateEPPipeline))
|
||||
PB.registerScalarOptimizerLateEPCallback(
|
||||
[&PB, VerifyEachPass, DebugLogging](
|
||||
FunctionPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, ScalarOptimizerLateEPPipeline,
|
||||
VerifyEachPass, DebugLogging);
|
||||
});
|
||||
if (tryParsePipelineText<CGSCCPassManager>(PB, CGSCCOptimizerLateEPPipeline))
|
||||
PB.registerCGSCCOptimizerLateEPCallback([&PB, VerifyEachPass, DebugLogging](
|
||||
CGSCCPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, CGSCCOptimizerLateEPPipeline, VerifyEachPass,
|
||||
DebugLogging);
|
||||
});
|
||||
if (tryParsePipelineText<FunctionPassManager>(PB, VectorizerStartEPPipeline))
|
||||
PB.registerVectorizerStartEPCallback([&PB, VerifyEachPass, DebugLogging](
|
||||
FunctionPassManager &PM, PassBuilder::OptimizationLevel Level) {
|
||||
PB.parsePassPipeline(PM, VectorizerStartEPPipeline, VerifyEachPass,
|
||||
DebugLogging);
|
||||
});
|
||||
}
|
||||
|
||||
#ifdef LINK_POLLY_INTO_TOOLS
|
||||
namespace polly {
|
||||
void RegisterPollyPasses(PassBuilder &);
|
||||
}
|
||||
#endif
|
||||
|
||||
bool llvm::runPassPipeline(StringRef Arg0, Module &M, TargetMachine *TM,
|
||||
ToolOutputFile *Out, ToolOutputFile *ThinLTOLinkOut,
|
||||
ToolOutputFile *OptRemarkFile,
|
||||
StringRef PassPipeline, OutputKind OK,
|
||||
VerifierKind VK,
|
||||
bool ShouldPreserveAssemblyUseListOrder,
|
||||
bool ShouldPreserveBitcodeUseListOrder,
|
||||
bool EmitSummaryIndex, bool EmitModuleHash) {
|
||||
bool VerifyEachPass = VK == VK_VerifyEachPass;
|
||||
|
||||
Optional<PGOOptions> P;
|
||||
switch (PGOKindFlag) {
|
||||
case InstrGen:
|
||||
P = PGOOptions(ProfileFile, "", "", true);
|
||||
break;
|
||||
case InstrUse:
|
||||
P = PGOOptions("", ProfileFile, "", false);
|
||||
break;
|
||||
case SampleUse:
|
||||
P = PGOOptions("", "", ProfileFile, false);
|
||||
break;
|
||||
case NoPGO:
|
||||
if (DebugInfoForProfiling)
|
||||
P = PGOOptions("", "", "", false, true);
|
||||
else
|
||||
P = None;
|
||||
}
|
||||
PassBuilder PB(TM, P);
|
||||
registerEPCallbacks(PB, VerifyEachPass, DebugPM);
|
||||
|
||||
#ifdef LINK_POLLY_INTO_TOOLS
|
||||
polly::RegisterPollyPasses(PB);
|
||||
#endif
|
||||
|
||||
// Specially handle the alias analysis manager so that we can register
|
||||
// a custom pipeline of AA passes with it.
|
||||
AAManager AA;
|
||||
if (!PB.parseAAPipeline(AA, AAPipeline)) {
|
||||
errs() << Arg0 << ": unable to parse AA pipeline description.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
LoopAnalysisManager LAM(DebugPM);
|
||||
FunctionAnalysisManager FAM(DebugPM);
|
||||
CGSCCAnalysisManager CGAM(DebugPM);
|
||||
ModuleAnalysisManager MAM(DebugPM);
|
||||
|
||||
// Register the AA manager first so that our version is the one used.
|
||||
FAM.registerPass([&] { return std::move(AA); });
|
||||
|
||||
// Register all the basic analyses with the managers.
|
||||
PB.registerModuleAnalyses(MAM);
|
||||
PB.registerCGSCCAnalyses(CGAM);
|
||||
PB.registerFunctionAnalyses(FAM);
|
||||
PB.registerLoopAnalyses(LAM);
|
||||
PB.crossRegisterProxies(LAM, FAM, CGAM, MAM);
|
||||
|
||||
ModulePassManager MPM(DebugPM);
|
||||
if (VK > VK_NoVerifier)
|
||||
MPM.addPass(VerifierPass());
|
||||
|
||||
if (!PB.parsePassPipeline(MPM, PassPipeline, VerifyEachPass, DebugPM)) {
|
||||
errs() << Arg0 << ": unable to parse pass pipeline description.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (VK > VK_NoVerifier)
|
||||
MPM.addPass(VerifierPass());
|
||||
|
||||
// Add any relevant output pass at the end of the pipeline.
|
||||
switch (OK) {
|
||||
case OK_NoOutput:
|
||||
break; // No output pass needed.
|
||||
case OK_OutputAssembly:
|
||||
MPM.addPass(
|
||||
PrintModulePass(Out->os(), "", ShouldPreserveAssemblyUseListOrder));
|
||||
break;
|
||||
case OK_OutputBitcode:
|
||||
MPM.addPass(BitcodeWriterPass(Out->os(), ShouldPreserveBitcodeUseListOrder,
|
||||
EmitSummaryIndex, EmitModuleHash));
|
||||
break;
|
||||
case OK_OutputThinLTOBitcode:
|
||||
MPM.addPass(ThinLTOBitcodeWriterPass(
|
||||
Out->os(), ThinLTOLinkOut ? &ThinLTOLinkOut->os() : nullptr));
|
||||
break;
|
||||
}
|
||||
|
||||
// Before executing passes, print the final values of the LLVM options.
|
||||
cl::PrintOptionValues();
|
||||
|
||||
// Now that we have all of the passes ready, run them.
|
||||
MPM.run(M, MAM);
|
||||
|
||||
// Declare success.
|
||||
if (OK != OK_NoOutput) {
|
||||
Out->keep();
|
||||
if (OK == OK_OutputThinLTOBitcode && ThinLTOLinkOut)
|
||||
ThinLTOLinkOut->keep();
|
||||
}
|
||||
|
||||
if (OptRemarkFile)
|
||||
OptRemarkFile->keep();
|
||||
|
||||
return true;
|
||||
}
|
63
external/llvm/tools/opt/NewPMDriver.h
vendored
63
external/llvm/tools/opt/NewPMDriver.h
vendored
@ -1,63 +0,0 @@
|
||||
//===- NewPMDriver.h - Function to drive opt with the new PM ----*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
/// \file
|
||||
///
|
||||
/// A single function which is called to drive the opt behavior for the new
|
||||
/// PassManager.
|
||||
///
|
||||
/// This is only in a separate TU with a header to avoid including all of the
|
||||
/// old pass manager headers and the new pass manager headers into the same
|
||||
/// file. Eventually all of the routines here will get folded back into
|
||||
/// opt.cpp.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_TOOLS_OPT_NEWPMDRIVER_H
|
||||
#define LLVM_TOOLS_OPT_NEWPMDRIVER_H
|
||||
|
||||
namespace llvm {
|
||||
class StringRef;
|
||||
class LLVMContext;
|
||||
class Module;
|
||||
class TargetMachine;
|
||||
class ToolOutputFile;
|
||||
|
||||
namespace opt_tool {
|
||||
enum OutputKind {
|
||||
OK_NoOutput,
|
||||
OK_OutputAssembly,
|
||||
OK_OutputBitcode,
|
||||
OK_OutputThinLTOBitcode,
|
||||
};
|
||||
enum VerifierKind {
|
||||
VK_NoVerifier,
|
||||
VK_VerifyInAndOut,
|
||||
VK_VerifyEachPass
|
||||
};
|
||||
}
|
||||
|
||||
/// \brief Driver function to run the new pass manager over a module.
|
||||
///
|
||||
/// This function only exists factored away from opt.cpp in order to prevent
|
||||
/// inclusion of the new pass manager headers and the old headers into the same
|
||||
/// file. It's interface is consequentially somewhat ad-hoc, but will go away
|
||||
/// when the transition finishes.
|
||||
///
|
||||
/// ThinLTOLinkOut is only used when OK is OK_OutputThinLTOBitcode, and can be
|
||||
/// nullptr.
|
||||
bool runPassPipeline(StringRef Arg0, Module &M, TargetMachine *TM,
|
||||
ToolOutputFile *Out, ToolOutputFile *ThinLinkOut,
|
||||
ToolOutputFile *OptRemarkFile, StringRef PassPipeline,
|
||||
opt_tool::OutputKind OK, opt_tool::VerifierKind VK,
|
||||
bool ShouldPreserveAssemblyUseListOrder,
|
||||
bool ShouldPreserveBitcodeUseListOrder,
|
||||
bool EmitSummaryIndex, bool EmitModuleHash);
|
||||
}
|
||||
|
||||
#endif
|
267
external/llvm/tools/opt/PassPrinters.cpp
vendored
267
external/llvm/tools/opt/PassPrinters.cpp
vendored
@ -1,267 +0,0 @@
|
||||
//===- PassPrinters.cpp - Utilities to print analysis info for passes -----===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
///
|
||||
/// \file
|
||||
/// \brief Utilities to print analysis info for various kinds of passes.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "PassPrinters.h"
|
||||
#include "llvm/Analysis/CallGraph.h"
|
||||
#include "llvm/Analysis/CallGraphSCCPass.h"
|
||||
#include "llvm/Analysis/LoopInfo.h"
|
||||
#include "llvm/Analysis/LoopPass.h"
|
||||
#include "llvm/Analysis/RegionInfo.h"
|
||||
#include "llvm/Analysis/RegionPass.h"
|
||||
#include "llvm/IR/BasicBlock.h"
|
||||
#include "llvm/IR/Function.h"
|
||||
#include "llvm/Pass.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include <string>
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
|
||||
struct FunctionPassPrinter : public FunctionPass {
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
static char ID;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
FunctionPassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: FunctionPass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "FunctionPass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnFunction(Function &F) override {
|
||||
if (!QuietPass)
|
||||
Out << "Printing analysis '" << PassToPrint->getPassName()
|
||||
<< "' for function '" << F.getName() << "':\n";
|
||||
|
||||
// Get and print pass...
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo()).print(Out, F.getParent());
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char FunctionPassPrinter::ID = 0;
|
||||
|
||||
struct CallGraphSCCPassPrinter : public CallGraphSCCPass {
|
||||
static char ID;
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
CallGraphSCCPassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: CallGraphSCCPass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "CallGraphSCCPass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnSCC(CallGraphSCC &SCC) override {
|
||||
if (!QuietPass)
|
||||
Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n";
|
||||
|
||||
// Get and print pass...
|
||||
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I) {
|
||||
Function *F = (*I)->getFunction();
|
||||
if (F)
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo())
|
||||
.print(Out, F->getParent());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char CallGraphSCCPassPrinter::ID = 0;
|
||||
|
||||
struct ModulePassPrinter : public ModulePass {
|
||||
static char ID;
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
ModulePassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: ModulePass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "ModulePass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnModule(Module &M) override {
|
||||
if (!QuietPass)
|
||||
Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n";
|
||||
|
||||
// Get and print pass...
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo()).print(Out, &M);
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char ModulePassPrinter::ID = 0;
|
||||
|
||||
struct LoopPassPrinter : public LoopPass {
|
||||
static char ID;
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
LoopPassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: LoopPass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "LoopPass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnLoop(Loop *L, LPPassManager &LPM) override {
|
||||
if (!QuietPass)
|
||||
Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n";
|
||||
|
||||
// Get and print pass...
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo())
|
||||
.print(Out, L->getHeader()->getParent()->getParent());
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char LoopPassPrinter::ID = 0;
|
||||
|
||||
struct RegionPassPrinter : public RegionPass {
|
||||
static char ID;
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
RegionPassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: RegionPass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "RegionPass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnRegion(Region *R, RGPassManager &RGM) override {
|
||||
if (!QuietPass) {
|
||||
Out << "Printing analysis '" << PassToPrint->getPassName() << "' for "
|
||||
<< "region: '" << R->getNameStr() << "' in function '"
|
||||
<< R->getEntry()->getParent()->getName() << "':\n";
|
||||
}
|
||||
// Get and print pass...
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo())
|
||||
.print(Out, R->getEntry()->getParent()->getParent());
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char RegionPassPrinter::ID = 0;
|
||||
|
||||
struct BasicBlockPassPrinter : public BasicBlockPass {
|
||||
const PassInfo *PassToPrint;
|
||||
raw_ostream &Out;
|
||||
static char ID;
|
||||
std::string PassName;
|
||||
bool QuietPass;
|
||||
|
||||
BasicBlockPassPrinter(const PassInfo *PI, raw_ostream &out, bool Quiet)
|
||||
: BasicBlockPass(ID), PassToPrint(PI), Out(out), QuietPass(Quiet) {
|
||||
std::string PassToPrintName = PassToPrint->getPassName();
|
||||
PassName = "BasicBlockPass Printer: " + PassToPrintName;
|
||||
}
|
||||
|
||||
bool runOnBasicBlock(BasicBlock &BB) override {
|
||||
if (!QuietPass)
|
||||
Out << "Printing Analysis info for BasicBlock '" << BB.getName()
|
||||
<< "': Pass " << PassToPrint->getPassName() << ":\n";
|
||||
|
||||
// Get and print pass...
|
||||
getAnalysisID<Pass>(PassToPrint->getTypeInfo())
|
||||
.print(Out, BB.getParent()->getParent());
|
||||
return false;
|
||||
}
|
||||
|
||||
StringRef getPassName() const override { return PassName; }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.addRequiredID(PassToPrint->getTypeInfo());
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
char BasicBlockPassPrinter::ID = 0;
|
||||
|
||||
} // end anonymous namespace
|
||||
|
||||
FunctionPass *llvm::createFunctionPassPrinter(const PassInfo *PI,
|
||||
raw_ostream &OS, bool Quiet) {
|
||||
return new FunctionPassPrinter(PI, OS, Quiet);
|
||||
}
|
||||
|
||||
CallGraphSCCPass *llvm::createCallGraphPassPrinter(const PassInfo *PI,
|
||||
raw_ostream &OS,
|
||||
bool Quiet) {
|
||||
return new CallGraphSCCPassPrinter(PI, OS, Quiet);
|
||||
}
|
||||
|
||||
ModulePass *llvm::createModulePassPrinter(const PassInfo *PI, raw_ostream &OS,
|
||||
bool Quiet) {
|
||||
return new ModulePassPrinter(PI, OS, Quiet);
|
||||
}
|
||||
|
||||
LoopPass *llvm::createLoopPassPrinter(const PassInfo *PI, raw_ostream &OS,
|
||||
bool Quiet) {
|
||||
return new LoopPassPrinter(PI, OS, Quiet);
|
||||
}
|
||||
|
||||
RegionPass *llvm::createRegionPassPrinter(const PassInfo *PI, raw_ostream &OS,
|
||||
bool Quiet) {
|
||||
return new RegionPassPrinter(PI, OS, Quiet);
|
||||
}
|
||||
|
||||
BasicBlockPass *llvm::createBasicBlockPassPrinter(const PassInfo *PI,
|
||||
raw_ostream &OS, bool Quiet) {
|
||||
return new BasicBlockPassPrinter(PI, OS, Quiet);
|
||||
}
|
49
external/llvm/tools/opt/PassPrinters.h
vendored
49
external/llvm/tools/opt/PassPrinters.h
vendored
@ -1,49 +0,0 @@
|
||||
//=- PassPrinters.h - Utilities to print analysis info for passes -*- C++ -*-=//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
///
|
||||
/// \file
|
||||
/// \brief Utilities to print analysis info for various kinds of passes.
|
||||
///
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_TOOLS_OPT_PASSPRINTERS_H
|
||||
#define LLVM_TOOLS_OPT_PASSPRINTERS_H
|
||||
|
||||
namespace llvm {
|
||||
|
||||
class BasicBlockPass;
|
||||
class CallGraphSCCPass;
|
||||
class FunctionPass;
|
||||
class ModulePass;
|
||||
class LoopPass;
|
||||
class PassInfo;
|
||||
class raw_ostream;
|
||||
class RegionPass;
|
||||
|
||||
FunctionPass *createFunctionPassPrinter(const PassInfo *PI, raw_ostream &out,
|
||||
bool Quiet);
|
||||
|
||||
CallGraphSCCPass *createCallGraphPassPrinter(const PassInfo *PI,
|
||||
raw_ostream &out, bool Quiet);
|
||||
|
||||
ModulePass *createModulePassPrinter(const PassInfo *PI, raw_ostream &out,
|
||||
bool Quiet);
|
||||
|
||||
LoopPass *createLoopPassPrinter(const PassInfo *PI, raw_ostream &out,
|
||||
bool Quiet);
|
||||
|
||||
RegionPass *createRegionPassPrinter(const PassInfo *PI, raw_ostream &out,
|
||||
bool Quiet);
|
||||
|
||||
BasicBlockPass *createBasicBlockPassPrinter(const PassInfo *PI,
|
||||
raw_ostream &out, bool Quiet);
|
||||
|
||||
} // end namespace llvm
|
||||
|
||||
#endif // LLVM_TOOLS_OPT_PASSPRINTERS_H
|
111
external/llvm/tools/opt/PrintSCC.cpp
vendored
111
external/llvm/tools/opt/PrintSCC.cpp
vendored
@ -1,111 +0,0 @@
|
||||
//===- PrintSCC.cpp - Enumerate SCCs in some key graphs -------------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file provides passes to print out SCCs in a CFG or a CallGraph.
|
||||
// Normally, you would not use these passes; instead, you would use the
|
||||
// scc_iterator directly to enumerate SCCs and process them in some way. These
|
||||
// passes serve three purposes:
|
||||
//
|
||||
// (1) As a reference for how to use the scc_iterator.
|
||||
// (2) To print out the SCCs for a CFG or a CallGraph:
|
||||
// analyze -print-cfg-sccs to print the SCCs in each CFG of a module.
|
||||
// analyze -print-cfg-sccs -stats to print the #SCCs and the maximum SCC size.
|
||||
// analyze -print-cfg-sccs -debug > /dev/null to watch the algorithm in action.
|
||||
//
|
||||
// and similarly:
|
||||
// analyze -print-callgraph-sccs [-stats] [-debug] to print SCCs in the CallGraph
|
||||
//
|
||||
// (3) To test the scc_iterator.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "llvm/ADT/SCCIterator.h"
|
||||
#include "llvm/Analysis/CallGraph.h"
|
||||
#include "llvm/IR/CFG.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/Pass.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
using namespace llvm;
|
||||
|
||||
namespace {
|
||||
struct CFGSCC : public FunctionPass {
|
||||
static char ID; // Pass identification, replacement for typeid
|
||||
CFGSCC() : FunctionPass(ID) {}
|
||||
bool runOnFunction(Function& func) override;
|
||||
|
||||
void print(raw_ostream &O, const Module* = nullptr) const override { }
|
||||
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
}
|
||||
};
|
||||
|
||||
struct CallGraphSCC : public ModulePass {
|
||||
static char ID; // Pass identification, replacement for typeid
|
||||
CallGraphSCC() : ModulePass(ID) {}
|
||||
|
||||
// run - Print out SCCs in the call graph for the specified module.
|
||||
bool runOnModule(Module &M) override;
|
||||
|
||||
void print(raw_ostream &O, const Module* = nullptr) const override { }
|
||||
|
||||
// getAnalysisUsage - This pass requires the CallGraph.
|
||||
void getAnalysisUsage(AnalysisUsage &AU) const override {
|
||||
AU.setPreservesAll();
|
||||
AU.addRequired<CallGraphWrapperPass>();
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
char CFGSCC::ID = 0;
|
||||
static RegisterPass<CFGSCC>
|
||||
Y("print-cfg-sccs", "Print SCCs of each function CFG");
|
||||
|
||||
char CallGraphSCC::ID = 0;
|
||||
static RegisterPass<CallGraphSCC>
|
||||
Z("print-callgraph-sccs", "Print SCCs of the Call Graph");
|
||||
|
||||
bool CFGSCC::runOnFunction(Function &F) {
|
||||
unsigned sccNum = 0;
|
||||
errs() << "SCCs for Function " << F.getName() << " in PostOrder:";
|
||||
for (scc_iterator<Function*> SCCI = scc_begin(&F); !SCCI.isAtEnd(); ++SCCI) {
|
||||
const std::vector<BasicBlock *> &nextSCC = *SCCI;
|
||||
errs() << "\nSCC #" << ++sccNum << " : ";
|
||||
for (std::vector<BasicBlock*>::const_iterator I = nextSCC.begin(),
|
||||
E = nextSCC.end(); I != E; ++I)
|
||||
errs() << (*I)->getName() << ", ";
|
||||
if (nextSCC.size() == 1 && SCCI.hasLoop())
|
||||
errs() << " (Has self-loop).";
|
||||
}
|
||||
errs() << "\n";
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// run - Print out SCCs in the call graph for the specified module.
|
||||
bool CallGraphSCC::runOnModule(Module &M) {
|
||||
CallGraph &CG = getAnalysis<CallGraphWrapperPass>().getCallGraph();
|
||||
unsigned sccNum = 0;
|
||||
errs() << "SCCs for the program in PostOrder:";
|
||||
for (scc_iterator<CallGraph*> SCCI = scc_begin(&CG); !SCCI.isAtEnd();
|
||||
++SCCI) {
|
||||
const std::vector<CallGraphNode*> &nextSCC = *SCCI;
|
||||
errs() << "\nSCC #" << ++sccNum << " : ";
|
||||
for (std::vector<CallGraphNode*>::const_iterator I = nextSCC.begin(),
|
||||
E = nextSCC.end(); I != E; ++I)
|
||||
errs() << ((*I)->getFunction() ? (*I)->getFunction()->getName()
|
||||
: "external node") << ", ";
|
||||
if (nextSCC.size() == 1 && SCCI.hasLoop())
|
||||
errs() << " (Has self-loop).";
|
||||
}
|
||||
errs() << "\n";
|
||||
|
||||
return true;
|
||||
}
|
794
external/llvm/tools/opt/opt.cpp
vendored
794
external/llvm/tools/opt/opt.cpp
vendored
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user