26 #define DEBUG_TYPE "instrprof"
39 const char *getPassName()
const override {
40 return "Frontend instrumentation-based coverage lowering";
43 bool runOnModule(
Module &M)
override;
53 std::vector<Value *> UsedVars;
55 bool isMachO()
const {
61 return isMachO() ?
"__DATA,__llvm_prf_cnts" :
"__llvm_prf_cnts";
66 return isMachO() ?
"__DATA,__llvm_prf_names" :
"__llvm_prf_names";
71 return isMachO() ?
"__DATA,__llvm_prf_data" :
"__llvm_prf_data";
76 return isMachO() ?
"__DATA,__llvm_covmap" :
"__llvm_covmap";
92 void emitRegistration();
95 void emitRuntimeHook();
102 void emitInitialization();
109 "Frontend instrumentation-based coverage lowering.",
false,
113 return new InstrProfiling(Options);
116 bool InstrProfiling::runOnModule(
Module &M) {
117 bool MadeChange =
false;
120 RegionCounters.clear();
125 for (
auto I = BB.begin(), E = BB.end();
I != E;)
126 if (
auto *Inc = dyn_cast<InstrProfIncrementInst>(
I++)) {
130 if (
GlobalVariable *Coverage = M.getNamedGlobal(
"__llvm_coverage_mapping")) {
131 lowerCoverageData(Coverage);
140 emitInitialization();
149 Value *Addr = Builder.CreateConstInBoundsGEP2_64(Counters, 0, Index);
150 Value *Count = Builder.CreateLoad(Addr,
"pgocount");
151 Count = Builder.CreateAdd(Count, Builder.getInt64(1));
156 void InstrProfiling::lowerCoverageData(
GlobalVariable *CoverageData) {
157 CoverageData->
setSection(getCoverageSection());
163 assert(Init->
getNumOperands() == 6 &&
"bad number of fields in coverage map");
165 "invalid function list in coverage map");
171 assert(isa<GlobalVariable>(V) &&
"Missing reference to function name");
175 auto It = RegionCounters.find(Name);
176 if (It != RegionCounters.end())
188 StringRef Name = Arr->isCString() ? Arr->getAsCString() : Arr->getAsString();
189 return (
"__llvm_profile_" + VarName +
"_" + Name).str();
195 auto It = RegionCounters.find(Name);
196 if (It != RegionCounters.end())
220 RegionCounters[Inc->
getName()] = Counters;
229 Type *DataTypes[] = {Int32Ty, Int32Ty, Int64Ty, Int8PtrTy, Int64PtrTy};
241 Data->setSection(getDataSection());
242 Data->setAlignment(8);
243 Data->setComdat(Fn->getComdat());
246 UsedVars.push_back(Data);
251 void InstrProfiling::emitRegistration() {
253 if (
Triple(M->getTargetTriple()).isOSDarwin())
261 "__llvm_profile_register_functions", M);
262 RegisterF->setUnnamedAddr(
true);
263 if (Options.NoRedZone)
267 auto *RuntimeRegisterF =
269 "__llvm_profile_register_function", M);
272 for (
Value *Data : UsedVars)
273 IRB.CreateCall(RuntimeRegisterF, IRB.CreateBitCast(Data, VoidPtrTy));
277 void InstrProfiling::emitRuntimeHook() {
278 const char *
const RuntimeVarName =
"__llvm_profile_runtime";
279 const char *
const RuntimeUserName =
"__llvm_profile_runtime_user";
282 if (M->getGlobalVariable(RuntimeVarName))
289 nullptr, RuntimeVarName);
296 if (Options.NoRedZone)
301 auto *
Load = IRB.CreateLoad(Var);
305 UsedVars.push_back(
User);
308 void InstrProfiling::emitUses() {
309 if (UsedVars.empty())
313 std::vector<Constant *> MergedVars;
324 for (
auto *
Value : UsedVars)
325 MergedVars.push_back(
334 LLVMUsed->setSection(
"llvm.metadata");
337 void InstrProfiling::emitInitialization() {
338 std::string InstrProfileOutput = Options.InstrProfileOutput;
340 Constant *RegisterF = M->getFunction(
"__llvm_profile_register_functions");
341 if (!RegisterF && InstrProfileOutput.empty())
349 F->setUnnamedAddr(
true);
351 if (Options.NoRedZone)
357 IRB.CreateCall(RegisterF, {});
358 if (!InstrProfileOutput.empty()) {
363 "__llvm_profile_override_default_filename", M);
372 IRB.CreateCall(SetNameF, IRB.CreatePointerCast(ProfileName, Int8PtrTy));
void setVisibility(VisibilityTypes V)
iplist< Instruction >::iterator eraseFromParent()
eraseFromParent - This method unlinks 'this' from the containing basic block and deletes it...
LinkageTypes getLinkage() const
static Constant * getString(LLVMContext &Context, StringRef Initializer, bool AddNull=true)
getString - This method constructs a CDS and initializes it with a text string.
Special purpose, only applies to global arrays.
VisibilityTypes getVisibility() const
A Module instance is used to store all the information related to an LLVM module. ...
unsigned getNumOperands() const
void appendToGlobalCtors(Module &M, Function *F, int Priority)
Append F to the list of global ctors of module M with the given Priority.
Like Internal, but omit from symbol table.
Externally visible function.
const Function * getParent() const
Return the enclosing method, or null if none.
static IntegerType * getInt64Ty(LLVMContext &C)
void setAlignment(unsigned Align)
const Constant * getInitializer() const
getInitializer - Return the initializer for this global variable.
const std::string & getTargetTriple() const
Get the target triple which is a string describing the target host.
ConstantInt * getHash() const
static PointerType * getInt64PtrTy(LLVMContext &C, unsigned AS=0)
Type * getPointerElementType() const
static Constant * getNullValue(Type *Ty)
ArrayRef< T > makeArrayRef(const T &OneElt)
Construct an ArrayRef from a single element.
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
ConstantInt * getIndex() const
void eraseFromParent() override
eraseFromParent - This method unlinks 'this' from the containing module and deletes it...
ConstantInt * getNumCounters() const
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
ArrayType - Class to represent array types.
void setComdat(Comdat *C)
static FunctionType * get(Type *Result, ArrayRef< Type * > Params, bool isVarArg)
FunctionType::get - This static method is the primary way of constructing a FunctionType.
void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
static Constant * getBitCast(Constant *C, Type *Ty, bool OnlyIfReduced=false)
Same, but only replaced by something equivalent.
GlobalVariable * getName() const
LLVM Basic Block Representation.
The instances of the Type class are immutable: once they are created, they are never changed...
This is an important class for using LLVM in a threaded context.
This is an important base class in LLVM.
static Constant * get(ArrayType *T, ArrayRef< Constant * > V)
ModulePass * createInstrProfilingPass(const InstrProfOptions &Options=InstrProfOptions())
Insert frontend instrumentation based profiling.
Represent the analysis usage information of a pass.
static Type * getVoidTy(LLVMContext &C)
Value * getOperand(unsigned i) const
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
static Constant * get(StructType *T, ArrayRef< Constant * > V)
Constant * getAggregateElement(unsigned Elt) const
getAggregateElement - For aggregates (struct/array/vector) return the constant that corresponds to th...
static PointerType * getInt8PtrTy(LLVMContext &C, unsigned AS=0)
Triple - Helper class for working with autoconf configuration names.
static StructType * get(LLVMContext &Context, ArrayRef< Type * > Elements, bool isPacked=false)
StructType::get - This static method is the primary way to create a literal StructType.
Module.h This file contains the declarations for the Module class.
Type * getType() const
All values are typed, get the type of this value.
static Constant * get(Type *Ty, uint64_t V, bool isSigned=false)
If Ty is a vector type, return a Constant with a splat of the given value.
void setPreservesCFG()
This function should be called by the pass, iff they do not:
INITIALIZE_PASS(InstrProfiling,"instrprof","Frontend instrumentation-based coverage lowering.", false, false) ModulePass *llvm
ConstantArray - Constant Array Declarations.
Options for the frontend instrumentation based profiling pass.
static std::string getVarName(InstrProfIncrementInst *Inc, StringRef VarName)
Get the name of a profiling variable for a particular function.
This represents the llvm.instrprof_increment intrinsic.
PointerType * getType() const
Global values are always pointers.
static IntegerType * getInt32Ty(LLVMContext &C)
ModulePass class - This class is used to implement unstructured interprocedural optimizations and ana...
static ArrayType * get(Type *ElementType, uint64_t NumElements)
ArrayType::get - This static method is the primary way to construct an ArrayType. ...
Rename collisions when linking (static functions).
LLVM Value Representation.
StringRef - Represent a constant reference to a string, i.e.
static Function * Create(FunctionType *Ty, LinkageTypes Linkage, const Twine &N="", Module *M=nullptr)
void setSection(StringRef S)
const BasicBlock * getParent() const