llvm.org GIT mirror llvm / 6140939
Remove top-level Clang -fsanitize= flags for optional ASan features. Init-order and use-after-return modes can currently be enabled by runtime flags. use-after-scope mode is not really working at the moment. The only problem I see is that users won't be able to disable extra instrumentation for init-order and use-after-scope by a top-level Clang flag. But this instrumentation was implicitly enabled for quite a while and we didn't hear from users hurt by it. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@210924 91177308-0d34-0410-b5e6-96231b3b80d8 Alexey Samsonov 5 years ago
5 changed file(s) with 21 addition(s) and 41 deletion(s). Raw diff Collapse all Expand all
6363 GCOVOptions::getDefault());
6464
6565 // Insert AddressSanitizer (address sanity checking) instrumentation
66 FunctionPass *createAddressSanitizerFunctionPass(
67 bool CheckInitOrder = true, bool CheckUseAfterReturn = false,
68 bool CheckLifetime = false);
69 ModulePass *createAddressSanitizerModulePass(
70 bool CheckInitOrder = true, StringRef BlacklistFile = StringRef());
66 FunctionPass *createAddressSanitizerFunctionPass();
67 ModulePass *
68 createAddressSanitizerModulePass(StringRef BlacklistFile = StringRef());
7169
7270 // Insert MemorySanitizer instrumentation (detection of uninitialized reads)
7371 FunctionPass *createMemorySanitizerPass(int TrackOrigins = 0);
127127 // This flag may need to be replaced with -f[no]asan-stack.
128128 static cl::opt ClStack("asan-stack",
129129 cl::desc("Handle stack memory"), cl::Hidden, cl::init(true));
130 // This flag may need to be replaced with -f[no]asan-use-after-return.
131130 static cl::opt ClUseAfterReturn("asan-use-after-return",
132 cl::desc("Check return-after-free"), cl::Hidden, cl::init(false));
131 cl::desc("Check return-after-free"), cl::Hidden, cl::init(true));
133132 // This flag may need to be replaced with -f[no]asan-globals.
134133 static cl::opt ClGlobals("asan-globals",
135134 cl::desc("Handle global objects"), cl::Hidden, cl::init(true));
141140 "are more than this number of blocks."),
142141 cl::Hidden, cl::init(1500));
143142 static cl::opt ClInitializers("asan-initialization-order",
144 cl::desc("Handle C++ initializer order"), cl::Hidden, cl::init(false));
143 cl::desc("Handle C++ initializer order"), cl::Hidden, cl::init(true));
145144 static cl::opt ClInvalidPointerPairs("asan-detect-invalid-pointer-pair",
146145 cl::desc("Instrument <, <=, >, >=, - with pointer operands"),
147146 cl::Hidden, cl::init(false));
304303
305304 /// AddressSanitizer: instrument the code in module to find memory bugs.
306305 struct AddressSanitizer : public FunctionPass {
307 AddressSanitizer(bool CheckInitOrder = true,
308 bool CheckUseAfterReturn = false,
309 bool CheckLifetime = false)
310 : FunctionPass(ID),
311 CheckInitOrder(CheckInitOrder || ClInitializers),
312 CheckUseAfterReturn(CheckUseAfterReturn || ClUseAfterReturn),
313 CheckLifetime(CheckLifetime || ClCheckLifetime) {}
306 AddressSanitizer() : FunctionPass(ID) {}
314307 const char *getPassName() const override {
315308 return "AddressSanitizerFunctionPass";
316309 }
338331 bool GlobalIsLinkerInitialized(GlobalVariable *G);
339332 bool InjectCoverage(Function &F, const ArrayRef AllBlocks);
340333 void InjectCoverageAtBlock(Function &F, BasicBlock &BB);
341
342 bool CheckInitOrder;
343 bool CheckUseAfterReturn;
344 bool CheckLifetime;
345334
346335 LLVMContext *C;
347336 const DataLayout *DL;
368357
369358 class AddressSanitizerModule : public ModulePass {
370359 public:
371 AddressSanitizerModule(bool CheckInitOrder = true,
372 StringRef BlacklistFile = StringRef())
373 : ModulePass(ID),
374 CheckInitOrder(CheckInitOrder || ClInitializers),
375 BlacklistFile(BlacklistFile.empty() ? ClBlacklistFile
376 : BlacklistFile) {}
360 AddressSanitizerModule(StringRef BlacklistFile = StringRef())
361 : ModulePass(ID), BlacklistFile(BlacklistFile.empty() ? ClBlacklistFile
362 : BlacklistFile) {}
377363 bool runOnModule(Module &M) override;
378364 static char ID; // Pass identification, replacement for typeid
379365 const char *getPassName() const override {
391377 return RedzoneSizeForScale(Mapping.Scale);
392378 }
393379
394 bool CheckInitOrder;
395380 SmallString<64> BlacklistFile;
396381
397382 std::unique_ptr BL;
492477 /// \brief Collect lifetime intrinsic calls to check for use-after-scope
493478 /// errors.
494479 void visitIntrinsicInst(IntrinsicInst &II) {
495 if (!ASan.CheckLifetime) return;
480 if (!ClCheckLifetime) return;
496481 Intrinsic::ID ID = II.getIntrinsicID();
497482 if (ID != Intrinsic::lifetime_start &&
498483 ID != Intrinsic::lifetime_end)
547532 INITIALIZE_PASS(AddressSanitizer, "asan",
548533 "AddressSanitizer: detects use-after-free and out-of-bounds bugs.",
549534 false, false)
550 FunctionPass *llvm::createAddressSanitizerFunctionPass(
551 bool CheckInitOrder, bool CheckUseAfterReturn, bool CheckLifetime) {
552 return new AddressSanitizer(CheckInitOrder, CheckUseAfterReturn,
553 CheckLifetime);
535 FunctionPass *llvm::createAddressSanitizerFunctionPass() {
536 return new AddressSanitizer();
554537 }
555538
556539 char AddressSanitizerModule::ID = 0;
557540 INITIALIZE_PASS(AddressSanitizerModule, "asan-module",
558541 "AddressSanitizer: detects use-after-free and out-of-bounds bugs."
559542 "ModulePass", false, false)
560 ModulePass *llvm::createAddressSanitizerModulePass(
561 bool CheckInitOrder, StringRef BlacklistFile) {
562 return new AddressSanitizerModule(CheckInitOrder, BlacklistFile);
543 ModulePass *llvm::createAddressSanitizerModulePass(StringRef BlacklistFile) {
544 return new AddressSanitizerModule(BlacklistFile);
563545 }
564546
565547 static size_t TypeSizeToSizeIndex(uint32_t TypeSize) {
700682 if (GlobalVariable *G = dyn_cast(Addr)) {
701683 // If initialization order checking is disabled, a simple access to a
702684 // dynamically initialized global is always valid.
703 if (!CheckInitOrder || GlobalIsLinkerInitialized(G)) {
685 if (!ClInitializers || GlobalIsLinkerInitialized(G)) {
704686 NumOptimizedAccessesToGlobalVar++;
705687 return;
706688 }
10761058 NULL);
10771059
10781060 // Populate the first and last globals declared in this TU.
1079 if (CheckInitOrder && GlobalHasDynamicInitializer)
1061 if (ClInitializers && GlobalHasDynamicInitializer)
10801062 HasDynamicallyInitializedGlobals = true;
10811063
10821064 DEBUG(dbgs() << "NEW GLOBAL: " << *NewGlobal << "\n");
10881070 ConstantArray::get(ArrayOfGlobalStructTy, Initializers), "");
10891071
10901072 // Create calls for poisoning before initializers run and unpoisoning after.
1091 if (CheckInitOrder && HasDynamicallyInitializedGlobals)
1073 if (HasDynamicallyInitializedGlobals)
10921074 createInitializerPoisonCalls(M, ModuleName);
10931075 IRB.CreateCall2(AsanRegisterGlobals,
10941076 IRB.CreatePointerCast(AllGlobals, IntptrTy),
15581540 DEBUG(dbgs() << L.DescriptionString << " --- " << L.FrameSize << "\n");
15591541 uint64_t LocalStackSize = L.FrameSize;
15601542 bool DoStackMalloc =
1561 ASan.CheckUseAfterReturn && LocalStackSize <= kMaxStackMallocSize;
1543 ClUseAfterReturn && LocalStackSize <= kMaxStackMallocSize;
15621544
15631545 Type *ByteArrayTy = ArrayType::get(IRB.getInt8Ty(), LocalStackSize);
15641546 AllocaInst *MyAlloca =
None ; RUN: opt < %s -asan -asan-module -S | FileCheck %s
0 ; RUN: opt < %s -asan -asan-module -asan-use-after-return=0 -S | FileCheck %s
11
22 ; Checks that llvm.dbg.declare instructions are updated
33 ; accordingly as we merge allocas.
0 ; Test hanlding of llvm.lifetime intrinsics.
1 ; RUN: opt < %s -asan -asan-module -asan-check-lifetime -S | FileCheck %s
1 ; RUN: opt < %s -asan -asan-module -asan-check-lifetime -asan-use-after-return=0 -S | FileCheck %s
22
33 target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128"
44 target triple = "x86_64-unknown-linux-gnu"
0 ; RUN: opt < %s -asan -asan-module -asan-use-after-return -S | FileCheck --check-prefix=CHECK-UAR %s
1 ; RUN: opt < %s -asan -asan-module -S | FileCheck --check-prefix=CHECK-PLAIN %s
1 ; RUN: opt < %s -asan -asan-module -asan-use-after-return=0 -S | FileCheck --check-prefix=CHECK-PLAIN %s
22 target datalayout = "e-i64:64-f80:128-s:64-n8:16:32:64-S128"
33 target triple = "x86_64-unknown-linux-gnu"
44