LLVM  15.0.0git
SanitizerCoverage.cpp
Go to the documentation of this file.
1 //===-- SanitizerCoverage.cpp - coverage instrumentation for sanitizers ---===//
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 // Coverage instrumentation done on LLVM IR level, works with Sanitizers.
10 //
11 //===----------------------------------------------------------------------===//
12 
14 #include "llvm/ADT/ArrayRef.h"
15 #include "llvm/ADT/SmallVector.h"
16 #include "llvm/ADT/Triple.h"
19 #include "llvm/IR/Constant.h"
20 #include "llvm/IR/DataLayout.h"
21 #include "llvm/IR/Dominators.h"
22 #include "llvm/IR/Function.h"
23 #include "llvm/IR/GlobalVariable.h"
24 #include "llvm/IR/IRBuilder.h"
25 #include "llvm/IR/IntrinsicInst.h"
26 #include "llvm/IR/Intrinsics.h"
27 #include "llvm/IR/LLVMContext.h"
28 #include "llvm/IR/Module.h"
29 #include "llvm/IR/Type.h"
30 #include "llvm/InitializePasses.h"
37 
38 using namespace llvm;
39 
40 #define DEBUG_TYPE "sancov"
41 
42 const char SanCovTracePCIndirName[] = "__sanitizer_cov_trace_pc_indir";
43 const char SanCovTracePCName[] = "__sanitizer_cov_trace_pc";
44 const char SanCovTraceCmp1[] = "__sanitizer_cov_trace_cmp1";
45 const char SanCovTraceCmp2[] = "__sanitizer_cov_trace_cmp2";
46 const char SanCovTraceCmp4[] = "__sanitizer_cov_trace_cmp4";
47 const char SanCovTraceCmp8[] = "__sanitizer_cov_trace_cmp8";
48 const char SanCovTraceConstCmp1[] = "__sanitizer_cov_trace_const_cmp1";
49 const char SanCovTraceConstCmp2[] = "__sanitizer_cov_trace_const_cmp2";
50 const char SanCovTraceConstCmp4[] = "__sanitizer_cov_trace_const_cmp4";
51 const char SanCovTraceConstCmp8[] = "__sanitizer_cov_trace_const_cmp8";
52 const char SanCovLoad1[] = "__sanitizer_cov_load1";
53 const char SanCovLoad2[] = "__sanitizer_cov_load2";
54 const char SanCovLoad4[] = "__sanitizer_cov_load4";
55 const char SanCovLoad8[] = "__sanitizer_cov_load8";
56 const char SanCovLoad16[] = "__sanitizer_cov_load16";
57 const char SanCovStore1[] = "__sanitizer_cov_store1";
58 const char SanCovStore2[] = "__sanitizer_cov_store2";
59 const char SanCovStore4[] = "__sanitizer_cov_store4";
60 const char SanCovStore8[] = "__sanitizer_cov_store8";
61 const char SanCovStore16[] = "__sanitizer_cov_store16";
62 const char SanCovTraceDiv4[] = "__sanitizer_cov_trace_div4";
63 const char SanCovTraceDiv8[] = "__sanitizer_cov_trace_div8";
64 const char SanCovTraceGep[] = "__sanitizer_cov_trace_gep";
65 const char SanCovTraceSwitchName[] = "__sanitizer_cov_trace_switch";
67  "sancov.module_ctor_trace_pc_guard";
69  "sancov.module_ctor_8bit_counters";
70 const char SanCovModuleCtorBoolFlagName[] = "sancov.module_ctor_bool_flag";
72 
73 const char SanCovTracePCGuardName[] = "__sanitizer_cov_trace_pc_guard";
74 const char SanCovTracePCGuardInitName[] = "__sanitizer_cov_trace_pc_guard_init";
75 const char SanCov8bitCountersInitName[] = "__sanitizer_cov_8bit_counters_init";
76 const char SanCovBoolFlagInitName[] = "__sanitizer_cov_bool_flag_init";
77 const char SanCovPCsInitName[] = "__sanitizer_cov_pcs_init";
78 
79 const char SanCovGuardsSectionName[] = "sancov_guards";
80 const char SanCovCountersSectionName[] = "sancov_cntrs";
81 const char SanCovBoolFlagSectionName[] = "sancov_bools";
82 const char SanCovPCsSectionName[] = "sancov_pcs";
83 
84 const char SanCovLowestStackName[] = "__sancov_lowest_stack";
85 
87  "sanitizer-coverage-level",
88  cl::desc("Sanitizer Coverage. 0: none, 1: entry block, 2: all blocks, "
89  "3: all blocks and critical edges"),
90  cl::Hidden, cl::init(0));
91 
92 static cl::opt<bool> ClTracePC("sanitizer-coverage-trace-pc",
93  cl::desc("Experimental pc tracing"), cl::Hidden,
94  cl::init(false));
95 
96 static cl::opt<bool> ClTracePCGuard("sanitizer-coverage-trace-pc-guard",
97  cl::desc("pc tracing with a guard"),
98  cl::Hidden, cl::init(false));
99 
100 // If true, we create a global variable that contains PCs of all instrumented
101 // BBs, put this global into a named section, and pass this section's bounds
102 // to __sanitizer_cov_pcs_init.
103 // This way the coverage instrumentation does not need to acquire the PCs
104 // at run-time. Works with trace-pc-guard, inline-8bit-counters, and
105 // inline-bool-flag.
106 static cl::opt<bool> ClCreatePCTable("sanitizer-coverage-pc-table",
107  cl::desc("create a static PC table"),
108  cl::Hidden, cl::init(false));
109 
110 static cl::opt<bool>
111  ClInline8bitCounters("sanitizer-coverage-inline-8bit-counters",
112  cl::desc("increments 8-bit counter for every edge"),
113  cl::Hidden, cl::init(false));
114 
115 static cl::opt<bool>
116  ClInlineBoolFlag("sanitizer-coverage-inline-bool-flag",
117  cl::desc("sets a boolean flag for every edge"), cl::Hidden,
118  cl::init(false));
119 
120 static cl::opt<bool>
121  ClCMPTracing("sanitizer-coverage-trace-compares",
122  cl::desc("Tracing of CMP and similar instructions"),
123  cl::Hidden, cl::init(false));
124 
125 static cl::opt<bool> ClDIVTracing("sanitizer-coverage-trace-divs",
126  cl::desc("Tracing of DIV instructions"),
127  cl::Hidden, cl::init(false));
128 
129 static cl::opt<bool> ClLoadTracing("sanitizer-coverage-trace-loads",
130  cl::desc("Tracing of load instructions"),
131  cl::Hidden, cl::init(false));
132 
133 static cl::opt<bool> ClStoreTracing("sanitizer-coverage-trace-stores",
134  cl::desc("Tracing of store instructions"),
135  cl::Hidden, cl::init(false));
136 
137 static cl::opt<bool> ClGEPTracing("sanitizer-coverage-trace-geps",
138  cl::desc("Tracing of GEP instructions"),
139  cl::Hidden, cl::init(false));
140 
141 static cl::opt<bool>
142  ClPruneBlocks("sanitizer-coverage-prune-blocks",
143  cl::desc("Reduce the number of instrumented blocks"),
144  cl::Hidden, cl::init(true));
145 
146 static cl::opt<bool> ClStackDepth("sanitizer-coverage-stack-depth",
147  cl::desc("max stack depth tracing"),
148  cl::Hidden, cl::init(false));
149 
150 namespace {
151 
152 SanitizerCoverageOptions getOptions(int LegacyCoverageLevel) {
154  switch (LegacyCoverageLevel) {
155  case 0:
157  break;
158  case 1:
160  break;
161  case 2:
163  break;
164  case 3:
166  break;
167  case 4:
169  Res.IndirectCalls = true;
170  break;
171  }
172  return Res;
173 }
174 
176  // Sets CoverageType and IndirectCalls.
177  SanitizerCoverageOptions CLOpts = getOptions(ClCoverageLevel);
178  Options.CoverageType = std::max(Options.CoverageType, CLOpts.CoverageType);
179  Options.IndirectCalls |= CLOpts.IndirectCalls;
180  Options.TraceCmp |= ClCMPTracing;
181  Options.TraceDiv |= ClDIVTracing;
182  Options.TraceGep |= ClGEPTracing;
183  Options.TracePC |= ClTracePC;
184  Options.TracePCGuard |= ClTracePCGuard;
185  Options.Inline8bitCounters |= ClInline8bitCounters;
186  Options.InlineBoolFlag |= ClInlineBoolFlag;
187  Options.PCTable |= ClCreatePCTable;
188  Options.NoPrune |= !ClPruneBlocks;
189  Options.StackDepth |= ClStackDepth;
190  Options.TraceLoads |= ClLoadTracing;
191  Options.TraceStores |= ClStoreTracing;
192  if (!Options.TracePCGuard && !Options.TracePC &&
193  !Options.Inline8bitCounters && !Options.StackDepth &&
194  !Options.InlineBoolFlag && !Options.TraceLoads && !Options.TraceStores)
195  Options.TracePCGuard = true; // TracePCGuard is default.
196  return Options;
197 }
198 
199 using DomTreeCallback = function_ref<const DominatorTree *(Function &F)>;
200 using PostDomTreeCallback =
202 
203 class ModuleSanitizerCoverage {
204 public:
205  ModuleSanitizerCoverage(
207  const SpecialCaseList *Allowlist = nullptr,
208  const SpecialCaseList *Blocklist = nullptr)
209  : Options(OverrideFromCL(Options)), Allowlist(Allowlist),
210  Blocklist(Blocklist) {}
211  bool instrumentModule(Module &M, DomTreeCallback DTCallback,
212  PostDomTreeCallback PDTCallback);
213 
214 private:
215  void instrumentFunction(Function &F, DomTreeCallback DTCallback,
216  PostDomTreeCallback PDTCallback);
217  void InjectCoverageForIndirectCalls(Function &F,
218  ArrayRef<Instruction *> IndirCalls);
219  void InjectTraceForCmp(Function &F, ArrayRef<Instruction *> CmpTraceTargets);
220  void InjectTraceForDiv(Function &F,
221  ArrayRef<BinaryOperator *> DivTraceTargets);
222  void InjectTraceForGep(Function &F,
223  ArrayRef<GetElementPtrInst *> GepTraceTargets);
224  void InjectTraceForLoadsAndStores(Function &F, ArrayRef<LoadInst *> Loads,
225  ArrayRef<StoreInst *> Stores);
226  void InjectTraceForSwitch(Function &F,
227  ArrayRef<Instruction *> SwitchTraceTargets);
228  bool InjectCoverage(Function &F, ArrayRef<BasicBlock *> AllBlocks,
229  bool IsLeafFunc = true);
230  GlobalVariable *CreateFunctionLocalArrayInSection(size_t NumElements,
231  Function &F, Type *Ty,
232  const char *Section);
233  GlobalVariable *CreatePCArray(Function &F, ArrayRef<BasicBlock *> AllBlocks);
234  void CreateFunctionLocalArrays(Function &F, ArrayRef<BasicBlock *> AllBlocks);
235  void InjectCoverageAtBlock(Function &F, BasicBlock &BB, size_t Idx,
236  bool IsLeafFunc = true);
237  Function *CreateInitCallsForSections(Module &M, const char *CtorName,
238  const char *InitFunctionName, Type *Ty,
239  const char *Section);
240  std::pair<Value *, Value *> CreateSecStartEnd(Module &M, const char *Section,
241  Type *Ty);
242 
243  void SetNoSanitizeMetadata(Instruction *I) {
244  I->setMetadata(I->getModule()->getMDKindID("nosanitize"),
245  MDNode::get(*C, None));
246  }
247 
248  std::string getSectionName(const std::string &Section) const;
249  std::string getSectionStart(const std::string &Section) const;
250  std::string getSectionEnd(const std::string &Section) const;
251  FunctionCallee SanCovTracePCIndir;
252  FunctionCallee SanCovTracePC, SanCovTracePCGuard;
253  std::array<FunctionCallee, 4> SanCovTraceCmpFunction;
254  std::array<FunctionCallee, 4> SanCovTraceConstCmpFunction;
255  std::array<FunctionCallee, 5> SanCovLoadFunction;
256  std::array<FunctionCallee, 5> SanCovStoreFunction;
257  std::array<FunctionCallee, 2> SanCovTraceDivFunction;
258  FunctionCallee SanCovTraceGepFunction;
259  FunctionCallee SanCovTraceSwitchFunction;
260  GlobalVariable *SanCovLowestStack;
261  Type *Int128PtrTy, *IntptrTy, *IntptrPtrTy, *Int64Ty, *Int64PtrTy, *Int32Ty,
262  *Int32PtrTy, *Int16PtrTy, *Int16Ty, *Int8Ty, *Int8PtrTy, *Int1Ty,
263  *Int1PtrTy;
264  Module *CurModule;
265  std::string CurModuleUniqueId;
266  Triple TargetTriple;
267  LLVMContext *C;
268  const DataLayout *DL;
269 
270  GlobalVariable *FunctionGuardArray; // for trace-pc-guard.
271  GlobalVariable *Function8bitCounterArray; // for inline-8bit-counters.
272  GlobalVariable *FunctionBoolArray; // for inline-bool-flag.
273  GlobalVariable *FunctionPCsArray; // for pc-table.
274  SmallVector<GlobalValue *, 20> GlobalsToAppendToUsed;
275  SmallVector<GlobalValue *, 20> GlobalsToAppendToCompilerUsed;
276 
278 
279  const SpecialCaseList *Allowlist;
280  const SpecialCaseList *Blocklist;
281 };
282 
283 class ModuleSanitizerCoverageLegacyPass : public ModulePass {
284 public:
285  ModuleSanitizerCoverageLegacyPass(
287  const std::vector<std::string> &AllowlistFiles =
288  std::vector<std::string>(),
289  const std::vector<std::string> &BlocklistFiles =
290  std::vector<std::string>())
292  if (AllowlistFiles.size() > 0)
293  Allowlist = SpecialCaseList::createOrDie(AllowlistFiles,
295  if (BlocklistFiles.size() > 0)
296  Blocklist = SpecialCaseList::createOrDie(BlocklistFiles,
300  }
301  bool runOnModule(Module &M) override {
302  ModuleSanitizerCoverage ModuleSancov(Options, Allowlist.get(),
303  Blocklist.get());
304  auto DTCallback = [this](Function &F) -> const DominatorTree * {
305  return &this->getAnalysis<DominatorTreeWrapperPass>(F).getDomTree();
306  };
307  auto PDTCallback = [this](Function &F) -> const PostDominatorTree * {
308  return &this->getAnalysis<PostDominatorTreeWrapperPass>(F)
309  .getPostDomTree();
310  };
311  return ModuleSancov.instrumentModule(M, DTCallback, PDTCallback);
312  }
313 
314  static char ID; // Pass identification, replacement for typeid
315  StringRef getPassName() const override { return "ModuleSanitizerCoverage"; }
316 
317  void getAnalysisUsage(AnalysisUsage &AU) const override {
320  }
321 
322 private:
324 
325  std::unique_ptr<SpecialCaseList> Allowlist;
326  std::unique_ptr<SpecialCaseList> Blocklist;
327 };
328 
329 } // namespace
330 
333  ModuleSanitizerCoverage ModuleSancov(Options, Allowlist.get(),
334  Blocklist.get());
335  auto &FAM = MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
336  auto DTCallback = [&FAM](Function &F) -> const DominatorTree * {
338  };
339  auto PDTCallback = [&FAM](Function &F) -> const PostDominatorTree * {
341  };
342  if (ModuleSancov.instrumentModule(M, DTCallback, PDTCallback))
343  return PreservedAnalyses::none();
344  return PreservedAnalyses::all();
345 }
346 
347 std::pair<Value *, Value *>
348 ModuleSanitizerCoverage::CreateSecStartEnd(Module &M, const char *Section,
349  Type *Ty) {
350  // Use ExternalWeak so that if all sections are discarded due to section
351  // garbage collection, the linker will not report undefined symbol errors.
352  // Windows defines the start/stop symbols in compiler-rt so no need for
353  // ExternalWeak.
354  GlobalValue::LinkageTypes Linkage = TargetTriple.isOSBinFormatCOFF()
357  GlobalVariable *SecStart =
358  new GlobalVariable(M, Ty, false, Linkage, nullptr,
359  getSectionStart(Section));
361  GlobalVariable *SecEnd =
362  new GlobalVariable(M, Ty, false, Linkage, nullptr,
363  getSectionEnd(Section));
365  IRBuilder<> IRB(M.getContext());
366  if (!TargetTriple.isOSBinFormatCOFF())
367  return std::make_pair(SecStart, SecEnd);
368 
369  // Account for the fact that on windows-msvc __start_* symbols actually
370  // point to a uint64_t before the start of the array.
371  auto SecStartI8Ptr = IRB.CreatePointerCast(SecStart, Int8PtrTy);
372  auto GEP = IRB.CreateGEP(Int8Ty, SecStartI8Ptr,
373  ConstantInt::get(IntptrTy, sizeof(uint64_t)));
374  return std::make_pair(IRB.CreatePointerCast(GEP, PointerType::getUnqual(Ty)),
375  SecEnd);
376 }
377 
378 Function *ModuleSanitizerCoverage::CreateInitCallsForSections(
379  Module &M, const char *CtorName, const char *InitFunctionName, Type *Ty,
380  const char *Section) {
381  auto SecStartEnd = CreateSecStartEnd(M, Section, Ty);
382  auto SecStart = SecStartEnd.first;
383  auto SecEnd = SecStartEnd.second;
384  Function *CtorFunc;
385  Type *PtrTy = PointerType::getUnqual(Ty);
386  std::tie(CtorFunc, std::ignore) = createSanitizerCtorAndInitFunctions(
387  M, CtorName, InitFunctionName, {PtrTy, PtrTy}, {SecStart, SecEnd});
388  assert(CtorFunc->getName() == CtorName);
389 
390  if (TargetTriple.supportsCOMDAT()) {
391  // Use comdat to dedup CtorFunc.
392  CtorFunc->setComdat(M.getOrInsertComdat(CtorName));
393  appendToGlobalCtors(M, CtorFunc, SanCtorAndDtorPriority, CtorFunc);
394  } else {
396  }
397 
398  if (TargetTriple.isOSBinFormatCOFF()) {
399  // In COFF files, if the contructors are set as COMDAT (they are because
400  // COFF supports COMDAT) and the linker flag /OPT:REF (strip unreferenced
401  // functions and data) is used, the constructors get stripped. To prevent
402  // this, give the constructors weak ODR linkage and ensure the linker knows
403  // to include the sancov constructor. This way the linker can deduplicate
404  // the constructors but always leave one copy.
406  }
407  return CtorFunc;
408 }
409 
410 bool ModuleSanitizerCoverage::instrumentModule(
411  Module &M, DomTreeCallback DTCallback, PostDomTreeCallback PDTCallback) {
412  if (Options.CoverageType == SanitizerCoverageOptions::SCK_None)
413  return false;
414  if (Allowlist &&
415  !Allowlist->inSection("coverage", "src", M.getSourceFileName()))
416  return false;
417  if (Blocklist &&
418  Blocklist->inSection("coverage", "src", M.getSourceFileName()))
419  return false;
420  C = &(M.getContext());
421  DL = &M.getDataLayout();
422  CurModule = &M;
423  CurModuleUniqueId = getUniqueModuleId(CurModule);
424  TargetTriple = Triple(M.getTargetTriple());
425  FunctionGuardArray = nullptr;
426  Function8bitCounterArray = nullptr;
427  FunctionBoolArray = nullptr;
428  FunctionPCsArray = nullptr;
429  IntptrTy = Type::getIntNTy(*C, DL->getPointerSizeInBits());
430  IntptrPtrTy = PointerType::getUnqual(IntptrTy);
431  Type *VoidTy = Type::getVoidTy(*C);
432  IRBuilder<> IRB(*C);
433  Int128PtrTy = PointerType::getUnqual(IRB.getInt128Ty());
434  Int64PtrTy = PointerType::getUnqual(IRB.getInt64Ty());
435  Int16PtrTy = PointerType::getUnqual(IRB.getInt16Ty());
436  Int32PtrTy = PointerType::getUnqual(IRB.getInt32Ty());
437  Int8PtrTy = PointerType::getUnqual(IRB.getInt8Ty());
438  Int1PtrTy = PointerType::getUnqual(IRB.getInt1Ty());
439  Int64Ty = IRB.getInt64Ty();
440  Int32Ty = IRB.getInt32Ty();
441  Int16Ty = IRB.getInt16Ty();
442  Int8Ty = IRB.getInt8Ty();
443  Int1Ty = IRB.getInt1Ty();
444 
445  SanCovTracePCIndir =
446  M.getOrInsertFunction(SanCovTracePCIndirName, VoidTy, IntptrTy);
447  // Make sure smaller parameters are zero-extended to i64 if required by the
448  // target ABI.
449  AttributeList SanCovTraceCmpZeroExtAL;
450  SanCovTraceCmpZeroExtAL =
451  SanCovTraceCmpZeroExtAL.addParamAttribute(*C, 0, Attribute::ZExt);
452  SanCovTraceCmpZeroExtAL =
453  SanCovTraceCmpZeroExtAL.addParamAttribute(*C, 1, Attribute::ZExt);
454 
455  SanCovTraceCmpFunction[0] =
456  M.getOrInsertFunction(SanCovTraceCmp1, SanCovTraceCmpZeroExtAL, VoidTy,
457  IRB.getInt8Ty(), IRB.getInt8Ty());
458  SanCovTraceCmpFunction[1] =
459  M.getOrInsertFunction(SanCovTraceCmp2, SanCovTraceCmpZeroExtAL, VoidTy,
460  IRB.getInt16Ty(), IRB.getInt16Ty());
461  SanCovTraceCmpFunction[2] =
462  M.getOrInsertFunction(SanCovTraceCmp4, SanCovTraceCmpZeroExtAL, VoidTy,
463  IRB.getInt32Ty(), IRB.getInt32Ty());
464  SanCovTraceCmpFunction[3] =
465  M.getOrInsertFunction(SanCovTraceCmp8, VoidTy, Int64Ty, Int64Ty);
466 
467  SanCovTraceConstCmpFunction[0] = M.getOrInsertFunction(
468  SanCovTraceConstCmp1, SanCovTraceCmpZeroExtAL, VoidTy, Int8Ty, Int8Ty);
469  SanCovTraceConstCmpFunction[1] = M.getOrInsertFunction(
470  SanCovTraceConstCmp2, SanCovTraceCmpZeroExtAL, VoidTy, Int16Ty, Int16Ty);
471  SanCovTraceConstCmpFunction[2] = M.getOrInsertFunction(
472  SanCovTraceConstCmp4, SanCovTraceCmpZeroExtAL, VoidTy, Int32Ty, Int32Ty);
473  SanCovTraceConstCmpFunction[3] =
474  M.getOrInsertFunction(SanCovTraceConstCmp8, VoidTy, Int64Ty, Int64Ty);
475 
476  // Loads.
477  SanCovLoadFunction[0] = M.getOrInsertFunction(SanCovLoad1, VoidTy, Int8PtrTy);
478  SanCovLoadFunction[1] =
479  M.getOrInsertFunction(SanCovLoad2, VoidTy, Int16PtrTy);
480  SanCovLoadFunction[2] =
481  M.getOrInsertFunction(SanCovLoad4, VoidTy, Int32PtrTy);
482  SanCovLoadFunction[3] =
483  M.getOrInsertFunction(SanCovLoad8, VoidTy, Int64PtrTy);
484  SanCovLoadFunction[4] =
485  M.getOrInsertFunction(SanCovLoad16, VoidTy, Int128PtrTy);
486  // Stores.
487  SanCovStoreFunction[0] =
488  M.getOrInsertFunction(SanCovStore1, VoidTy, Int8PtrTy);
489  SanCovStoreFunction[1] =
490  M.getOrInsertFunction(SanCovStore2, VoidTy, Int16PtrTy);
491  SanCovStoreFunction[2] =
492  M.getOrInsertFunction(SanCovStore4, VoidTy, Int32PtrTy);
493  SanCovStoreFunction[3] =
494  M.getOrInsertFunction(SanCovStore8, VoidTy, Int64PtrTy);
495  SanCovStoreFunction[4] =
496  M.getOrInsertFunction(SanCovStore16, VoidTy, Int128PtrTy);
497 
498  {
500  AL = AL.addParamAttribute(*C, 0, Attribute::ZExt);
501  SanCovTraceDivFunction[0] =
502  M.getOrInsertFunction(SanCovTraceDiv4, AL, VoidTy, IRB.getInt32Ty());
503  }
504  SanCovTraceDivFunction[1] =
505  M.getOrInsertFunction(SanCovTraceDiv8, VoidTy, Int64Ty);
506  SanCovTraceGepFunction =
507  M.getOrInsertFunction(SanCovTraceGep, VoidTy, IntptrTy);
508  SanCovTraceSwitchFunction =
509  M.getOrInsertFunction(SanCovTraceSwitchName, VoidTy, Int64Ty, Int64PtrTy);
510 
511  Constant *SanCovLowestStackConstant =
512  M.getOrInsertGlobal(SanCovLowestStackName, IntptrTy);
513  SanCovLowestStack = dyn_cast<GlobalVariable>(SanCovLowestStackConstant);
514  if (!SanCovLowestStack || SanCovLowestStack->getValueType() != IntptrTy) {
515  C->emitError(StringRef("'") + SanCovLowestStackName +
516  "' should not be declared by the user");
517  return true;
518  }
519  SanCovLowestStack->setThreadLocalMode(
520  GlobalValue::ThreadLocalMode::InitialExecTLSModel);
521  if (Options.StackDepth && !SanCovLowestStack->isDeclaration())
522  SanCovLowestStack->setInitializer(Constant::getAllOnesValue(IntptrTy));
523 
524  SanCovTracePC = M.getOrInsertFunction(SanCovTracePCName, VoidTy);
525  SanCovTracePCGuard =
526  M.getOrInsertFunction(SanCovTracePCGuardName, VoidTy, Int32PtrTy);
527 
528  for (auto &F : M)
529  instrumentFunction(F, DTCallback, PDTCallback);
530 
531  Function *Ctor = nullptr;
532 
533  if (FunctionGuardArray)
534  Ctor = CreateInitCallsForSections(M, SanCovModuleCtorTracePcGuardName,
537  if (Function8bitCounterArray)
538  Ctor = CreateInitCallsForSections(M, SanCovModuleCtor8bitCountersName,
541  if (FunctionBoolArray) {
542  Ctor = CreateInitCallsForSections(M, SanCovModuleCtorBoolFlagName,
543  SanCovBoolFlagInitName, Int1Ty,
545  }
546  if (Ctor && Options.PCTable) {
547  auto SecStartEnd = CreateSecStartEnd(M, SanCovPCsSectionName, IntptrTy);
549  M, SanCovPCsInitName, {IntptrPtrTy, IntptrPtrTy});
550  IRBuilder<> IRBCtor(Ctor->getEntryBlock().getTerminator());
551  IRBCtor.CreateCall(InitFunction, {SecStartEnd.first, SecStartEnd.second});
552  }
553  appendToUsed(M, GlobalsToAppendToUsed);
554  appendToCompilerUsed(M, GlobalsToAppendToCompilerUsed);
555  return true;
556 }
557 
558 // True if block has successors and it dominates all of them.
559 static bool isFullDominator(const BasicBlock *BB, const DominatorTree *DT) {
560  if (succ_empty(BB))
561  return false;
562 
563  return llvm::all_of(successors(BB), [&](const BasicBlock *SUCC) {
564  return DT->dominates(BB, SUCC);
565  });
566 }
567 
568 // True if block has predecessors and it postdominates all of them.
569 static bool isFullPostDominator(const BasicBlock *BB,
570  const PostDominatorTree *PDT) {
571  if (pred_empty(BB))
572  return false;
573 
574  return llvm::all_of(predecessors(BB), [&](const BasicBlock *PRED) {
575  return PDT->dominates(BB, PRED);
576  });
577 }
578 
579 static bool shouldInstrumentBlock(const Function &F, const BasicBlock *BB,
580  const DominatorTree *DT,
581  const PostDominatorTree *PDT,
583  // Don't insert coverage for blocks containing nothing but unreachable: we
584  // will never call __sanitizer_cov() for them, so counting them in
585  // NumberOfInstrumentedBlocks() might complicate calculation of code coverage
586  // percentage. Also, unreachable instructions frequently have no debug
587  // locations.
588  if (isa<UnreachableInst>(BB->getFirstNonPHIOrDbgOrLifetime()))
589  return false;
590 
591  // Don't insert coverage into blocks without a valid insertion point
592  // (catchswitch blocks).
593  if (BB->getFirstInsertionPt() == BB->end())
594  return false;
595 
596  if (Options.NoPrune || &F.getEntryBlock() == BB)
597  return true;
598 
599  if (Options.CoverageType == SanitizerCoverageOptions::SCK_Function &&
600  &F.getEntryBlock() != BB)
601  return false;
602 
603  // Do not instrument full dominators, or full post-dominators with multiple
604  // predecessors.
605  return !isFullDominator(BB, DT)
606  && !(isFullPostDominator(BB, PDT) && !BB->getSinglePredecessor());
607 }
608 
609 
610 // Returns true iff From->To is a backedge.
611 // A twist here is that we treat From->To as a backedge if
612 // * To dominates From or
613 // * To->UniqueSuccessor dominates From
615  const DominatorTree *DT) {
616  if (DT->dominates(To, From))
617  return true;
618  if (auto Next = To->getUniqueSuccessor())
619  if (DT->dominates(Next, From))
620  return true;
621  return false;
622 }
623 
624 // Prunes uninteresting Cmp instrumentation:
625 // * CMP instructions that feed into loop backedge branch.
626 //
627 // Note that Cmp pruning is controlled by the same flag as the
628 // BB pruning.
629 static bool IsInterestingCmp(ICmpInst *CMP, const DominatorTree *DT,
631  if (!Options.NoPrune)
632  if (CMP->hasOneUse())
633  if (auto BR = dyn_cast<BranchInst>(CMP->user_back()))
634  for (BasicBlock *B : BR->successors())
635  if (IsBackEdge(BR->getParent(), B, DT))
636  return false;
637  return true;
638 }
639 
640 void ModuleSanitizerCoverage::instrumentFunction(
641  Function &F, DomTreeCallback DTCallback, PostDomTreeCallback PDTCallback) {
642  if (F.empty())
643  return;
644  if (F.getName().find(".module_ctor") != std::string::npos)
645  return; // Should not instrument sanitizer init functions.
646  if (F.getName().startswith("__sanitizer_"))
647  return; // Don't instrument __sanitizer_* callbacks.
648  // Don't touch available_externally functions, their actual body is elewhere.
649  if (F.getLinkage() == GlobalValue::AvailableExternallyLinkage)
650  return;
651  // Don't instrument MSVC CRT configuration helpers. They may run before normal
652  // initialization.
653  if (F.getName() == "__local_stdio_printf_options" ||
654  F.getName() == "__local_stdio_scanf_options")
655  return;
656  if (isa<UnreachableInst>(F.getEntryBlock().getTerminator()))
657  return;
658  // Don't instrument functions using SEH for now. Splitting basic blocks like
659  // we do for coverage breaks WinEHPrepare.
660  // FIXME: Remove this when SEH no longer uses landingpad pattern matching.
661  if (F.hasPersonalityFn() &&
663  return;
664  if (Allowlist && !Allowlist->inSection("coverage", "fun", F.getName()))
665  return;
666  if (Blocklist && Blocklist->inSection("coverage", "fun", F.getName()))
667  return;
668  if (F.hasFnAttribute(Attribute::NoSanitizeCoverage))
669  return;
670  if (Options.CoverageType >= SanitizerCoverageOptions::SCK_Edge)
671  SplitAllCriticalEdges(F, CriticalEdgeSplittingOptions().setIgnoreUnreachableDests());
673  SmallVector<BasicBlock *, 16> BlocksToInstrument;
674  SmallVector<Instruction *, 8> CmpTraceTargets;
675  SmallVector<Instruction *, 8> SwitchTraceTargets;
676  SmallVector<BinaryOperator *, 8> DivTraceTargets;
677  SmallVector<GetElementPtrInst *, 8> GepTraceTargets;
680 
681  const DominatorTree *DT = DTCallback(F);
682  const PostDominatorTree *PDT = PDTCallback(F);
683  bool IsLeafFunc = true;
684 
685  for (auto &BB : F) {
686  if (shouldInstrumentBlock(F, &BB, DT, PDT, Options))
687  BlocksToInstrument.push_back(&BB);
688  for (auto &Inst : BB) {
689  if (Options.IndirectCalls) {
690  CallBase *CB = dyn_cast<CallBase>(&Inst);
691  if (CB && CB->isIndirectCall())
692  IndirCalls.push_back(&Inst);
693  }
694  if (Options.TraceCmp) {
695  if (ICmpInst *CMP = dyn_cast<ICmpInst>(&Inst))
696  if (IsInterestingCmp(CMP, DT, Options))
697  CmpTraceTargets.push_back(&Inst);
698  if (isa<SwitchInst>(&Inst))
699  SwitchTraceTargets.push_back(&Inst);
700  }
701  if (Options.TraceDiv)
702  if (BinaryOperator *BO = dyn_cast<BinaryOperator>(&Inst))
703  if (BO->getOpcode() == Instruction::SDiv ||
704  BO->getOpcode() == Instruction::UDiv)
705  DivTraceTargets.push_back(BO);
706  if (Options.TraceGep)
707  if (GetElementPtrInst *GEP = dyn_cast<GetElementPtrInst>(&Inst))
708  GepTraceTargets.push_back(GEP);
709  if (Options.TraceLoads)
710  if (LoadInst *LI = dyn_cast<LoadInst>(&Inst))
711  Loads.push_back(LI);
712  if (Options.TraceStores)
713  if (StoreInst *SI = dyn_cast<StoreInst>(&Inst))
714  Stores.push_back(SI);
715  if (Options.StackDepth)
716  if (isa<InvokeInst>(Inst) ||
717  (isa<CallInst>(Inst) && !isa<IntrinsicInst>(Inst)))
718  IsLeafFunc = false;
719  }
720  }
721 
722  InjectCoverage(F, BlocksToInstrument, IsLeafFunc);
723  InjectCoverageForIndirectCalls(F, IndirCalls);
724  InjectTraceForCmp(F, CmpTraceTargets);
725  InjectTraceForSwitch(F, SwitchTraceTargets);
726  InjectTraceForDiv(F, DivTraceTargets);
727  InjectTraceForGep(F, GepTraceTargets);
728  InjectTraceForLoadsAndStores(F, Loads, Stores);
729 }
730 
731 GlobalVariable *ModuleSanitizerCoverage::CreateFunctionLocalArrayInSection(
732  size_t NumElements, Function &F, Type *Ty, const char *Section) {
733  ArrayType *ArrayTy = ArrayType::get(Ty, NumElements);
734  auto Array = new GlobalVariable(
735  *CurModule, ArrayTy, false, GlobalVariable::PrivateLinkage,
736  Constant::getNullValue(ArrayTy), "__sancov_gen_");
737 
738  if (TargetTriple.supportsCOMDAT() &&
739  (TargetTriple.isOSBinFormatELF() || !F.isInterposable()))
740  if (auto Comdat = getOrCreateFunctionComdat(F, TargetTriple))
741  Array->setComdat(Comdat);
742  Array->setSection(getSectionName(Section));
743  Array->setAlignment(Align(DL->getTypeStoreSize(Ty).getFixedSize()));
744 
745  // sancov_pcs parallels the other metadata section(s). Optimizers (e.g.
746  // GlobalOpt/ConstantMerge) may not discard sancov_pcs and the other
747  // section(s) as a unit, so we conservatively retain all unconditionally in
748  // the compiler.
749  //
750  // With comdat (COFF/ELF), the linker can guarantee the associated sections
751  // will be retained or discarded as a unit, so llvm.compiler.used is
752  // sufficient. Otherwise, conservatively make all of them retained by the
753  // linker.
754  if (Array->hasComdat())
755  GlobalsToAppendToCompilerUsed.push_back(Array);
756  else
757  GlobalsToAppendToUsed.push_back(Array);
758 
759  return Array;
760 }
761 
763 ModuleSanitizerCoverage::CreatePCArray(Function &F,
764  ArrayRef<BasicBlock *> AllBlocks) {
765  size_t N = AllBlocks.size();
766  assert(N);
768  IRBuilder<> IRB(&*F.getEntryBlock().getFirstInsertionPt());
769  for (size_t i = 0; i < N; i++) {
770  if (&F.getEntryBlock() == AllBlocks[i]) {
771  PCs.push_back((Constant *)IRB.CreatePointerCast(&F, IntptrPtrTy));
772  PCs.push_back((Constant *)IRB.CreateIntToPtr(
773  ConstantInt::get(IntptrTy, 1), IntptrPtrTy));
774  } else {
775  PCs.push_back((Constant *)IRB.CreatePointerCast(
776  BlockAddress::get(AllBlocks[i]), IntptrPtrTy));
777  PCs.push_back((Constant *)IRB.CreateIntToPtr(
778  ConstantInt::get(IntptrTy, 0), IntptrPtrTy));
779  }
780  }
781  auto *PCArray = CreateFunctionLocalArrayInSection(N * 2, F, IntptrPtrTy,
783  PCArray->setInitializer(
784  ConstantArray::get(ArrayType::get(IntptrPtrTy, N * 2), PCs));
785  PCArray->setConstant(true);
786 
787  return PCArray;
788 }
789 
790 void ModuleSanitizerCoverage::CreateFunctionLocalArrays(
791  Function &F, ArrayRef<BasicBlock *> AllBlocks) {
792  if (Options.TracePCGuard)
793  FunctionGuardArray = CreateFunctionLocalArrayInSection(
794  AllBlocks.size(), F, Int32Ty, SanCovGuardsSectionName);
795 
796  if (Options.Inline8bitCounters)
797  Function8bitCounterArray = CreateFunctionLocalArrayInSection(
798  AllBlocks.size(), F, Int8Ty, SanCovCountersSectionName);
799  if (Options.InlineBoolFlag)
800  FunctionBoolArray = CreateFunctionLocalArrayInSection(
801  AllBlocks.size(), F, Int1Ty, SanCovBoolFlagSectionName);
802 
803  if (Options.PCTable)
804  FunctionPCsArray = CreatePCArray(F, AllBlocks);
805 }
806 
807 bool ModuleSanitizerCoverage::InjectCoverage(Function &F,
808  ArrayRef<BasicBlock *> AllBlocks,
809  bool IsLeafFunc) {
810  if (AllBlocks.empty()) return false;
811  CreateFunctionLocalArrays(F, AllBlocks);
812  for (size_t i = 0, N = AllBlocks.size(); i < N; i++)
813  InjectCoverageAtBlock(F, *AllBlocks[i], i, IsLeafFunc);
814  return true;
815 }
816 
817 // On every indirect call we call a run-time function
818 // __sanitizer_cov_indir_call* with two parameters:
819 // - callee address,
820 // - global cache array that contains CacheSize pointers (zero-initialized).
821 // The cache is used to speed up recording the caller-callee pairs.
822 // The address of the caller is passed implicitly via caller PC.
823 // CacheSize is encoded in the name of the run-time function.
824 void ModuleSanitizerCoverage::InjectCoverageForIndirectCalls(
825  Function &F, ArrayRef<Instruction *> IndirCalls) {
826  if (IndirCalls.empty())
827  return;
828  assert(Options.TracePC || Options.TracePCGuard ||
829  Options.Inline8bitCounters || Options.InlineBoolFlag);
830  for (auto I : IndirCalls) {
831  IRBuilder<> IRB(I);
832  CallBase &CB = cast<CallBase>(*I);
833  Value *Callee = CB.getCalledOperand();
834  if (isa<InlineAsm>(Callee))
835  continue;
836  IRB.CreateCall(SanCovTracePCIndir, IRB.CreatePointerCast(Callee, IntptrTy));
837  }
838 }
839 
840 // For every switch statement we insert a call:
841 // __sanitizer_cov_trace_switch(CondValue,
842 // {NumCases, ValueSizeInBits, Case0Value, Case1Value, Case2Value, ... })
843 
844 void ModuleSanitizerCoverage::InjectTraceForSwitch(
845  Function &, ArrayRef<Instruction *> SwitchTraceTargets) {
846  for (auto I : SwitchTraceTargets) {
847  if (SwitchInst *SI = dyn_cast<SwitchInst>(I)) {
848  IRBuilder<> IRB(I);
849  SmallVector<Constant *, 16> Initializers;
850  Value *Cond = SI->getCondition();
851  if (Cond->getType()->getScalarSizeInBits() >
852  Int64Ty->getScalarSizeInBits())
853  continue;
854  Initializers.push_back(ConstantInt::get(Int64Ty, SI->getNumCases()));
855  Initializers.push_back(
856  ConstantInt::get(Int64Ty, Cond->getType()->getScalarSizeInBits()));
857  if (Cond->getType()->getScalarSizeInBits() <
858  Int64Ty->getScalarSizeInBits())
859  Cond = IRB.CreateIntCast(Cond, Int64Ty, false);
860  for (auto It : SI->cases()) {
861  Constant *C = It.getCaseValue();
862  if (C->getType()->getScalarSizeInBits() <
863  Int64Ty->getScalarSizeInBits())
864  C = ConstantExpr::getCast(CastInst::ZExt, It.getCaseValue(), Int64Ty);
865  Initializers.push_back(C);
866  }
867  llvm::sort(drop_begin(Initializers, 2),
868  [](const Constant *A, const Constant *B) {
869  return cast<ConstantInt>(A)->getLimitedValue() <
870  cast<ConstantInt>(B)->getLimitedValue();
871  });
872  ArrayType *ArrayOfInt64Ty = ArrayType::get(Int64Ty, Initializers.size());
873  GlobalVariable *GV = new GlobalVariable(
874  *CurModule, ArrayOfInt64Ty, false, GlobalVariable::InternalLinkage,
875  ConstantArray::get(ArrayOfInt64Ty, Initializers),
876  "__sancov_gen_cov_switch_values");
877  IRB.CreateCall(SanCovTraceSwitchFunction,
878  {Cond, IRB.CreatePointerCast(GV, Int64PtrTy)});
879  }
880  }
881 }
882 
883 void ModuleSanitizerCoverage::InjectTraceForDiv(
884  Function &, ArrayRef<BinaryOperator *> DivTraceTargets) {
885  for (auto BO : DivTraceTargets) {
886  IRBuilder<> IRB(BO);
887  Value *A1 = BO->getOperand(1);
888  if (isa<ConstantInt>(A1)) continue;
889  if (!A1->getType()->isIntegerTy())
890  continue;
891  uint64_t TypeSize = DL->getTypeStoreSizeInBits(A1->getType());
892  int CallbackIdx = TypeSize == 32 ? 0 :
893  TypeSize == 64 ? 1 : -1;
894  if (CallbackIdx < 0) continue;
895  auto Ty = Type::getIntNTy(*C, TypeSize);
896  IRB.CreateCall(SanCovTraceDivFunction[CallbackIdx],
897  {IRB.CreateIntCast(A1, Ty, true)});
898  }
899 }
900 
901 void ModuleSanitizerCoverage::InjectTraceForGep(
902  Function &, ArrayRef<GetElementPtrInst *> GepTraceTargets) {
903  for (auto GEP : GepTraceTargets) {
904  IRBuilder<> IRB(GEP);
905  for (Use &Idx : GEP->indices())
906  if (!isa<ConstantInt>(Idx) && Idx->getType()->isIntegerTy())
907  IRB.CreateCall(SanCovTraceGepFunction,
908  {IRB.CreateIntCast(Idx, IntptrTy, true)});
909  }
910 }
911 
912 void ModuleSanitizerCoverage::InjectTraceForLoadsAndStores(
914  auto CallbackIdx = [&](Type *ElementTy) -> int {
915  uint64_t TypeSize = DL->getTypeStoreSizeInBits(ElementTy);
916  return TypeSize == 8 ? 0
917  : TypeSize == 16 ? 1
918  : TypeSize == 32 ? 2
919  : TypeSize == 64 ? 3
920  : TypeSize == 128 ? 4
921  : -1;
922  };
923  Type *PointerType[5] = {Int8PtrTy, Int16PtrTy, Int32PtrTy, Int64PtrTy,
924  Int128PtrTy};
925  for (auto LI : Loads) {
926  IRBuilder<> IRB(LI);
927  auto Ptr = LI->getPointerOperand();
928  int Idx = CallbackIdx(LI->getType());
929  if (Idx < 0)
930  continue;
931  IRB.CreateCall(SanCovLoadFunction[Idx],
932  IRB.CreatePointerCast(Ptr, PointerType[Idx]));
933  }
934  for (auto SI : Stores) {
935  IRBuilder<> IRB(SI);
936  auto Ptr = SI->getPointerOperand();
937  int Idx = CallbackIdx(SI->getValueOperand()->getType());
938  if (Idx < 0)
939  continue;
940  IRB.CreateCall(SanCovStoreFunction[Idx],
941  IRB.CreatePointerCast(Ptr, PointerType[Idx]));
942  }
943 }
944 
945 void ModuleSanitizerCoverage::InjectTraceForCmp(
946  Function &, ArrayRef<Instruction *> CmpTraceTargets) {
947  for (auto I : CmpTraceTargets) {
948  if (ICmpInst *ICMP = dyn_cast<ICmpInst>(I)) {
949  IRBuilder<> IRB(ICMP);
950  Value *A0 = ICMP->getOperand(0);
951  Value *A1 = ICMP->getOperand(1);
952  if (!A0->getType()->isIntegerTy())
953  continue;
954  uint64_t TypeSize = DL->getTypeStoreSizeInBits(A0->getType());
955  int CallbackIdx = TypeSize == 8 ? 0 :
956  TypeSize == 16 ? 1 :
957  TypeSize == 32 ? 2 :
958  TypeSize == 64 ? 3 : -1;
959  if (CallbackIdx < 0) continue;
960  // __sanitizer_cov_trace_cmp((type_size << 32) | predicate, A0, A1);
961  auto CallbackFunc = SanCovTraceCmpFunction[CallbackIdx];
962  bool FirstIsConst = isa<ConstantInt>(A0);
963  bool SecondIsConst = isa<ConstantInt>(A1);
964  // If both are const, then we don't need such a comparison.
965  if (FirstIsConst && SecondIsConst) continue;
966  // If only one is const, then make it the first callback argument.
967  if (FirstIsConst || SecondIsConst) {
968  CallbackFunc = SanCovTraceConstCmpFunction[CallbackIdx];
969  if (SecondIsConst)
970  std::swap(A0, A1);
971  }
972 
973  auto Ty = Type::getIntNTy(*C, TypeSize);
974  IRB.CreateCall(CallbackFunc, {IRB.CreateIntCast(A0, Ty, true),
975  IRB.CreateIntCast(A1, Ty, true)});
976  }
977  }
978 }
979 
980 void ModuleSanitizerCoverage::InjectCoverageAtBlock(Function &F, BasicBlock &BB,
981  size_t Idx,
982  bool IsLeafFunc) {
983  BasicBlock::iterator IP = BB.getFirstInsertionPt();
984  bool IsEntryBB = &BB == &F.getEntryBlock();
985  DebugLoc EntryLoc;
986  if (IsEntryBB) {
987  if (auto SP = F.getSubprogram())
988  EntryLoc = DILocation::get(SP->getContext(), SP->getScopeLine(), 0, SP);
989  // Keep static allocas and llvm.localescape calls in the entry block. Even
990  // if we aren't splitting the block, it's nice for allocas to be before
991  // calls.
993  }
994 
996  if (EntryLoc)
997  IRB.SetCurrentDebugLocation(EntryLoc);
998  if (Options.TracePC) {
999  IRB.CreateCall(SanCovTracePC)
1000  ->setCannotMerge(); // gets the PC using GET_CALLER_PC.
1001  }
1002  if (Options.TracePCGuard) {
1003  auto GuardPtr = IRB.CreateIntToPtr(
1004  IRB.CreateAdd(IRB.CreatePointerCast(FunctionGuardArray, IntptrTy),
1005  ConstantInt::get(IntptrTy, Idx * 4)),
1006  Int32PtrTy);
1007  IRB.CreateCall(SanCovTracePCGuard, GuardPtr)->setCannotMerge();
1008  }
1009  if (Options.Inline8bitCounters) {
1010  auto CounterPtr = IRB.CreateGEP(
1011  Function8bitCounterArray->getValueType(), Function8bitCounterArray,
1012  {ConstantInt::get(IntptrTy, 0), ConstantInt::get(IntptrTy, Idx)});
1013  auto Load = IRB.CreateLoad(Int8Ty, CounterPtr);
1014  auto Inc = IRB.CreateAdd(Load, ConstantInt::get(Int8Ty, 1));
1015  auto Store = IRB.CreateStore(Inc, CounterPtr);
1016  SetNoSanitizeMetadata(Load);
1017  SetNoSanitizeMetadata(Store);
1018  }
1019  if (Options.InlineBoolFlag) {
1020  auto FlagPtr = IRB.CreateGEP(
1021  FunctionBoolArray->getValueType(), FunctionBoolArray,
1022  {ConstantInt::get(IntptrTy, 0), ConstantInt::get(IntptrTy, Idx)});
1023  auto Load = IRB.CreateLoad(Int1Ty, FlagPtr);
1024  auto ThenTerm =
1025  SplitBlockAndInsertIfThen(IRB.CreateIsNull(Load), &*IP, false);
1026  IRBuilder<> ThenIRB(ThenTerm);
1027  auto Store = ThenIRB.CreateStore(ConstantInt::getTrue(Int1Ty), FlagPtr);
1028  SetNoSanitizeMetadata(Load);
1029  SetNoSanitizeMetadata(Store);
1030  }
1031  if (Options.StackDepth && IsEntryBB && !IsLeafFunc) {
1032  // Check stack depth. If it's the deepest so far, record it.
1033  Module *M = F.getParent();
1034  Function *GetFrameAddr = Intrinsic::getDeclaration(
1035  M, Intrinsic::frameaddress,
1036  IRB.getInt8PtrTy(M->getDataLayout().getAllocaAddrSpace()));
1037  auto FrameAddrPtr =
1038  IRB.CreateCall(GetFrameAddr, {Constant::getNullValue(Int32Ty)});
1039  auto FrameAddrInt = IRB.CreatePtrToInt(FrameAddrPtr, IntptrTy);
1040  auto LowestStack = IRB.CreateLoad(IntptrTy, SanCovLowestStack);
1041  auto IsStackLower = IRB.CreateICmpULT(FrameAddrInt, LowestStack);
1042  auto ThenTerm = SplitBlockAndInsertIfThen(IsStackLower, &*IP, false);
1043  IRBuilder<> ThenIRB(ThenTerm);
1044  auto Store = ThenIRB.CreateStore(FrameAddrInt, SanCovLowestStack);
1045  SetNoSanitizeMetadata(LowestStack);
1046  SetNoSanitizeMetadata(Store);
1047  }
1048 }
1049 
1050 std::string
1051 ModuleSanitizerCoverage::getSectionName(const std::string &Section) const {
1052  if (TargetTriple.isOSBinFormatCOFF()) {
1053  if (Section == SanCovCountersSectionName)
1054  return ".SCOV$CM";
1055  if (Section == SanCovBoolFlagSectionName)
1056  return ".SCOV$BM";
1057  if (Section == SanCovPCsSectionName)
1058  return ".SCOVP$M";
1059  return ".SCOV$GM"; // For SanCovGuardsSectionName.
1060  }
1061  if (TargetTriple.isOSBinFormatMachO())
1062  return "__DATA,__" + Section;
1063  return "__" + Section;
1064 }
1065 
1066 std::string
1067 ModuleSanitizerCoverage::getSectionStart(const std::string &Section) const {
1068  if (TargetTriple.isOSBinFormatMachO())
1069  return "\1section$start$__DATA$__" + Section;
1070  return "__start___" + Section;
1071 }
1072 
1073 std::string
1074 ModuleSanitizerCoverage::getSectionEnd(const std::string &Section) const {
1075  if (TargetTriple.isOSBinFormatMachO())
1076  return "\1section$end$__DATA$__" + Section;
1077  return "__stop___" + Section;
1078 }
1079 
1081 INITIALIZE_PASS_BEGIN(ModuleSanitizerCoverageLegacyPass, "sancov",
1082  "Pass for instrumenting coverage on functions", false,
1083  false)
1086 INITIALIZE_PASS_END(ModuleSanitizerCoverageLegacyPass, "sancov",
1087  "Pass for instrumenting coverage on functions", false,
1088  false)
1091  const std::vector<std::string> &AllowlistFiles,
1092  const std::vector<std::string> &BlocklistFiles) {
1093  return new ModuleSanitizerCoverageLegacyPass(Options, AllowlistFiles,
1094  BlocklistFiles);
1095 }
i
i
Definition: README.txt:29
ClInline8bitCounters
static cl::opt< bool > ClInline8bitCounters("sanitizer-coverage-inline-8bit-counters", cl::desc("increments 8-bit counter for every edge"), cl::Hidden, cl::init(false))
llvm::PreservedAnalyses
A set of analyses that are preserved following a run of a transformation pass.
Definition: PassManager.h:152
llvm::SpecialCaseList
Definition: SpecialCaseList.h:69
Instrumentation.h
llvm::isAsynchronousEHPersonality
bool isAsynchronousEHPersonality(EHPersonality Pers)
Returns true if this personality function catches asynchronous exceptions.
Definition: EHPersonalities.h:49
Int32Ty
IntegerType * Int32Ty
Definition: NVVMIntrRange.cpp:67
llvm::PrepareToSplitEntryBlock
BasicBlock::iterator PrepareToSplitEntryBlock(BasicBlock &BB, BasicBlock::iterator IP)
Instrumentation passes often insert conditional checks into entry blocks.
Definition: Instrumentation.cpp:41
INITIALIZE_PASS_BEGIN
INITIALIZE_PASS_BEGIN(ModuleSanitizerCoverageLegacyPass, "sancov", "Pass for instrumenting coverage on functions", false, false) INITIALIZE_PASS_END(ModuleSanitizerCoverageLegacyPass
llvm::GlobalObject::setComdat
void setComdat(Comdat *C)
Definition: Globals.cpp:190
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:17
llvm::Type::getInt1Ty
static IntegerType * getInt1Ty(LLVMContext &C)
Definition: Type.cpp:236
M
We currently emits eax Perhaps this is what we really should generate is Is imull three or four cycles eax eax The current instruction priority is based on pattern complexity The former is more complex because it folds a load so the latter will not be emitted Perhaps we should use AddedComplexity to give LEA32r a higher priority We should always try to match LEA first since the LEA matching code does some estimate to determine whether the match is profitable if we care more about code then imull is better It s two bytes shorter than movl leal On a Pentium M
Definition: README.txt:252
llvm::AArch64CC::AL
@ AL
Definition: AArch64BaseInfo.h:269
llvm::drop_begin
auto drop_begin(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the first N elements excluded.
Definition: STLExtras.h:280
SanCovTraceCmp2
const char SanCovTraceCmp2[]
Definition: SanitizerCoverage.cpp:45
ClGEPTracing
static cl::opt< bool > ClGEPTracing("sanitizer-coverage-trace-geps", cl::desc("Tracing of GEP instructions"), cl::Hidden, cl::init(false))
llvm::DataLayout
A parsed version of the target data layout string in and methods for querying it.
Definition: DataLayout.h:113
SanCovTracePCName
const char SanCovTracePCName[]
Definition: SanitizerCoverage.cpp:43
llvm::Intrinsic::getDeclaration
Function * getDeclaration(Module *M, ID id, ArrayRef< Type * > Tys=None)
Create or insert an LLVM Function declaration for an intrinsic, and return it.
Definition: Function.cpp:1410
llvm::BasicBlock::iterator
InstListType::iterator iterator
Instruction iterators...
Definition: BasicBlock.h:87
llvm::ModulePass
ModulePass class - This class is used to implement unstructured interprocedural optimizations and ana...
Definition: Pass.h:248
llvm::SanitizerCoverageOptions
Definition: Instrumentation.h:141
IntrinsicInst.h
llvm::AnalysisManager::getResult
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
Definition: PassManager.h:780
llvm::SystemZISD::ICMP
@ ICMP
Definition: SystemZISelLowering.h:55
functions
Pass for instrumenting coverage on functions
Definition: SanitizerCoverage.cpp:1087
llvm::GlobalValue::HiddenVisibility
@ HiddenVisibility
The GV is hidden.
Definition: GlobalValue.h:64
llvm::Function
Definition: Function.h:60
ClDIVTracing
static cl::opt< bool > ClDIVTracing("sanitizer-coverage-trace-divs", cl::desc("Tracing of DIV instructions"), cl::Hidden, cl::init(false))
llvm::SmallVector
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1185
llvm::AttributeList::addParamAttribute
LLVM_NODISCARD AttributeList addParamAttribute(LLVMContext &C, unsigned ArgNo, Attribute::AttrKind Kind) const
Add an argument attribute to the list.
Definition: Attributes.h:544
llvm::Function::getEntryBlock
const BasicBlock & getEntryBlock() const
Definition: Function.h:709
llvm::IRBuilder<>
SanCov8bitCountersInitName
const char SanCov8bitCountersInitName[]
Definition: SanitizerCoverage.cpp:75
llvm::GlobalVariable
Definition: GlobalVariable.h:39
SanCovTraceGep
const char SanCovTraceGep[]
Definition: SanitizerCoverage.cpp:64
SanCovModuleCtorBoolFlagName
const char SanCovModuleCtorBoolFlagName[]
Definition: SanitizerCoverage.cpp:70
llvm::DominatorTree
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
Definition: Dominators.h:166
llvm::Triple
Triple - Helper class for working with autoconf configuration names.
Definition: Triple.h:44
FAM
FunctionAnalysisManager FAM
Definition: PassBuilderBindings.cpp:59
llvm::cl::Hidden
@ Hidden
Definition: CommandLine.h:139
llvm::PreservedAnalyses::none
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
Definition: PassManager.h:155
llvm::Type
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
Module.h
llvm::AttributeList
Definition: Attributes.h:408
EHPersonalities.h
llvm::SPII::Load
@ Load
Definition: SparcInstrInfo.h:32
SanCovModuleCtor8bitCountersName
const char SanCovModuleCtor8bitCountersName[]
Definition: SanitizerCoverage.cpp:68
SanCovStore16
const char SanCovStore16[]
Definition: SanitizerCoverage.cpp:61
llvm::msgpack::Type::Array
@ Array
llvm::successors
auto successors(MachineBasicBlock *BB)
Definition: MachineSSAContext.h:29
ClInlineBoolFlag
static cl::opt< bool > ClInlineBoolFlag("sanitizer-coverage-inline-bool-flag", cl::desc("sets a boolean flag for every edge"), cl::Hidden, cl::init(false))
ClCreatePCTable
static cl::opt< bool > ClCreatePCTable("sanitizer-coverage-pc-table", cl::desc("create a static PC table"), cl::Hidden, cl::init(false))
llvm::GlobalValue::LinkageTypes
LinkageTypes
An enumeration for the kinds of linkage for global values.
Definition: GlobalValue.h:47
llvm::ArrayType
Class to represent array types.
Definition: DerivedTypes.h:357
llvm::succ_empty
bool succ_empty(const Instruction *I)
Definition: CFG.h:255
llvm::Type::getInt8Ty
static IntegerType * getInt8Ty(LLVMContext &C)
Definition: Type.cpp:237
ClLoadTracing
static cl::opt< bool > ClLoadTracing("sanitizer-coverage-trace-loads", cl::desc("Tracing of load instructions"), cl::Hidden, cl::init(false))
llvm::Type::getInt32Ty
static IntegerType * getInt32Ty(LLVMContext &C)
Definition: Type.cpp:239
llvm::ArrayRef::empty
bool empty() const
empty - Check if the array is empty.
Definition: ArrayRef.h:159
SanCovLowestStackName
const char SanCovLowestStackName[]
Definition: SanitizerCoverage.cpp:84
llvm::MDNode::get
static MDTuple * get(LLVMContext &Context, ArrayRef< Metadata * > MDs)
Definition: Metadata.h:1300
F
#define F(x, y, z)
Definition: MD5.cpp:55
llvm::BasicBlock::getUniqueSuccessor
const BasicBlock * getUniqueSuccessor() const
Return the successor of this block if it has a unique successor.
Definition: BasicBlock.cpp:299
llvm::BasicBlock
LLVM Basic Block Representation.
Definition: BasicBlock.h:55
llvm::ARMBuildAttrs::Section
@ Section
Legacy Tags.
Definition: ARMBuildAttributes.h:82
llvm::SanitizerCoverageOptions::SCK_Edge
@ SCK_Edge
Definition: Instrumentation.h:146
llvm::classifyEHPersonality
EHPersonality classifyEHPersonality(const Value *Pers)
See if the given exception handling personality function is one that we understand.
Definition: EHPersonalities.cpp:21
llvm::DominatorTree::dominates
bool dominates(const BasicBlock *BB, const Use &U) const
Return true if the (end of the) basic block BB dominates the use U.
Definition: Dominators.cpp:122
SanCovLoad2
const char SanCovLoad2[]
Definition: SanitizerCoverage.cpp:53
CommandLine.h
llvm::all_of
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
Definition: STLExtras.h:1607
llvm::SanitizerCoverageOptions::CoverageType
enum llvm::SanitizerCoverageOptions::Type CoverageType
SanCovBoolFlagInitName
const char SanCovBoolFlagInitName[]
Definition: SanitizerCoverage.cpp:76
llvm::PassRegistry::getPassRegistry
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
Definition: PassRegistry.cpp:31
PostDominators.h
SanCovTraceCmp4
const char SanCovTraceCmp4[]
Definition: SanitizerCoverage.cpp:46
SanCovStore4
const char SanCovStore4[]
Definition: SanitizerCoverage.cpp:59
Intrinsics.h
C
(vector float) vec_cmpeq(*A, *B) C
Definition: README_ALTIVEC.txt:86
MAM
ModuleAnalysisManager MAM
Definition: PassBuilderBindings.cpp:61
llvm::ModuleSanitizerCoveragePass::run
PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM)
Definition: SanitizerCoverage.cpp:331
llvm::PostDominatorTreeWrapperPass
Definition: PostDominators.h:73
SanCovPCsSectionName
const char SanCovPCsSectionName[]
Definition: SanitizerCoverage.cpp:82
llvm::AnalysisUsage
Represent the analysis usage information of a pass.
Definition: PassAnalysisSupport.h:47
isFullPostDominator
static bool isFullPostDominator(const BasicBlock *BB, const PostDominatorTree *PDT)
Definition: SanitizerCoverage.cpp:569
SanCovLoad4
const char SanCovLoad4[]
Definition: SanitizerCoverage.cpp:54
SanCovTraceDiv8
const char SanCovTraceDiv8[]
Definition: SanitizerCoverage.cpp:63
IP
Definition: NVPTXLowerArgs.cpp:167
llvm::CriticalEdgeSplittingOptions
Option class for critical edge splitting.
Definition: BasicBlockUtils.h:142
false
Definition: StackSlotColoring.cpp:141
B
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
llvm::Constant::getAllOnesValue
static Constant * getAllOnesValue(Type *Ty)
Definition: Constants.cpp:395
llvm::InstrumentationIRBuilder
Definition: Instrumentation.h:194
llvm::Instruction
Definition: Instruction.h:42
llvm::SPII::Store
@ Store
Definition: SparcInstrInfo.h:33
ClPruneBlocks
static cl::opt< bool > ClPruneBlocks("sanitizer-coverage-prune-blocks", cl::desc("Reduce the number of instrumented blocks"), cl::Hidden, cl::init(true))
llvm::DominatorTreeWrapperPass
Legacy analysis pass which computes a DominatorTree.
Definition: Dominators.h:302
llvm::appendToCompilerUsed
void appendToCompilerUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.compiler.used list.
Definition: ModuleUtils.cpp:109
Options
const char LLVMTargetMachineRef LLVMPassBuilderOptionsRef Options
Definition: PassBuilderBindings.cpp:48
llvm::predecessors
auto predecessors(MachineBasicBlock *BB)
Definition: MachineSSAContext.h:30
llvm::initializeModuleSanitizerCoverageLegacyPassPass
void initializeModuleSanitizerCoverageLegacyPassPass(PassRegistry &)
llvm::ConstantInt::get
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.
Definition: Constants.cpp:919
SanCovGuardsSectionName
const char SanCovGuardsSectionName[]
Definition: SanitizerCoverage.cpp:79
Align
uint64_t Align
Definition: ELFObjHandler.cpp:81
llvm::GlobalValue::InternalLinkage
@ InternalLinkage
Rename collisions when linking (static functions).
Definition: GlobalValue.h:55
llvm::Comdat
Definition: Comdat.h:33
llvm::SanitizerCoverageOptions::SCK_BB
@ SCK_BB
Definition: Instrumentation.h:145
SanCovTraceConstCmp8
const char SanCovTraceConstCmp8[]
Definition: SanitizerCoverage.cpp:51
shouldInstrumentBlock
static bool shouldInstrumentBlock(const Function &F, const BasicBlock *BB, const DominatorTree *DT, const PostDominatorTree *PDT, const SanitizerCoverageOptions &Options)
Definition: SanitizerCoverage.cpp:579
llvm::None
const NoneType None
Definition: None.h:24
llvm::CallingConv::ID
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition: CallingConv.h:24
SanCovTraceSwitchName
const char SanCovTraceSwitchName[]
Definition: SanitizerCoverage.cpp:65
Type.h
INITIALIZE_PASS_END
#define INITIALIZE_PASS_END(passName, arg, name, cfg, analysis)
Definition: PassSupport.h:58
llvm::Type::isIntegerTy
bool isIntegerTy() const
True if this is an instance of IntegerType.
Definition: Type.h:191
llvm::function_ref
An efficient, type-erasing, non-owning reference to a callable.
Definition: STLFunctionalExtras.h:36
llvm::cl::opt
Definition: CommandLine.h:1392
llvm::StoreInst
An instruction for storing to memory.
Definition: Instructions.h:305
llvm::Constant
This is an important base class in LLVM.
Definition: Constant.h:41
llvm::vfs::getRealFileSystem
IntrusiveRefCntPtr< FileSystem > getRealFileSystem()
Gets an vfs::FileSystem for the 'real' file system, as seen by the operating system.
Definition: VirtualFileSystem.cpp:376
llvm::PointerType::getUnqual
static PointerType * getUnqual(Type *ElementType)
This constructs a pointer to an object of the specified type in the default address space (address sp...
Definition: DerivedTypes.h:651
llvm::createSanitizerCtorAndInitFunctions
std::pair< Function *, FunctionCallee > createSanitizerCtorAndInitFunctions(Module &M, StringRef CtorName, StringRef InitName, ArrayRef< Type * > InitArgTypes, ArrayRef< Value * > InitArgs, StringRef VersionCheckName=StringRef())
Creates sanitizer constructor function, and calls sanitizer's init function from it.
Definition: ModuleUtils.cpp:135
llvm::ICmpInst
This instruction compares its operands according to the predicate given to the constructor.
Definition: Instructions.h:1186
uint64_t
const
aarch64 promote const
Definition: AArch64PromoteConstant.cpp:232
SanCovBoolFlagSectionName
const char SanCovBoolFlagSectionName[]
Definition: SanitizerCoverage.cpp:81
INITIALIZE_PASS_DEPENDENCY
INITIALIZE_PASS_DEPENDENCY(DominatorTreeWrapperPass)
sancov
sancov
Definition: SanitizerCoverage.cpp:1086
llvm::LLVMContext
This is an important class for using LLVM in a threaded context.
Definition: LLVMContext.h:68
llvm::declareSanitizerInitFunction
FunctionCallee declareSanitizerInitFunction(Module &M, StringRef InitName, ArrayRef< Type * > InitArgTypes)
Definition: ModuleUtils.cpp:114
I
#define I(x, y, z)
Definition: MD5.cpp:58
ClCoverageLevel
static cl::opt< int > ClCoverageLevel("sanitizer-coverage-level", cl::desc("Sanitizer Coverage. 0: none, 1: entry block, 2: all blocks, " "3: all blocks and critical edges"), cl::Hidden, cl::init(0))
SanCovStore8
const char SanCovStore8[]
Definition: SanitizerCoverage.cpp:60
llvm::GetElementPtrInst
an instruction for type-safe pointer arithmetic to access elements of arrays and structs
Definition: Instructions.h:929
llvm::cl::init
initializer< Ty > init(const Ty &Val)
Definition: CommandLine.h:432
llvm::appendToUsed
void appendToUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.used list.
Definition: ModuleUtils.cpp:105
llvm::PointerType
Class to represent pointers.
Definition: DerivedTypes.h:632
llvm::GlobalValue::setLinkage
void setLinkage(LinkageTypes LT)
Definition: GlobalValue.h:459
ArrayRef.h
llvm::SpecialCaseList::createOrDie
static std::unique_ptr< SpecialCaseList > createOrDie(const std::vector< std::string > &Paths, llvm::vfs::FileSystem &FS)
Parses the special case list entries from files.
Definition: SpecialCaseList.cpp:90
IRBuilder.h
ClTracePC
static cl::opt< bool > ClTracePC("sanitizer-coverage-trace-pc", cl::desc("Experimental pc tracing"), cl::Hidden, cl::init(false))
assert
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
SanCovTraceCmp1
const char SanCovTraceCmp1[]
Definition: SanitizerCoverage.cpp:44
std::swap
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition: BitVector.h:853
SI
StandardInstrumentations SI(Debug, VerifyEach)
SanCovTracePCGuardInitName
const char SanCovTracePCGuardInitName[]
Definition: SanitizerCoverage.cpp:74
llvm::ConstantExpr::getCast
static Constant * getCast(unsigned ops, Constant *C, Type *Ty, bool OnlyIfReduced=false)
Convenience function for getting a Cast operation.
Definition: Constants.cpp:2002
SanCovModuleCtorTracePcGuardName
const char SanCovModuleCtorTracePcGuardName[]
Definition: SanitizerCoverage.cpp:66
IsInterestingCmp
static bool IsInterestingCmp(ICmpInst *CMP, const DominatorTree *DT, const SanitizerCoverageOptions &Options)
Definition: SanitizerCoverage.cpp:629
llvm::ArrayType::get
static ArrayType * get(Type *ElementType, uint64_t NumElements)
This static method is the primary way to construct an ArrayType.
Definition: Type.cpp:638
llvm::Module
A Module instance is used to store all the information related to an LLVM module.
Definition: Module.h:65
ClCMPTracing
static cl::opt< bool > ClCMPTracing("sanitizer-coverage-trace-compares", cl::desc("Tracing of CMP and similar instructions"), cl::Hidden, cl::init(false))
Triple.h
SanCovTracePCIndirName
const char SanCovTracePCIndirName[]
Definition: SanitizerCoverage.cpp:42
ClStoreTracing
static cl::opt< bool > ClStoreTracing("sanitizer-coverage-trace-stores", cl::desc("Tracing of store instructions"), cl::Hidden, cl::init(false))
llvm::ArrayRef
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: APInt.h:32
llvm::BinaryOperator
Definition: InstrTypes.h:188
SanCovLoad1
const char SanCovLoad1[]
Definition: SanitizerCoverage.cpp:52
DataLayout.h
Cond
SmallVector< MachineOperand, 4 > Cond
Definition: BasicBlockSections.cpp:178
llvm::StringRef
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:58
SanCovTracePCGuardName
const char SanCovTracePCGuardName[]
Definition: SanitizerCoverage.cpp:73
llvm::SanitizerCoverageOptions::SCK_Function
@ SCK_Function
Definition: Instrumentation.h:144
SanitizerCoverage.h
llvm::PostDominatorTree
PostDominatorTree Class - Concrete subclass of DominatorTree that is used to compute the post-dominat...
Definition: PostDominators.h:28
llvm::Value::getType
Type * getType() const
All values are typed, get the type of this value.
Definition: Value.h:255
llvm::GlobalValue::WeakODRLinkage
@ WeakODRLinkage
Same, but only replaced by something equivalent.
Definition: GlobalValue.h:53
DL
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Definition: AArch64SLSHardening.cpp:76
llvm::pred_empty
bool pred_empty(const BasicBlock *BB)
Definition: CFG.h:118
ClTracePCGuard
static cl::opt< bool > ClTracePCGuard("sanitizer-coverage-trace-pc-guard", cl::desc("pc tracing with a guard"), cl::Hidden, cl::init(false))
llvm::GlobalValue::AvailableExternallyLinkage
@ AvailableExternallyLinkage
Available for inspection, not emission.
Definition: GlobalValue.h:49
llvm::Value::getName
StringRef getName() const
Return a constant reference to the value's name.
Definition: Value.cpp:305
for
this could be done in SelectionDAGISel along with other special for
Definition: README.txt:104
llvm::LoadInst
An instruction for reading from memory.
Definition: Instructions.h:176
VirtualFileSystem.h
SanCovLoad16
const char SanCovLoad16[]
Definition: SanitizerCoverage.cpp:56
Callee
amdgpu Simplify well known AMD library false FunctionCallee Callee
Definition: AMDGPULibCalls.cpp:186
SanCovTraceConstCmp1
const char SanCovTraceConstCmp1[]
Definition: SanitizerCoverage.cpp:48
Constant.h
llvm::ConstantInt::getTrue
static ConstantInt * getTrue(LLVMContext &Context)
Definition: Constants.cpp:867
std
Definition: BitVector.h:851
llvm::Constant::getNullValue
static Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
Definition: Constants.cpp:350
llvm::Type::getIntNTy
static IntegerType * getIntNTy(LLVMContext &C, unsigned N)
Definition: Type.cpp:243
llvm::PreservedAnalyses::all
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
Definition: PassManager.h:158
llvm::ISD::BR
@ BR
Control flow instructions. These all have token chains.
Definition: ISDOpcodes.h:975
GlobalVariable.h
llvm::TypeSize
Definition: TypeSize.h:421
llvm::getOrCreateFunctionComdat
Comdat * getOrCreateFunctionComdat(Function &F, Triple &T)
Definition: Instrumentation.cpp:76
Function.h
llvm::sort
void sort(IteratorTy Start, IteratorTy End)
Definition: STLExtras.h:1552
llvm::CallBase::isIndirectCall
bool isIndirectCall() const
Return true if the callsite is an indirect call.
Definition: Instructions.cpp:289
SpecialCaseList.h
llvm::getUniqueModuleId
std::string getUniqueModuleId(Module *M)
Produce a unique identifier for this module by taking the MD5 sum of the names of the module's strong...
Definition: ModuleUtils.cpp:207
llvm::ConstantArray::get
static Constant * get(ArrayType *T, ArrayRef< Constant * > V)
Definition: Constants.cpp:1282
isFullDominator
static bool isFullDominator(const BasicBlock *BB, const DominatorTree *DT)
Definition: SanitizerCoverage.cpp:559
llvm::SanitizerCoverageOptions::SCK_None
@ SCK_None
Definition: Instrumentation.h:143
llvm::CallBase::getCalledOperand
Value * getCalledOperand() const
Definition: InstrTypes.h:1389
SanCovTraceConstCmp4
const char SanCovTraceConstCmp4[]
Definition: SanitizerCoverage.cpp:50
SanCovTraceCmp8
const char SanCovTraceCmp8[]
Definition: SanitizerCoverage.cpp:47
llvm::GlobalValue::ExternalLinkage
@ ExternalLinkage
Externally visible function.
Definition: GlobalValue.h:48
llvm::DominatorTreeAnalysis
Analysis pass which computes a DominatorTree.
Definition: Dominators.h:267
llvm::Type::getVoidTy
static Type * getVoidTy(LLVMContext &C)
Definition: Type.cpp:222
llvm::SplitAllCriticalEdges
unsigned SplitAllCriticalEdges(Function &F, const CriticalEdgeSplittingOptions &Options=CriticalEdgeSplittingOptions())
Loop over all of the edges in the CFG, breaking critical edges as they are found.
Definition: BasicBlockUtils.cpp:767
llvm::Pass
Pass interface - Implemented by all 'passes'.
Definition: Pass.h:91
llvm::GlobalValue::PrivateLinkage
@ PrivateLinkage
Like Internal, but omit from symbol table.
Definition: GlobalValue.h:56
SmallVector.h
Dominators.h
llvm::ARCISD::CMP
@ CMP
Definition: ARCISelLowering.h:40
ModuleUtils.h
N
#define N
llvm::BlockAddress::get
static BlockAddress * get(Function *F, BasicBlock *BB)
Return a BlockAddress for the specified function and basic block.
Definition: Constants.cpp:1807
llvm::ArrayRef::size
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:164
llvm::max
Align max(MaybeAlign Lhs, Align Rhs)
Definition: Alignment.h:340
SanCovTraceDiv4
const char SanCovTraceDiv4[]
Definition: SanitizerCoverage.cpp:62
SanCtorAndDtorPriority
static const uint64_t SanCtorAndDtorPriority
Definition: SanitizerCoverage.cpp:71
llvm::FunctionCallee
A handy container for a FunctionType+Callee-pointer pair, which can be passed around as a single enti...
Definition: DerivedTypes.h:165
llvm::BasicBlock::getTerminator
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction if the block is well formed or null if the block is not well forme...
Definition: BasicBlock.h:119
SanCovTraceConstCmp2
const char SanCovTraceConstCmp2[]
Definition: SanitizerCoverage.cpp:49
llvm::CallBase
Base class for all callable instructions (InvokeInst and CallInst) Holds everything related to callin...
Definition: InstrTypes.h:1174
llvm::Type::getInt16Ty
static IntegerType * getInt16Ty(LLVMContext &C)
Definition: Type.cpp:238
llvm::AnalysisManager
A container for analyses that lazily runs them and caches their results.
Definition: InstructionSimplify.h:42
SanCovPCsInitName
const char SanCovPCsInitName[]
Definition: SanitizerCoverage.cpp:77
llvm::InnerAnalysisManagerProxy
An analysis over an "outer" IR unit that provides access to an analysis manager over an "inner" IR un...
Definition: PassManager.h:937
BB
Common register allocation spilling lr str ldr sxth r3 ldr mla r4 can lr mov lr str ldr sxth r3 mla r4 and then merge mul and lr str ldr sxth r3 mla r4 It also increase the likelihood the store may become dead bb27 Successors according to LLVM BB
Definition: README.txt:39
GEP
Hexagon Common GEP
Definition: HexagonCommonGEP.cpp:172
llvm::PostDominatorTreeAnalysis
Analysis pass which computes a PostDominatorTree.
Definition: PostDominators.h:47
llvm::AnalysisUsage::addRequired
AnalysisUsage & addRequired()
Definition: PassAnalysisSupport.h:75
LLVMContext.h
From
BlockVerifier::State From
Definition: BlockVerifier.cpp:55
llvm::SwitchInst
Multiway switch.
Definition: Instructions.h:3243
llvm::DebugLoc
A debug info location.
Definition: DebugLoc.h:33
llvm::SplitBlockAndInsertIfThen
Instruction * SplitBlockAndInsertIfThen(Value *Cond, Instruction *SplitBefore, bool Unreachable, MDNode *BranchWeights, DominatorTree *DT, LoopInfo *LI=nullptr, BasicBlock *ThenBlock=nullptr)
Split the containing block at the specified instruction - everything before SplitBefore stays in the ...
Definition: BasicBlockUtils.cpp:1446
llvm::appendToGlobalCtors
void appendToGlobalCtors(Module &M, Function *F, int Priority, Constant *Data=nullptr)
Append F to the list of global ctors of module M with the given Priority.
Definition: ModuleUtils.cpp:65
llvm::cl::desc
Definition: CommandLine.h:405
llvm::SanitizerCoverageOptions::IndirectCalls
bool IndirectCalls
Definition: Instrumentation.h:148
llvm::GlobalValue::ExternalWeakLinkage
@ ExternalWeakLinkage
ExternalWeak linkage description.
Definition: GlobalValue.h:57
SanCovStore2
const char SanCovStore2[]
Definition: SanitizerCoverage.cpp:58
BasicBlockUtils.h
llvm::PostDominatorTree::dominates
bool dominates(const Instruction *I1, const Instruction *I2) const
Return true if I1 dominates I2.
Definition: PostDominators.cpp:54
llvm::GlobalValue::setVisibility
void setVisibility(VisibilityTypes V)
Definition: GlobalValue.h:234
SanCovStore1
const char SanCovStore1[]
Definition: SanitizerCoverage.cpp:57
InitializePasses.h
llvm::Value
LLVM Value Representation.
Definition: Value.h:74
IsBackEdge
static bool IsBackEdge(BasicBlock *From, BasicBlock *To, const DominatorTree *DT)
Definition: SanitizerCoverage.cpp:614
SanCovLoad8
const char SanCovLoad8[]
Definition: SanitizerCoverage.cpp:55
llvm::createModuleSanitizerCoverageLegacyPassPass
ModulePass * createModuleSanitizerCoverageLegacyPassPass(const SanitizerCoverageOptions &Options=SanitizerCoverageOptions(), const std::vector< std::string > &AllowlistFiles=std::vector< std::string >(), const std::vector< std::string > &BlocklistFiles=std::vector< std::string >())
Definition: SanitizerCoverage.cpp:1089
SanCovCountersSectionName
const char SanCovCountersSectionName[]
Definition: SanitizerCoverage.cpp:80
llvm::Use
A Use represents the edge between a Value definition and its users.
Definition: Use.h:43
llvm::Intrinsic::ID
unsigned ID
Definition: TargetTransformInfo.h:37
ClStackDepth
static cl::opt< bool > ClStackDepth("sanitizer-coverage-stack-depth", cl::desc("max stack depth tracing"), cl::Hidden, cl::init(false))