LLVM 23.0.0git
AddressSanitizer.cpp
Go to the documentation of this file.
1//===- AddressSanitizer.cpp - memory error detector -----------------------===//
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// This file is a part of AddressSanitizer, an address basic correctness
10// checker.
11// Details of the algorithm:
12// https://github.com/google/sanitizers/wiki/AddressSanitizerAlgorithm
13//
14// FIXME: This sanitizer does not yet handle scalable vectors
15//
16//===----------------------------------------------------------------------===//
17
19#include "llvm/ADT/ArrayRef.h"
20#include "llvm/ADT/DenseMap.h"
23#include "llvm/ADT/SmallSet.h"
25#include "llvm/ADT/Statistic.h"
27#include "llvm/ADT/StringRef.h"
28#include "llvm/ADT/Twine.h"
37#include "llvm/IR/Argument.h"
38#include "llvm/IR/Attributes.h"
39#include "llvm/IR/BasicBlock.h"
40#include "llvm/IR/Comdat.h"
41#include "llvm/IR/Constant.h"
42#include "llvm/IR/Constants.h"
43#include "llvm/IR/DIBuilder.h"
44#include "llvm/IR/DataLayout.h"
46#include "llvm/IR/DebugLoc.h"
49#include "llvm/IR/Function.h"
50#include "llvm/IR/GlobalAlias.h"
51#include "llvm/IR/GlobalValue.h"
53#include "llvm/IR/IRBuilder.h"
54#include "llvm/IR/InlineAsm.h"
55#include "llvm/IR/InstVisitor.h"
56#include "llvm/IR/InstrTypes.h"
57#include "llvm/IR/Instruction.h"
60#include "llvm/IR/Intrinsics.h"
61#include "llvm/IR/LLVMContext.h"
62#include "llvm/IR/MDBuilder.h"
63#include "llvm/IR/Metadata.h"
64#include "llvm/IR/Module.h"
65#include "llvm/IR/Type.h"
66#include "llvm/IR/Use.h"
67#include "llvm/IR/Value.h"
71#include "llvm/Support/Debug.h"
74#include "llvm/Support/ModRef.h"
85#include <algorithm>
86#include <cassert>
87#include <cstddef>
88#include <cstdint>
89#include <iomanip>
90#include <limits>
91#include <sstream>
92#include <string>
93#include <tuple>
94#include <utility>
95
96using namespace llvm;
97
98#define DEBUG_TYPE "asan"
99
101static const uint64_t kDefaultShadowOffset32 = 1ULL << 29;
102static const uint64_t kDefaultShadowOffset64 = 1ULL << 44;
104 std::numeric_limits<uint64_t>::max();
105static const uint64_t kSmallX86_64ShadowOffsetBase = 0x7FFFFFFF; // < 2G.
107static const uint64_t kLinuxKasan_ShadowOffset64 = 0xdffffc0000000000;
108static const uint64_t kPPC64_ShadowOffset64 = 1ULL << 44;
109static const uint64_t kSystemZ_ShadowOffset64 = 1ULL << 52;
110static const uint64_t kMIPS_ShadowOffsetN32 = 1ULL << 29;
111static const uint64_t kMIPS32_ShadowOffset32 = 0x0aaa0000;
112static const uint64_t kMIPS64_ShadowOffset64 = 1ULL << 37;
113static const uint64_t kAArch64_ShadowOffset64 = 1ULL << 36;
114static const uint64_t kLoongArch64_ShadowOffset64 = 1ULL << 46;
116static const uint64_t kFreeBSD_ShadowOffset32 = 1ULL << 30;
117static const uint64_t kFreeBSD_ShadowOffset64 = 1ULL << 46;
118static const uint64_t kFreeBSDAArch64_ShadowOffset64 = 1ULL << 47;
119static const uint64_t kFreeBSDKasan_ShadowOffset64 = 0xdffff7c000000000;
120static const uint64_t kNetBSD_ShadowOffset32 = 1ULL << 30;
121static const uint64_t kNetBSD_ShadowOffset64 = 1ULL << 46;
122static const uint64_t kNetBSDKasan_ShadowOffset64 = 0xdfff900000000000;
123static const uint64_t kPS_ShadowOffset64 = 1ULL << 40;
124static const uint64_t kWindowsShadowOffset32 = 3ULL << 28;
126
127// The shadow memory space is dynamically allocated.
129
130static const size_t kMinStackMallocSize = 1 << 6; // 64B
131static const size_t kMaxStackMallocSize = 1 << 16; // 64K
132static const uintptr_t kCurrentStackFrameMagic = 0x41B58AB3;
133static const uintptr_t kRetiredStackFrameMagic = 0x45E0360E;
134
135const char kAsanModuleCtorName[] = "asan.module_ctor";
136const char kAsanModuleDtorName[] = "asan.module_dtor";
138// On Emscripten, the system needs more than one priorities for constructors.
140const char kAsanReportErrorTemplate[] = "__asan_report_";
141const char kAsanRegisterGlobalsName[] = "__asan_register_globals";
142const char kAsanUnregisterGlobalsName[] = "__asan_unregister_globals";
143const char kAsanRegisterImageGlobalsName[] = "__asan_register_image_globals";
145 "__asan_unregister_image_globals";
146const char kAsanRegisterElfGlobalsName[] = "__asan_register_elf_globals";
147const char kAsanUnregisterElfGlobalsName[] = "__asan_unregister_elf_globals";
148const char kAsanPoisonGlobalsName[] = "__asan_before_dynamic_init";
149const char kAsanUnpoisonGlobalsName[] = "__asan_after_dynamic_init";
150const char kAsanInitName[] = "__asan_init";
151const char kAsanVersionCheckNamePrefix[] = "__asan_version_mismatch_check_v";
152const char kAsanPtrCmp[] = "__sanitizer_ptr_cmp";
153const char kAsanPtrSub[] = "__sanitizer_ptr_sub";
154const char kAsanHandleNoReturnName[] = "__asan_handle_no_return";
155static const int kMaxAsanStackMallocSizeClass = 10;
156const char kAsanStackMallocNameTemplate[] = "__asan_stack_malloc_";
158 "__asan_stack_malloc_always_";
159const char kAsanStackFreeNameTemplate[] = "__asan_stack_free_";
160const char kAsanGenPrefix[] = "___asan_gen_";
161const char kODRGenPrefix[] = "__odr_asan_gen_";
162const char kSanCovGenPrefix[] = "__sancov_gen_";
163const char kAsanSetShadowPrefix[] = "__asan_set_shadow_";
164const char kAsanPoisonStackMemoryName[] = "__asan_poison_stack_memory";
165const char kAsanUnpoisonStackMemoryName[] = "__asan_unpoison_stack_memory";
166
167// ASan version script has __asan_* wildcard. Triple underscore prevents a
168// linker (gold) warning about attempting to export a local symbol.
169const char kAsanGlobalsRegisteredFlagName[] = "___asan_globals_registered";
170
172 "__asan_option_detect_stack_use_after_return";
173
175 "__asan_shadow_memory_dynamic_address";
176
177const char kAsanAllocaPoison[] = "__asan_alloca_poison";
178const char kAsanAllocasUnpoison[] = "__asan_allocas_unpoison";
179
180const char kAMDGPUAddressSharedName[] = "llvm.amdgcn.is.shared";
181const char kAMDGPUAddressPrivateName[] = "llvm.amdgcn.is.private";
182const char kAMDGPUBallotName[] = "llvm.amdgcn.ballot.i64";
183const char kAMDGPUUnreachableName[] = "llvm.amdgcn.unreachable";
184
185// Accesses sizes are powers of two: 1, 2, 4, 8, 16.
186static const size_t kNumberOfAccessSizes = 5;
187
188static const uint64_t kAllocaRzSize = 32;
189
190// ASanAccessInfo implementation constants.
191constexpr size_t kCompileKernelShift = 0;
192constexpr size_t kCompileKernelMask = 0x1;
193constexpr size_t kAccessSizeIndexShift = 1;
194constexpr size_t kAccessSizeIndexMask = 0xf;
195constexpr size_t kIsWriteShift = 5;
196constexpr size_t kIsWriteMask = 0x1;
197
198// Command-line flags.
199
201 "asan-kernel", cl::desc("Enable KernelAddressSanitizer instrumentation"),
202 cl::Hidden, cl::init(false));
203
205 "asan-recover",
206 cl::desc("Enable recovery mode (continue-after-error)."),
207 cl::Hidden, cl::init(false));
208
210 "asan-guard-against-version-mismatch",
211 cl::desc("Guard against compiler/runtime version mismatch."), cl::Hidden,
212 cl::init(true));
213
214// This flag may need to be replaced with -f[no-]asan-reads.
215static cl::opt<bool> ClInstrumentReads("asan-instrument-reads",
216 cl::desc("instrument read instructions"),
217 cl::Hidden, cl::init(true));
218
220 "asan-instrument-writes", cl::desc("instrument write instructions"),
221 cl::Hidden, cl::init(true));
222
223static cl::opt<bool>
224 ClUseStackSafety("asan-use-stack-safety", cl::Hidden, cl::init(true),
225 cl::Hidden, cl::desc("Use Stack Safety analysis results"),
227
229 "asan-instrument-atomics",
230 cl::desc("instrument atomic instructions (rmw, cmpxchg)"), cl::Hidden,
231 cl::init(true));
232
233static cl::opt<bool>
234 ClInstrumentByval("asan-instrument-byval",
235 cl::desc("instrument byval call arguments"), cl::Hidden,
236 cl::init(true));
237
239 "asan-always-slow-path",
240 cl::desc("use instrumentation with slow path for all accesses"), cl::Hidden,
241 cl::init(false));
242
244 "asan-force-dynamic-shadow",
245 cl::desc("Load shadow address into a local variable for each function"),
246 cl::Hidden, cl::init(false));
247
248static cl::opt<bool>
249 ClWithIfunc("asan-with-ifunc",
250 cl::desc("Access dynamic shadow through an ifunc global on "
251 "platforms that support this"),
252 cl::Hidden, cl::init(true));
253
254static cl::opt<int>
255 ClShadowAddrSpace("asan-shadow-addr-space",
256 cl::desc("Address space for pointers to the shadow map"),
257 cl::Hidden, cl::init(0));
258
260 "asan-with-ifunc-suppress-remat",
261 cl::desc("Suppress rematerialization of dynamic shadow address by passing "
262 "it through inline asm in prologue."),
263 cl::Hidden, cl::init(true));
264
265// This flag limits the number of instructions to be instrumented
266// in any given BB. Normally, this should be set to unlimited (INT_MAX),
267// but due to http://llvm.org/bugs/show_bug.cgi?id=12652 we temporary
268// set it to 10000.
270 "asan-max-ins-per-bb", cl::init(10000),
271 cl::desc("maximal number of instructions to instrument in any given BB"),
272 cl::Hidden);
273
274// This flag may need to be replaced with -f[no]asan-stack.
275static cl::opt<bool> ClStack("asan-stack", cl::desc("Handle stack memory"),
276 cl::Hidden, cl::init(true));
278 "asan-max-inline-poisoning-size",
279 cl::desc(
280 "Inline shadow poisoning for blocks up to the given size in bytes."),
281 cl::Hidden, cl::init(64));
282
284 "asan-use-after-return",
285 cl::desc("Sets the mode of detection for stack-use-after-return."),
288 "Never detect stack use after return."),
291 "Detect stack use after return if "
292 "binary flag 'ASAN_OPTIONS=detect_stack_use_after_return' is set."),
294 "Always detect stack use after return.")),
296
297static cl::opt<bool> ClRedzoneByvalArgs("asan-redzone-byval-args",
298 cl::desc("Create redzones for byval "
299 "arguments (extra copy "
300 "required)"), cl::Hidden,
301 cl::init(true));
302
303static cl::opt<bool> ClUseAfterScope("asan-use-after-scope",
304 cl::desc("Check stack-use-after-scope"),
305 cl::Hidden, cl::init(false));
306
307// This flag may need to be replaced with -f[no]asan-globals.
308static cl::opt<bool> ClGlobals("asan-globals",
309 cl::desc("Handle global objects"), cl::Hidden,
310 cl::init(true));
311
312static cl::opt<bool> ClInitializers("asan-initialization-order",
313 cl::desc("Handle C++ initializer order"),
314 cl::Hidden, cl::init(true));
315
317 "asan-detect-invalid-pointer-pair",
318 cl::desc("Instrument <, <=, >, >=, - with pointer operands"), cl::Hidden,
319 cl::init(false));
320
322 "asan-detect-invalid-pointer-cmp",
323 cl::desc("Instrument <, <=, >, >= with pointer operands"), cl::Hidden,
324 cl::init(false));
325
327 "asan-detect-invalid-pointer-sub",
328 cl::desc("Instrument - operations with pointer operands"), cl::Hidden,
329 cl::init(false));
330
332 "asan-realign-stack",
333 cl::desc("Realign stack to the value of this flag (power of two)"),
334 cl::Hidden, cl::init(32));
335
337 "asan-instrumentation-with-call-threshold",
338 cl::desc("If the function being instrumented contains more than "
339 "this number of memory accesses, use callbacks instead of "
340 "inline checks (-1 means never use callbacks)."),
341 cl::Hidden, cl::init(7000));
342
344 "asan-memory-access-callback-prefix",
345 cl::desc("Prefix for memory access callbacks"), cl::Hidden,
346 cl::init("__asan_"));
347
349 "asan-kernel-mem-intrinsic-prefix",
350 cl::desc("Use prefix for memory intrinsics in KASAN mode"), cl::Hidden,
351 cl::init(false));
352
353static cl::opt<bool>
354 ClInstrumentDynamicAllocas("asan-instrument-dynamic-allocas",
355 cl::desc("instrument dynamic allocas"),
356 cl::Hidden, cl::init(true));
357
359 "asan-skip-promotable-allocas",
360 cl::desc("Do not instrument promotable allocas"), cl::Hidden,
361 cl::init(true));
362
364 "asan-constructor-kind",
365 cl::desc("Sets the ASan constructor kind"),
366 cl::values(clEnumValN(AsanCtorKind::None, "none", "No constructors"),
368 "Use global constructors")),
370// These flags allow to change the shadow mapping.
371// The shadow mapping looks like
372// Shadow = (Mem >> scale) + offset
373
374static cl::opt<int> ClMappingScale("asan-mapping-scale",
375 cl::desc("scale of asan shadow mapping"),
376 cl::Hidden, cl::init(0));
377
379 ClMappingOffset("asan-mapping-offset",
380 cl::desc("offset of asan shadow mapping [EXPERIMENTAL]"),
381 cl::Hidden, cl::init(0));
382
383// Optimization flags. Not user visible, used mostly for testing
384// and benchmarking the tool.
385
386static cl::opt<bool> ClOpt("asan-opt", cl::desc("Optimize instrumentation"),
387 cl::Hidden, cl::init(true));
388
389static cl::opt<bool> ClOptimizeCallbacks("asan-optimize-callbacks",
390 cl::desc("Optimize callbacks"),
391 cl::Hidden, cl::init(false));
392
394 "asan-opt-same-temp", cl::desc("Instrument the same temp just once"),
395 cl::Hidden, cl::init(true));
396
397static cl::opt<bool> ClOptGlobals("asan-opt-globals",
398 cl::desc("Don't instrument scalar globals"),
399 cl::Hidden, cl::init(true));
400
402 "asan-opt-stack", cl::desc("Don't instrument scalar stack variables"),
403 cl::Hidden, cl::init(false));
404
406 "asan-stack-dynamic-alloca",
407 cl::desc("Use dynamic alloca to represent stack variables"), cl::Hidden,
408 cl::init(true));
409
411 "asan-force-experiment",
412 cl::desc("Force optimization experiment (for testing)"), cl::Hidden,
413 cl::init(0));
414
415static cl::opt<bool>
416 ClUsePrivateAlias("asan-use-private-alias",
417 cl::desc("Use private aliases for global variables"),
418 cl::Hidden, cl::init(true));
419
420static cl::opt<bool>
421 ClUseOdrIndicator("asan-use-odr-indicator",
422 cl::desc("Use odr indicators to improve ODR reporting"),
423 cl::Hidden, cl::init(true));
424
425static cl::opt<bool>
426 ClUseGlobalsGC("asan-globals-live-support",
427 cl::desc("Use linker features to support dead "
428 "code stripping of globals"),
429 cl::Hidden, cl::init(true));
430
431// This is on by default even though there is a bug in gold:
432// https://sourceware.org/bugzilla/show_bug.cgi?id=19002
433static cl::opt<bool>
434 ClWithComdat("asan-with-comdat",
435 cl::desc("Place ASan constructors in comdat sections"),
436 cl::Hidden, cl::init(true));
437
439 "asan-destructor-kind",
440 cl::desc("Sets the ASan destructor kind. The default is to use the value "
441 "provided to the pass constructor"),
442 cl::values(clEnumValN(AsanDtorKind::None, "none", "No destructors"),
444 "Use global destructors")),
446
449 "asan-instrument-address-spaces",
450 cl::desc("Only instrument variables in the specified address spaces."),
451 cl::Hidden, cl::CommaSeparated, cl::callback([](const unsigned &AddrSpace) {
452 SrcAddrSpaces.insert(AddrSpace);
453 }));
454
455// Debug flags.
456
457static cl::opt<int> ClDebug("asan-debug", cl::desc("debug"), cl::Hidden,
458 cl::init(0));
459
460static cl::opt<int> ClDebugStack("asan-debug-stack", cl::desc("debug stack"),
461 cl::Hidden, cl::init(0));
462
464 cl::desc("Debug func"));
465
466static cl::opt<int> ClDebugMin("asan-debug-min", cl::desc("Debug min inst"),
467 cl::Hidden, cl::init(-1));
468
469static cl::opt<int> ClDebugMax("asan-debug-max", cl::desc("Debug max inst"),
470 cl::Hidden, cl::init(-1));
471
472STATISTIC(NumInstrumentedReads, "Number of instrumented reads");
473STATISTIC(NumInstrumentedWrites, "Number of instrumented writes");
474STATISTIC(NumOptimizedAccessesToGlobalVar,
475 "Number of optimized accesses to global vars");
476STATISTIC(NumOptimizedAccessesToStackVar,
477 "Number of optimized accesses to stack vars");
478
479namespace {
480
481/// This struct defines the shadow mapping using the rule:
482/// shadow = (mem >> Scale) ADD-or-OR Offset.
483/// If InGlobal is true, then
484/// extern char __asan_shadow[];
485/// shadow = (mem >> Scale) + &__asan_shadow
486struct ShadowMapping {
487 int Scale;
489 bool OrShadowOffset;
490 bool InGlobal;
491};
492
493} // end anonymous namespace
494
495static ShadowMapping getShadowMapping(const Triple &TargetTriple, int LongSize,
496 bool IsKasan) {
497 bool IsAndroid = TargetTriple.isAndroid();
498 bool IsIOS = TargetTriple.isiOS() || TargetTriple.isWatchOS() ||
499 TargetTriple.isDriverKit();
500 bool IsMacOS = TargetTriple.isMacOSX();
501 bool IsFreeBSD = TargetTriple.isOSFreeBSD();
502 bool IsNetBSD = TargetTriple.isOSNetBSD();
503 bool IsPS = TargetTriple.isPS();
504 bool IsLinux = TargetTriple.isOSLinux();
505 bool IsPPC64 = TargetTriple.getArch() == Triple::ppc64 ||
506 TargetTriple.getArch() == Triple::ppc64le;
507 bool IsSystemZ = TargetTriple.getArch() == Triple::systemz;
508 bool IsX86_64 = TargetTriple.getArch() == Triple::x86_64;
509 bool IsMIPSN32ABI = TargetTriple.isABIN32();
510 bool IsMIPS32 = TargetTriple.isMIPS32();
511 bool IsMIPS64 = TargetTriple.isMIPS64();
512 bool IsArmOrThumb = TargetTriple.isARM() || TargetTriple.isThumb();
513 bool IsAArch64 = TargetTriple.getArch() == Triple::aarch64 ||
514 TargetTriple.getArch() == Triple::aarch64_be;
515 bool IsLoongArch64 = TargetTriple.isLoongArch64();
516 bool IsRISCV64 = TargetTriple.getArch() == Triple::riscv64;
517 bool IsWindows = TargetTriple.isOSWindows();
518 bool IsFuchsia = TargetTriple.isOSFuchsia();
519 bool IsAMDGPU = TargetTriple.isAMDGPU();
520 bool IsHaiku = TargetTriple.isOSHaiku();
521 bool IsWasm = TargetTriple.isWasm();
522 bool IsBPF = TargetTriple.isBPF();
523
524 ShadowMapping Mapping;
525
526 Mapping.Scale = kDefaultShadowScale;
527 if (ClMappingScale.getNumOccurrences() > 0) {
528 Mapping.Scale = ClMappingScale;
529 }
530
531 if (LongSize == 32) {
532 if (IsAndroid)
533 Mapping.Offset = kDynamicShadowSentinel;
534 else if (IsMIPSN32ABI)
535 Mapping.Offset = kMIPS_ShadowOffsetN32;
536 else if (IsMIPS32)
537 Mapping.Offset = kMIPS32_ShadowOffset32;
538 else if (IsFreeBSD)
539 Mapping.Offset = kFreeBSD_ShadowOffset32;
540 else if (IsNetBSD)
541 Mapping.Offset = kNetBSD_ShadowOffset32;
542 else if (IsIOS)
543 Mapping.Offset = kDynamicShadowSentinel;
544 else if (IsWindows)
545 Mapping.Offset = kWindowsShadowOffset32;
546 else if (IsWasm)
547 Mapping.Offset = kWebAssemblyShadowOffset;
548 else
549 Mapping.Offset = kDefaultShadowOffset32;
550 } else { // LongSize == 64
551 // Fuchsia is always PIE, which means that the beginning of the address
552 // space is always available.
553 if (IsFuchsia) {
554 // kDynamicShadowSentinel tells instrumentation to use the dynamic shadow.
555 Mapping.Offset = kDynamicShadowSentinel;
556 } else if (IsPPC64)
557 Mapping.Offset = kPPC64_ShadowOffset64;
558 else if (IsSystemZ)
559 Mapping.Offset = kSystemZ_ShadowOffset64;
560 else if (IsFreeBSD && IsAArch64)
561 Mapping.Offset = kFreeBSDAArch64_ShadowOffset64;
562 else if (IsFreeBSD && !IsMIPS64) {
563 if (IsKasan)
564 Mapping.Offset = kFreeBSDKasan_ShadowOffset64;
565 else
566 Mapping.Offset = kFreeBSD_ShadowOffset64;
567 } else if (IsNetBSD) {
568 if (IsKasan)
569 Mapping.Offset = kNetBSDKasan_ShadowOffset64;
570 else
571 Mapping.Offset = kNetBSD_ShadowOffset64;
572 } else if (IsPS)
573 Mapping.Offset = kPS_ShadowOffset64;
574 else if (IsLinux && IsX86_64) {
575 if (IsKasan)
576 Mapping.Offset = kLinuxKasan_ShadowOffset64;
577 else
578 Mapping.Offset = (kSmallX86_64ShadowOffsetBase &
579 (kSmallX86_64ShadowOffsetAlignMask << Mapping.Scale));
580 } else if (IsWindows && (IsX86_64 || IsAArch64)) {
581 Mapping.Offset = kWindowsShadowOffset64;
582 } else if (IsMIPS64)
583 Mapping.Offset = kMIPS64_ShadowOffset64;
584 else if (IsIOS)
585 Mapping.Offset = kDynamicShadowSentinel;
586 else if (IsMacOS && IsAArch64)
587 Mapping.Offset = kDynamicShadowSentinel;
588 else if (IsAArch64)
589 Mapping.Offset = kAArch64_ShadowOffset64;
590 else if (IsLoongArch64)
591 Mapping.Offset = kLoongArch64_ShadowOffset64;
592 else if (IsRISCV64)
593 Mapping.Offset = kRISCV64_ShadowOffset64;
594 else if (IsAMDGPU)
595 Mapping.Offset = (kSmallX86_64ShadowOffsetBase &
596 (kSmallX86_64ShadowOffsetAlignMask << Mapping.Scale));
597 else if (IsHaiku && IsX86_64)
598 Mapping.Offset = (kSmallX86_64ShadowOffsetBase &
599 (kSmallX86_64ShadowOffsetAlignMask << Mapping.Scale));
600 else if (IsBPF)
601 Mapping.Offset = kDynamicShadowSentinel;
602 else
603 Mapping.Offset = kDefaultShadowOffset64;
604 }
605
607 Mapping.Offset = kDynamicShadowSentinel;
608 }
609
610 if (ClMappingOffset.getNumOccurrences() > 0) {
611 Mapping.Offset = ClMappingOffset;
612 }
613
614 // OR-ing shadow offset if more efficient (at least on x86) if the offset
615 // is a power of two, but on ppc64 and loongarch64 we have to use add since
616 // the shadow offset is not necessarily 1/8-th of the address space. On
617 // SystemZ, we could OR the constant in a single instruction, but it's more
618 // efficient to load it once and use indexed addressing.
619 Mapping.OrShadowOffset = !IsAArch64 && !IsPPC64 && !IsSystemZ && !IsPS &&
620 !IsRISCV64 && !IsLoongArch64 &&
621 !(Mapping.Offset & (Mapping.Offset - 1)) &&
622 Mapping.Offset != kDynamicShadowSentinel;
623 Mapping.InGlobal = ClWithIfunc && IsAndroid && IsArmOrThumb;
624
625 return Mapping;
626}
627
628void llvm::getAddressSanitizerParams(const Triple &TargetTriple, int LongSize,
629 bool IsKasan, uint64_t *ShadowBase,
630 int *MappingScale, bool *OrShadowOffset) {
631 auto Mapping = getShadowMapping(TargetTriple, LongSize, IsKasan);
632 *ShadowBase = Mapping.Offset;
633 *MappingScale = Mapping.Scale;
634 *OrShadowOffset = Mapping.OrShadowOffset;
635}
636
638 // Adding sanitizer checks invalidates previously inferred memory attributes.
639 //
640 // This is not only true for sanitized functions, because AttrInfer can
641 // infer those attributes on libc functions, which is not true if those
642 // are instrumented (Android) or intercepted.
643 //
644 // We might want to model ASan shadow memory more opaquely to get rid of
645 // this problem altogether, by hiding the shadow memory write in an
646 // intrinsic, essentially like in the AArch64StackTagging pass. But that's
647 // for another day.
648
649 bool Changed = false;
650 // We add memory(readwrite) to functions that don't already have that set and
651 // can access any non-inaccessible memory. Sanitizer instrumentation can
652 // read/write shadow memory, which is IRMemLocation::Other. Sanitizer
653 // instrumentation can instrument any memory accesses to non-inaccessible
654 // memory.
655 if (!F.getMemoryEffects()
656 .getWithoutLoc(IRMemLocation::InaccessibleMem)
657 .doesNotAccessMemory() &&
658 !isModAndRefSet(F.getMemoryEffects().getModRef(IRMemLocation::Other))) {
659 F.setMemoryEffects(F.getMemoryEffects() |
661 Changed = true;
662 }
663 // HWASan reads from argument memory even for previously write-only accesses.
664 if (ReadsArgMem) {
665 if (F.getMemoryEffects().getModRef(IRMemLocation::ArgMem) ==
667 F.setMemoryEffects(F.getMemoryEffects() |
669 Changed = true;
670 }
671 for (Argument &A : F.args()) {
672 if (A.hasAttribute(Attribute::WriteOnly)) {
673 A.removeAttr(Attribute::WriteOnly);
674 Changed = true;
675 }
676 }
677 }
678 if (Changed) {
679 // nobuiltin makes sure later passes don't restore assumptions about
680 // the function.
681 F.addFnAttr(Attribute::NoBuiltin);
682 }
683}
684
690
698
699static uint64_t getRedzoneSizeForScale(int MappingScale) {
700 // Redzone used for stack and globals is at least 32 bytes.
701 // For scales 6 and 7, the redzone has to be 64 and 128 bytes respectively.
702 return std::max(32U, 1U << MappingScale);
703}
704
706 if (TargetTriple.isOSEmscripten())
708 else
710}
711
712static Twine genName(StringRef suffix) {
713 return Twine(kAsanGenPrefix) + suffix;
714}
715
716namespace {
717
718class AsanFunctionInserter {
719public:
720 AsanFunctionInserter(Module &M) : M(M) {}
721
722 template <typename... ArgTypes>
723 FunctionCallee insertFunction(StringRef Name, ArgTypes &&...Args) {
724 return M.getOrInsertFunction(Name, std::forward<ArgTypes>(Args)...);
725 }
726
727private:
728 Module &M;
729};
730
731} // end anonymous namespace
732
733namespace {
734/// Helper RAII class to post-process inserted asan runtime calls during a
735/// pass on a single Function. Upon end of scope, detects and applies the
736/// required funclet OpBundle.
737class RuntimeCallInserter {
738 Function *OwnerFn = nullptr;
739 bool TrackInsertedCalls = false;
740 SmallVector<CallInst *> InsertedCalls;
741
742public:
743 RuntimeCallInserter(Function &Fn) : OwnerFn(&Fn) {
744 if (Fn.hasPersonalityFn()) {
745 auto Personality = classifyEHPersonality(Fn.getPersonalityFn());
746 if (isScopedEHPersonality(Personality))
747 TrackInsertedCalls = true;
748 }
749 }
750
751 ~RuntimeCallInserter() {
752 if (InsertedCalls.empty())
753 return;
754 assert(TrackInsertedCalls && "Calls were wrongly tracked");
755
756 DenseMap<BasicBlock *, ColorVector> BlockColors = colorEHFunclets(*OwnerFn);
757 for (CallInst *CI : InsertedCalls) {
758 BasicBlock *BB = CI->getParent();
759 assert(BB && "Instruction doesn't belong to a BasicBlock");
760 assert(BB->getParent() == OwnerFn &&
761 "Instruction doesn't belong to the expected Function!");
762
763 ColorVector &Colors = BlockColors[BB];
764 // funclet opbundles are only valid in monochromatic BBs.
765 // Note that unreachable BBs are seen as colorless by colorEHFunclets()
766 // and will be DCE'ed later.
767 if (Colors.empty())
768 continue;
769 if (Colors.size() != 1) {
770 OwnerFn->getContext().emitError(
771 "Instruction's BasicBlock is not monochromatic");
772 continue;
773 }
774
775 BasicBlock *Color = Colors.front();
776 BasicBlock::iterator EHPadIt = Color->getFirstNonPHIIt();
777
778 if (EHPadIt != Color->end() && EHPadIt->isEHPad()) {
779 // Replace CI with a clone with an added funclet OperandBundle
780 OperandBundleDef OB("funclet", &*EHPadIt);
782 OB, CI->getIterator());
783 NewCall->copyMetadata(*CI);
784 CI->replaceAllUsesWith(NewCall);
785 CI->eraseFromParent();
786 }
787 }
788 }
789
790 CallInst *createRuntimeCall(IRBuilder<> &IRB, FunctionCallee Callee,
791 ArrayRef<Value *> Args = {},
792 const Twine &Name = "") {
793 assert(IRB.GetInsertBlock()->getParent() == OwnerFn);
794
795 CallInst *Inst = IRB.CreateCall(Callee, Args, Name, nullptr);
796 if (TrackInsertedCalls)
797 InsertedCalls.push_back(Inst);
798 return Inst;
799 }
800};
801
802/// AddressSanitizer: instrument the code in module to find memory bugs.
803struct AddressSanitizer {
804 AddressSanitizer(Module &M, const StackSafetyGlobalInfo *SSGI,
805 int InstrumentationWithCallsThreshold,
806 uint32_t MaxInlinePoisoningSize, bool CompileKernel = false,
807 bool Recover = false, bool UseAfterScope = false,
808 AsanDetectStackUseAfterReturnMode UseAfterReturn =
809 AsanDetectStackUseAfterReturnMode::Runtime)
810 : M(M), Inserter(M),
811 CompileKernel(ClEnableKasan.getNumOccurrences() > 0 ? ClEnableKasan
812 : CompileKernel),
813 Recover(ClRecover.getNumOccurrences() > 0 ? ClRecover : Recover),
814 UseAfterScope(UseAfterScope || ClUseAfterScope),
815 UseAfterReturn(ClUseAfterReturn.getNumOccurrences() ? ClUseAfterReturn
816 : UseAfterReturn),
817 SSGI(SSGI),
818 InstrumentationWithCallsThreshold(
819 ClInstrumentationWithCallsThreshold.getNumOccurrences() > 0
821 : InstrumentationWithCallsThreshold),
822 MaxInlinePoisoningSize(ClMaxInlinePoisoningSize.getNumOccurrences() > 0
824 : MaxInlinePoisoningSize) {
825 C = &(M.getContext());
826 DL = &M.getDataLayout();
827 LongSize = M.getDataLayout().getPointerSizeInBits();
828 IntptrTy = Type::getIntNTy(*C, LongSize);
829 PtrTy = PointerType::getUnqual(*C);
830 Int32Ty = Type::getInt32Ty(*C);
831 TargetTriple = M.getTargetTriple();
832
833 Mapping = getShadowMapping(TargetTriple, LongSize, this->CompileKernel);
834
835 assert(this->UseAfterReturn != AsanDetectStackUseAfterReturnMode::Invalid);
836 }
837
838 TypeSize getAllocaSizeInBytes(const AllocaInst &AI) const {
839 return *AI.getAllocationSize(AI.getDataLayout());
840 }
841
842 /// Check if we want (and can) handle this alloca.
843 bool isInterestingAlloca(const AllocaInst &AI);
844
845 bool ignoreAccess(Instruction *Inst, Value *Ptr);
847 Instruction *I, SmallVectorImpl<InterestingMemoryOperand> &Interesting,
848 const TargetTransformInfo *TTI);
849
850 void instrumentMop(ObjectSizeOffsetVisitor &ObjSizeVis,
851 InterestingMemoryOperand &O, bool UseCalls,
852 const DataLayout &DL, RuntimeCallInserter &RTCI);
853 void instrumentPointerComparisonOrSubtraction(Instruction *I,
854 RuntimeCallInserter &RTCI);
855 void instrumentAddress(Instruction *OrigIns, Instruction *InsertBefore,
856 Value *Addr, MaybeAlign Alignment,
857 uint32_t TypeStoreSize, bool IsWrite,
858 Value *SizeArgument, bool UseCalls, uint32_t Exp,
859 RuntimeCallInserter &RTCI);
860 Instruction *instrumentAMDGPUAddress(Instruction *OrigIns,
861 Instruction *InsertBefore, Value *Addr,
862 uint32_t TypeStoreSize, bool IsWrite,
863 Value *SizeArgument);
864 Instruction *genAMDGPUReportBlock(IRBuilder<> &IRB, Value *Cond,
865 bool Recover);
866 void instrumentUnusualSizeOrAlignment(Instruction *I,
867 Instruction *InsertBefore, Value *Addr,
868 TypeSize TypeStoreSize, bool IsWrite,
869 Value *SizeArgument, bool UseCalls,
870 uint32_t Exp,
871 RuntimeCallInserter &RTCI);
872 void instrumentMaskedLoadOrStore(AddressSanitizer *Pass, const DataLayout &DL,
873 Type *IntptrTy, Value *Mask, Value *EVL,
874 Value *Stride, Instruction *I, Value *Addr,
875 MaybeAlign Alignment, unsigned Granularity,
876 Type *OpType, bool IsWrite,
877 Value *SizeArgument, bool UseCalls,
878 uint32_t Exp, RuntimeCallInserter &RTCI);
879 Value *createSlowPathCmp(IRBuilder<> &IRB, Value *AddrLong,
880 Value *ShadowValue, uint32_t TypeStoreSize);
881 Instruction *generateCrashCode(Instruction *InsertBefore, Value *Addr,
882 bool IsWrite, size_t AccessSizeIndex,
883 Value *SizeArgument, uint32_t Exp,
884 RuntimeCallInserter &RTCI);
885 void instrumentMemIntrinsic(MemIntrinsic *MI, RuntimeCallInserter &RTCI);
886 Value *memToShadow(Value *Shadow, IRBuilder<> &IRB);
887 bool suppressInstrumentationSiteForDebug(int &Instrumented);
888 bool instrumentFunction(Function &F, const TargetLibraryInfo *TLI,
889 const TargetTransformInfo *TTI);
890 bool maybeInsertAsanInitAtFunctionEntry(Function &F);
891 bool maybeInsertDynamicShadowAtFunctionEntry(Function &F);
892 void markEscapedLocalAllocas(Function &F);
893 void markCatchParametersAsUninteresting(Function &F);
894
895private:
896 friend struct FunctionStackPoisoner;
897
898 void initializeCallbacks(const TargetLibraryInfo *TLI);
899
900 bool LooksLikeCodeInBug11395(Instruction *I);
901 bool GlobalIsLinkerInitialized(GlobalVariable *G);
902 bool isSafeAccess(ObjectSizeOffsetVisitor &ObjSizeVis, Value *Addr,
903 TypeSize TypeStoreSize) const;
904
905 /// Helper to cleanup per-function state.
906 struct FunctionStateRAII {
907 AddressSanitizer *Pass;
908
909 FunctionStateRAII(AddressSanitizer *Pass) : Pass(Pass) {
910 assert(Pass->ProcessedAllocas.empty() &&
911 "last pass forgot to clear cache");
912 assert(!Pass->LocalDynamicShadow);
913 }
914
915 ~FunctionStateRAII() {
916 Pass->LocalDynamicShadow = nullptr;
917 Pass->ProcessedAllocas.clear();
918 }
919 };
920
921 Module &M;
922 AsanFunctionInserter Inserter;
923 LLVMContext *C;
924 const DataLayout *DL;
925 Triple TargetTriple;
926 int LongSize;
927 bool CompileKernel;
928 bool Recover;
929 bool UseAfterScope;
931 Type *IntptrTy;
932 Type *Int32Ty;
933 PointerType *PtrTy;
934 ShadowMapping Mapping;
935 FunctionCallee AsanHandleNoReturnFunc;
936 FunctionCallee AsanPtrCmpFunction, AsanPtrSubFunction;
937 Constant *AsanShadowGlobal;
938
939 // These arrays is indexed by AccessIsWrite, Experiment and log2(AccessSize).
940 FunctionCallee AsanErrorCallback[2][2][kNumberOfAccessSizes];
941 FunctionCallee AsanMemoryAccessCallback[2][2][kNumberOfAccessSizes];
942
943 // These arrays is indexed by AccessIsWrite and Experiment.
944 FunctionCallee AsanErrorCallbackSized[2][2];
945 FunctionCallee AsanMemoryAccessCallbackSized[2][2];
946
947 FunctionCallee AsanMemmove, AsanMemcpy, AsanMemset;
948 Value *LocalDynamicShadow = nullptr;
949 const StackSafetyGlobalInfo *SSGI;
950 DenseMap<const AllocaInst *, bool> ProcessedAllocas;
951
952 FunctionCallee AMDGPUAddressShared;
953 FunctionCallee AMDGPUAddressPrivate;
954 int InstrumentationWithCallsThreshold;
955 uint32_t MaxInlinePoisoningSize;
956};
957
958class ModuleAddressSanitizer {
959public:
960 ModuleAddressSanitizer(Module &M, bool InsertVersionCheck,
961 bool CompileKernel = false, bool Recover = false,
962 bool UseGlobalsGC = true, bool UseOdrIndicator = true,
963 AsanDtorKind DestructorKind = AsanDtorKind::Global,
964 AsanCtorKind ConstructorKind = AsanCtorKind::Global)
965 : M(M), Inserter(M),
966 CompileKernel(ClEnableKasan.getNumOccurrences() > 0 ? ClEnableKasan
967 : CompileKernel),
968 InsertVersionCheck(ClInsertVersionCheck.getNumOccurrences() > 0
970 : InsertVersionCheck),
971 Recover(ClRecover.getNumOccurrences() > 0 ? ClRecover : Recover),
972 UseGlobalsGC(UseGlobalsGC && ClUseGlobalsGC && !this->CompileKernel),
973 // Enable aliases as they should have no downside with ODR indicators.
974 UsePrivateAlias(ClUsePrivateAlias.getNumOccurrences() > 0
976 : UseOdrIndicator),
977 UseOdrIndicator(ClUseOdrIndicator.getNumOccurrences() > 0
979 : UseOdrIndicator),
980 // Not a typo: ClWithComdat is almost completely pointless without
981 // ClUseGlobalsGC (because then it only works on modules without
982 // globals, which are rare); it is a prerequisite for ClUseGlobalsGC;
983 // and both suffer from gold PR19002 for which UseGlobalsGC constructor
984 // argument is designed as workaround. Therefore, disable both
985 // ClWithComdat and ClUseGlobalsGC unless the frontend says it's ok to
986 // do globals-gc.
987 UseCtorComdat(UseGlobalsGC && ClWithComdat && !this->CompileKernel),
988 DestructorKind(DestructorKind),
989 ConstructorKind(ClConstructorKind.getNumOccurrences() > 0
991 : ConstructorKind) {
992 C = &(M.getContext());
993 int LongSize = M.getDataLayout().getPointerSizeInBits();
994 IntptrTy = Type::getIntNTy(*C, LongSize);
995 PtrTy = PointerType::getUnqual(*C);
996 TargetTriple = M.getTargetTriple();
997 Mapping = getShadowMapping(TargetTriple, LongSize, this->CompileKernel);
998
999 if (ClOverrideDestructorKind != AsanDtorKind::Invalid)
1000 this->DestructorKind = ClOverrideDestructorKind;
1001 assert(this->DestructorKind != AsanDtorKind::Invalid);
1002 }
1003
1004 bool instrumentModule();
1005
1006private:
1007 void initializeCallbacks();
1008
1009 void instrumentGlobals(IRBuilder<> &IRB, bool *CtorComdat);
1010 void InstrumentGlobalsCOFF(IRBuilder<> &IRB,
1011 ArrayRef<GlobalVariable *> ExtendedGlobals,
1012 ArrayRef<Constant *> MetadataInitializers);
1013 void instrumentGlobalsELF(IRBuilder<> &IRB,
1014 ArrayRef<GlobalVariable *> ExtendedGlobals,
1015 ArrayRef<Constant *> MetadataInitializers,
1016 const std::string &UniqueModuleId);
1017 void InstrumentGlobalsMachO(IRBuilder<> &IRB,
1018 ArrayRef<GlobalVariable *> ExtendedGlobals,
1019 ArrayRef<Constant *> MetadataInitializers);
1020 void
1021 InstrumentGlobalsWithMetadataArray(IRBuilder<> &IRB,
1022 ArrayRef<GlobalVariable *> ExtendedGlobals,
1023 ArrayRef<Constant *> MetadataInitializers);
1024
1025 GlobalVariable *CreateMetadataGlobal(Constant *Initializer,
1026 StringRef OriginalName);
1027 void SetComdatForGlobalMetadata(GlobalVariable *G, GlobalVariable *Metadata,
1028 StringRef InternalSuffix);
1029 Instruction *CreateAsanModuleDtor();
1030
1031 const GlobalVariable *getExcludedAliasedGlobal(const GlobalAlias &GA) const;
1032 bool shouldInstrumentGlobal(GlobalVariable *G) const;
1033 bool ShouldUseMachOGlobalsSection() const;
1034 StringRef getGlobalMetadataSection() const;
1035 void poisonOneInitializer(Function &GlobalInit);
1036 void createInitializerPoisonCalls();
1037 uint64_t getMinRedzoneSizeForGlobal() const {
1038 return getRedzoneSizeForScale(Mapping.Scale);
1039 }
1040 uint64_t getRedzoneSizeForGlobal(uint64_t SizeInBytes) const;
1041 int GetAsanVersion() const;
1042 GlobalVariable *getOrCreateModuleName();
1043
1044 Module &M;
1045 AsanFunctionInserter Inserter;
1046 bool CompileKernel;
1047 bool InsertVersionCheck;
1048 bool Recover;
1049 bool UseGlobalsGC;
1050 bool UsePrivateAlias;
1051 bool UseOdrIndicator;
1052 bool UseCtorComdat;
1053 AsanDtorKind DestructorKind;
1054 AsanCtorKind ConstructorKind;
1055 Type *IntptrTy;
1056 PointerType *PtrTy;
1057 LLVMContext *C;
1058 Triple TargetTriple;
1059 ShadowMapping Mapping;
1060 FunctionCallee AsanPoisonGlobals;
1061 FunctionCallee AsanUnpoisonGlobals;
1062 FunctionCallee AsanRegisterGlobals;
1063 FunctionCallee AsanUnregisterGlobals;
1064 FunctionCallee AsanRegisterImageGlobals;
1065 FunctionCallee AsanUnregisterImageGlobals;
1066 FunctionCallee AsanRegisterElfGlobals;
1067 FunctionCallee AsanUnregisterElfGlobals;
1068
1069 Function *AsanCtorFunction = nullptr;
1070 Function *AsanDtorFunction = nullptr;
1071 GlobalVariable *ModuleName = nullptr;
1072};
1073
1074// Stack poisoning does not play well with exception handling.
1075// When an exception is thrown, we essentially bypass the code
1076// that unpoisones the stack. This is why the run-time library has
1077// to intercept __cxa_throw (as well as longjmp, etc) and unpoison the entire
1078// stack in the interceptor. This however does not work inside the
1079// actual function which catches the exception. Most likely because the
1080// compiler hoists the load of the shadow value somewhere too high.
1081// This causes asan to report a non-existing bug on 453.povray.
1082// It sounds like an LLVM bug.
1083struct FunctionStackPoisoner : public InstVisitor<FunctionStackPoisoner> {
1084 Function &F;
1085 AddressSanitizer &ASan;
1086 RuntimeCallInserter &RTCI;
1087 DIBuilder DIB;
1088 LLVMContext *C;
1089 Type *IntptrTy;
1090 Type *IntptrPtrTy;
1091 ShadowMapping Mapping;
1092
1094 SmallVector<AllocaInst *, 16> StaticAllocasToMoveUp;
1095 SmallVector<Instruction *, 8> RetVec;
1096
1097 FunctionCallee AsanStackMallocFunc[kMaxAsanStackMallocSizeClass + 1],
1098 AsanStackFreeFunc[kMaxAsanStackMallocSizeClass + 1];
1099 FunctionCallee AsanSetShadowFunc[0x100] = {};
1100 FunctionCallee AsanPoisonStackMemoryFunc, AsanUnpoisonStackMemoryFunc;
1101 FunctionCallee AsanAllocaPoisonFunc, AsanAllocasUnpoisonFunc;
1102
1103 // Stores a place and arguments of poisoning/unpoisoning call for alloca.
1104 struct AllocaPoisonCall {
1105 IntrinsicInst *InsBefore;
1106 AllocaInst *AI;
1107 uint64_t Size;
1108 bool DoPoison;
1109 };
1110 SmallVector<AllocaPoisonCall, 8> DynamicAllocaPoisonCallVec;
1111 SmallVector<AllocaPoisonCall, 8> StaticAllocaPoisonCallVec;
1112
1113 SmallVector<AllocaInst *, 1> DynamicAllocaVec;
1114 SmallVector<IntrinsicInst *, 1> StackRestoreVec;
1115 AllocaInst *DynamicAllocaLayout = nullptr;
1116 IntrinsicInst *LocalEscapeCall = nullptr;
1117
1118 bool HasInlineAsm = false;
1119 bool HasReturnsTwiceCall = false;
1120 bool PoisonStack;
1121
1122 FunctionStackPoisoner(Function &F, AddressSanitizer &ASan,
1123 RuntimeCallInserter &RTCI)
1124 : F(F), ASan(ASan), RTCI(RTCI),
1125 DIB(*F.getParent(), /*AllowUnresolved*/ false), C(ASan.C),
1126 IntptrTy(ASan.IntptrTy),
1127 IntptrPtrTy(PointerType::get(IntptrTy->getContext(), 0)),
1128 Mapping(ASan.Mapping),
1129 PoisonStack(ClStack && !F.getParent()->getTargetTriple().isAMDGPU()) {}
1130
1131 bool runOnFunction() {
1132 if (!PoisonStack)
1133 return false;
1134
1136 copyArgsPassedByValToAllocas();
1137
1138 // Collect alloca, ret, lifetime instructions etc.
1139 for (BasicBlock *BB : depth_first(&F.getEntryBlock())) visit(*BB);
1140
1141 if (AllocaVec.empty() && DynamicAllocaVec.empty()) return false;
1142
1143 initializeCallbacks(*F.getParent());
1144
1145 processDynamicAllocas();
1146 processStaticAllocas();
1147
1148 if (ClDebugStack) {
1149 LLVM_DEBUG(dbgs() << F);
1150 }
1151 return true;
1152 }
1153
1154 // Arguments marked with the "byval" attribute are implicitly copied without
1155 // using an alloca instruction. To produce redzones for those arguments, we
1156 // copy them a second time into memory allocated with an alloca instruction.
1157 void copyArgsPassedByValToAllocas();
1158
1159 // Finds all Alloca instructions and puts
1160 // poisoned red zones around all of them.
1161 // Then unpoison everything back before the function returns.
1162 void processStaticAllocas();
1163 void processDynamicAllocas();
1164
1165 void createDynamicAllocasInitStorage();
1166
1167 // ----------------------- Visitors.
1168 /// Collect all Ret instructions, or the musttail call instruction if it
1169 /// precedes the return instruction.
1170 void visitReturnInst(ReturnInst &RI) {
1171 if (CallInst *CI = RI.getParent()->getTerminatingMustTailCall())
1172 RetVec.push_back(CI);
1173 else
1174 RetVec.push_back(&RI);
1175 }
1176
1177 /// Collect all Resume instructions.
1178 void visitResumeInst(ResumeInst &RI) { RetVec.push_back(&RI); }
1179
1180 /// Collect all CatchReturnInst instructions.
1181 void visitCleanupReturnInst(CleanupReturnInst &CRI) { RetVec.push_back(&CRI); }
1182
1183 void unpoisonDynamicAllocasBeforeInst(Instruction *InstBefore,
1184 Value *SavedStack) {
1185 IRBuilder<> IRB(InstBefore);
1186 Value *DynamicAreaPtr = IRB.CreatePtrToInt(SavedStack, IntptrTy);
1187 // When we insert _asan_allocas_unpoison before @llvm.stackrestore, we
1188 // need to adjust extracted SP to compute the address of the most recent
1189 // alloca. We have a special @llvm.get.dynamic.area.offset intrinsic for
1190 // this purpose.
1191 if (!isa<ReturnInst>(InstBefore)) {
1192 Value *DynamicAreaOffset = IRB.CreateIntrinsic(
1193 Intrinsic::get_dynamic_area_offset, {IntptrTy}, {});
1194
1195 DynamicAreaPtr = IRB.CreateAdd(IRB.CreatePtrToInt(SavedStack, IntptrTy),
1196 DynamicAreaOffset);
1197 }
1198
1199 RTCI.createRuntimeCall(
1200 IRB, AsanAllocasUnpoisonFunc,
1201 {IRB.CreateLoad(IntptrTy, DynamicAllocaLayout), DynamicAreaPtr});
1202 }
1203
1204 // Unpoison dynamic allocas redzones.
1205 void unpoisonDynamicAllocas() {
1206 for (Instruction *Ret : RetVec)
1207 unpoisonDynamicAllocasBeforeInst(Ret, DynamicAllocaLayout);
1208
1209 for (Instruction *StackRestoreInst : StackRestoreVec)
1210 unpoisonDynamicAllocasBeforeInst(StackRestoreInst,
1211 StackRestoreInst->getOperand(0));
1212 }
1213
1214 // Deploy and poison redzones around dynamic alloca call. To do this, we
1215 // should replace this call with another one with changed parameters and
1216 // replace all its uses with new address, so
1217 // addr = alloca type, old_size, align
1218 // is replaced by
1219 // new_size = (old_size + additional_size) * sizeof(type)
1220 // tmp = alloca i8, new_size, max(align, 32)
1221 // addr = tmp + 32 (first 32 bytes are for the left redzone).
1222 // Additional_size is added to make new memory allocation contain not only
1223 // requested memory, but also left, partial and right redzones.
1224 void handleDynamicAllocaCall(AllocaInst *AI);
1225
1226 /// Collect Alloca instructions we want (and can) handle.
1227 void visitAllocaInst(AllocaInst &AI) {
1228 // FIXME: Handle scalable vectors instead of ignoring them.
1229 const Type *AllocaType = AI.getAllocatedType();
1230 const auto *STy = dyn_cast<StructType>(AllocaType);
1231 if (!ASan.isInterestingAlloca(AI) || isa<ScalableVectorType>(AllocaType) ||
1232 (STy && STy->containsHomogeneousScalableVectorTypes())) {
1233 if (AI.isStaticAlloca()) {
1234 // Skip over allocas that are present *before* the first instrumented
1235 // alloca, we don't want to move those around.
1236 if (AllocaVec.empty())
1237 return;
1238
1239 StaticAllocasToMoveUp.push_back(&AI);
1240 }
1241 return;
1242 }
1243
1244 if (!AI.isStaticAlloca())
1245 DynamicAllocaVec.push_back(&AI);
1246 else
1247 AllocaVec.push_back(&AI);
1248 }
1249
1250 /// Collect lifetime intrinsic calls to check for use-after-scope
1251 /// errors.
1252 void visitIntrinsicInst(IntrinsicInst &II) {
1253 Intrinsic::ID ID = II.getIntrinsicID();
1254 if (ID == Intrinsic::stackrestore) StackRestoreVec.push_back(&II);
1255 if (ID == Intrinsic::localescape) LocalEscapeCall = &II;
1256 if (!ASan.UseAfterScope)
1257 return;
1258 if (!II.isLifetimeStartOrEnd())
1259 return;
1260 // Find alloca instruction that corresponds to llvm.lifetime argument.
1261 AllocaInst *AI = dyn_cast<AllocaInst>(II.getArgOperand(0));
1262 // We're interested only in allocas we can handle.
1263 if (!AI || !ASan.isInterestingAlloca(*AI))
1264 return;
1265
1266 std::optional<TypeSize> Size = AI->getAllocationSize(AI->getDataLayout());
1267 // Check that size is known and can be stored in IntptrTy.
1268 // TODO: Add support for scalable vectors if possible.
1269 if (!Size || Size->isScalable() ||
1271 return;
1272
1273 bool DoPoison = (ID == Intrinsic::lifetime_end);
1274 AllocaPoisonCall APC = {&II, AI, *Size, DoPoison};
1275 if (AI->isStaticAlloca())
1276 StaticAllocaPoisonCallVec.push_back(APC);
1278 DynamicAllocaPoisonCallVec.push_back(APC);
1279 }
1280
1281 void visitCallBase(CallBase &CB) {
1282 if (CallInst *CI = dyn_cast<CallInst>(&CB)) {
1283 HasInlineAsm |= CI->isInlineAsm() && &CB != ASan.LocalDynamicShadow;
1284 HasReturnsTwiceCall |= CI->canReturnTwice();
1285 }
1286 }
1287
1288 // ---------------------- Helpers.
1289 void initializeCallbacks(Module &M);
1290
1291 // Copies bytes from ShadowBytes into shadow memory for indexes where
1292 // ShadowMask is not zero. If ShadowMask[i] is zero, we assume that
1293 // ShadowBytes[i] is constantly zero and doesn't need to be overwritten.
1294 void copyToShadow(ArrayRef<uint8_t> ShadowMask, ArrayRef<uint8_t> ShadowBytes,
1295 IRBuilder<> &IRB, Value *ShadowBase);
1296 void copyToShadow(ArrayRef<uint8_t> ShadowMask, ArrayRef<uint8_t> ShadowBytes,
1297 size_t Begin, size_t End, IRBuilder<> &IRB,
1298 Value *ShadowBase);
1299 void copyToShadowInline(ArrayRef<uint8_t> ShadowMask,
1300 ArrayRef<uint8_t> ShadowBytes, size_t Begin,
1301 size_t End, IRBuilder<> &IRB, Value *ShadowBase);
1302
1303 void poisonAlloca(Value *V, uint64_t Size, IRBuilder<> &IRB, bool DoPoison);
1304
1305 Value *createAllocaForLayout(IRBuilder<> &IRB, const ASanStackFrameLayout &L,
1306 bool Dynamic);
1307 PHINode *createPHI(IRBuilder<> &IRB, Value *Cond, Value *ValueIfTrue,
1308 Instruction *ThenTerm, Value *ValueIfFalse);
1309};
1310
1311} // end anonymous namespace
1312
1314 raw_ostream &OS, function_ref<StringRef(StringRef)> MapClassName2PassName) {
1316 OS, MapClassName2PassName);
1317 OS << '<';
1318 if (Options.CompileKernel)
1319 OS << "kernel;";
1320 if (Options.UseAfterScope)
1321 OS << "use-after-scope";
1322 OS << '>';
1323}
1324
1326 const AddressSanitizerOptions &Options, bool UseGlobalGC,
1327 bool UseOdrIndicator, AsanDtorKind DestructorKind,
1328 AsanCtorKind ConstructorKind)
1329 : Options(Options), UseGlobalGC(UseGlobalGC),
1330 UseOdrIndicator(UseOdrIndicator), DestructorKind(DestructorKind),
1331 ConstructorKind(ConstructorKind) {}
1332
1335 // Return early if nosanitize_address module flag is present for the module.
1336 // This implies that asan pass has already run before.
1337 if (checkIfAlreadyInstrumented(M, "nosanitize_address"))
1338 return PreservedAnalyses::all();
1339
1340 ModuleAddressSanitizer ModuleSanitizer(
1341 M, Options.InsertVersionCheck, Options.CompileKernel, Options.Recover,
1342 UseGlobalGC, UseOdrIndicator, DestructorKind, ConstructorKind);
1343 bool Modified = false;
1344 auto &FAM = MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
1345 const StackSafetyGlobalInfo *const SSGI =
1346 ClUseStackSafety ? &MAM.getResult<StackSafetyGlobalAnalysis>(M) : nullptr;
1347 for (Function &F : M) {
1348 if (F.empty())
1349 continue;
1350 if (F.getLinkage() == GlobalValue::AvailableExternallyLinkage)
1351 continue;
1352 if (!ClDebugFunc.empty() && ClDebugFunc == F.getName())
1353 continue;
1354 if (F.getName().starts_with("__asan_"))
1355 continue;
1356 if (F.isPresplitCoroutine())
1357 continue;
1358 AddressSanitizer FunctionSanitizer(
1359 M, SSGI, Options.InstrumentationWithCallsThreshold,
1360 Options.MaxInlinePoisoningSize, Options.CompileKernel, Options.Recover,
1361 Options.UseAfterScope, Options.UseAfterReturn);
1362 const TargetLibraryInfo &TLI = FAM.getResult<TargetLibraryAnalysis>(F);
1363 const TargetTransformInfo &TTI = FAM.getResult<TargetIRAnalysis>(F);
1364 Modified |= FunctionSanitizer.instrumentFunction(F, &TLI, &TTI);
1365 }
1366 Modified |= ModuleSanitizer.instrumentModule();
1367 if (!Modified)
1368 return PreservedAnalyses::all();
1369
1371 // GlobalsAA is considered stateless and does not get invalidated unless
1372 // explicitly invalidated; PreservedAnalyses::none() is not enough. Sanitizers
1373 // make changes that require GlobalsAA to be invalidated.
1374 PA.abandon<GlobalsAA>();
1375 return PA;
1376}
1377
1379 size_t Res = llvm::countr_zero(TypeSize / 8);
1381 return Res;
1382}
1383
1384/// Check if \p G has been created by a trusted compiler pass.
1386 // Do not instrument @llvm.global_ctors, @llvm.used, etc.
1387 if (G->getName().starts_with("llvm.") ||
1388 // Do not instrument gcov counter arrays.
1389 G->getName().starts_with("__llvm_gcov_ctr") ||
1390 // Do not instrument rtti proxy symbols for function sanitizer.
1391 G->getName().starts_with("__llvm_rtti_proxy"))
1392 return true;
1393
1394 // Do not instrument asan globals.
1395 if (G->getName().starts_with(kAsanGenPrefix) ||
1396 G->getName().starts_with(kSanCovGenPrefix) ||
1397 G->getName().starts_with(kODRGenPrefix))
1398 return true;
1399
1400 return false;
1401}
1402
1404 Type *PtrTy = cast<PointerType>(Addr->getType()->getScalarType());
1405 unsigned int AddrSpace = PtrTy->getPointerAddressSpace();
1406 // Globals in address space 1 and 4 are supported for AMDGPU.
1407 if (AddrSpace == 3 || AddrSpace == 5)
1408 return true;
1409 return false;
1410}
1411
1412static bool isSupportedAddrspace(const Triple &TargetTriple, Value *Addr) {
1413 Type *PtrTy = cast<PointerType>(Addr->getType()->getScalarType());
1414 unsigned int AddrSpace = PtrTy->getPointerAddressSpace();
1415
1416 if (!SrcAddrSpaces.empty())
1417 return SrcAddrSpaces.count(AddrSpace);
1418
1419 if (TargetTriple.isAMDGPU())
1420 return !isUnsupportedAMDGPUAddrspace(Addr);
1421
1422 return AddrSpace == 0;
1423}
1424
1425Value *AddressSanitizer::memToShadow(Value *Shadow, IRBuilder<> &IRB) {
1426 // Shadow >> scale
1427 Shadow = IRB.CreateLShr(Shadow, Mapping.Scale);
1428 if (Mapping.Offset == 0) return Shadow;
1429 // (Shadow >> scale) | offset
1430 Value *ShadowBase;
1431 if (LocalDynamicShadow)
1432 ShadowBase = LocalDynamicShadow;
1433 else
1434 ShadowBase = ConstantInt::get(IntptrTy, Mapping.Offset);
1435 if (Mapping.OrShadowOffset)
1436 return IRB.CreateOr(Shadow, ShadowBase);
1437 else
1438 return IRB.CreateAdd(Shadow, ShadowBase);
1439}
1440
1441// Instrument memset/memmove/memcpy
1442void AddressSanitizer::instrumentMemIntrinsic(MemIntrinsic *MI,
1443 RuntimeCallInserter &RTCI) {
1445 if (isa<MemTransferInst>(MI)) {
1446 RTCI.createRuntimeCall(
1447 IRB, isa<MemMoveInst>(MI) ? AsanMemmove : AsanMemcpy,
1448 {IRB.CreateAddrSpaceCast(MI->getOperand(0), PtrTy),
1449 IRB.CreateAddrSpaceCast(MI->getOperand(1), PtrTy),
1450 IRB.CreateIntCast(MI->getOperand(2), IntptrTy, false)});
1451 } else if (isa<MemSetInst>(MI)) {
1452 RTCI.createRuntimeCall(
1453 IRB, AsanMemset,
1454 {IRB.CreateAddrSpaceCast(MI->getOperand(0), PtrTy),
1455 IRB.CreateIntCast(MI->getOperand(1), IRB.getInt32Ty(), false),
1456 IRB.CreateIntCast(MI->getOperand(2), IntptrTy, false)});
1457 }
1458 MI->eraseFromParent();
1459}
1460
1461/// Check if we want (and can) handle this alloca.
1462bool AddressSanitizer::isInterestingAlloca(const AllocaInst &AI) {
1463 auto [It, Inserted] = ProcessedAllocas.try_emplace(&AI);
1464
1465 if (!Inserted)
1466 return It->getSecond();
1467
1468 bool IsInteresting =
1469 (AI.getAllocatedType()->isSized() &&
1470 // alloca() may be called with 0 size, ignore it.
1471 ((!AI.isStaticAlloca()) || !getAllocaSizeInBytes(AI).isZero()) &&
1472 // We are only interested in allocas not promotable to registers.
1473 // Promotable allocas are common under -O0.
1475 // inalloca allocas are not treated as static, and we don't want
1476 // dynamic alloca instrumentation for them as well.
1477 !AI.isUsedWithInAlloca() &&
1478 // swifterror allocas are register promoted by ISel
1479 !AI.isSwiftError() &&
1480 // safe allocas are not interesting
1481 !(SSGI && SSGI->isSafe(AI)));
1482
1483 It->second = IsInteresting;
1484 return IsInteresting;
1485}
1486
1487bool AddressSanitizer::ignoreAccess(Instruction *Inst, Value *Ptr) {
1488 // Check whether the target supports sanitizing the address space
1489 // of the pointer.
1490 if (!isSupportedAddrspace(TargetTriple, Ptr))
1491 return true;
1492
1493 // Ignore swifterror addresses.
1494 // swifterror memory addresses are mem2reg promoted by instruction
1495 // selection. As such they cannot have regular uses like an instrumentation
1496 // function and it makes no sense to track them as memory.
1497 if (Ptr->isSwiftError())
1498 return true;
1499
1500 // Treat memory accesses to promotable allocas as non-interesting since they
1501 // will not cause memory violations. This greatly speeds up the instrumented
1502 // executable at -O0.
1503 if (auto AI = dyn_cast_or_null<AllocaInst>(Ptr))
1504 if (ClSkipPromotableAllocas && !isInterestingAlloca(*AI))
1505 return true;
1506
1507 if (SSGI != nullptr && SSGI->stackAccessIsSafe(*Inst) &&
1508 findAllocaForValue(Ptr))
1509 return true;
1510
1511 return false;
1512}
1513
1514void AddressSanitizer::getInterestingMemoryOperands(
1516 const TargetTransformInfo *TTI) {
1517 // Do not instrument the load fetching the dynamic shadow address.
1518 if (LocalDynamicShadow == I)
1519 return;
1520
1521 if (LoadInst *LI = dyn_cast<LoadInst>(I)) {
1522 if (!ClInstrumentReads || ignoreAccess(I, LI->getPointerOperand()))
1523 return;
1524 Interesting.emplace_back(I, LI->getPointerOperandIndex(), false,
1525 LI->getType(), LI->getAlign());
1526 } else if (StoreInst *SI = dyn_cast<StoreInst>(I)) {
1527 if (!ClInstrumentWrites || ignoreAccess(I, SI->getPointerOperand()))
1528 return;
1529 Interesting.emplace_back(I, SI->getPointerOperandIndex(), true,
1530 SI->getValueOperand()->getType(), SI->getAlign());
1531 } else if (AtomicRMWInst *RMW = dyn_cast<AtomicRMWInst>(I)) {
1532 if (!ClInstrumentAtomics || ignoreAccess(I, RMW->getPointerOperand()))
1533 return;
1534 Interesting.emplace_back(I, RMW->getPointerOperandIndex(), true,
1535 RMW->getValOperand()->getType(), std::nullopt);
1536 } else if (AtomicCmpXchgInst *XCHG = dyn_cast<AtomicCmpXchgInst>(I)) {
1537 if (!ClInstrumentAtomics || ignoreAccess(I, XCHG->getPointerOperand()))
1538 return;
1539 Interesting.emplace_back(I, XCHG->getPointerOperandIndex(), true,
1540 XCHG->getCompareOperand()->getType(),
1541 std::nullopt);
1542 } else if (auto CI = dyn_cast<CallInst>(I)) {
1543 switch (CI->getIntrinsicID()) {
1544 case Intrinsic::masked_load:
1545 case Intrinsic::masked_store:
1546 case Intrinsic::masked_gather:
1547 case Intrinsic::masked_scatter: {
1548 bool IsWrite = CI->getType()->isVoidTy();
1549 // Masked store has an initial operand for the value.
1550 unsigned OpOffset = IsWrite ? 1 : 0;
1551 if (IsWrite ? !ClInstrumentWrites : !ClInstrumentReads)
1552 return;
1553
1554 auto BasePtr = CI->getOperand(OpOffset);
1555 if (ignoreAccess(I, BasePtr))
1556 return;
1557 Type *Ty = IsWrite ? CI->getArgOperand(0)->getType() : CI->getType();
1558 MaybeAlign Alignment = CI->getParamAlign(0);
1559 Value *Mask = CI->getOperand(1 + OpOffset);
1560 Interesting.emplace_back(I, OpOffset, IsWrite, Ty, Alignment, Mask);
1561 break;
1562 }
1563 case Intrinsic::masked_expandload:
1564 case Intrinsic::masked_compressstore: {
1565 bool IsWrite = CI->getIntrinsicID() == Intrinsic::masked_compressstore;
1566 unsigned OpOffset = IsWrite ? 1 : 0;
1567 if (IsWrite ? !ClInstrumentWrites : !ClInstrumentReads)
1568 return;
1569 auto BasePtr = CI->getOperand(OpOffset);
1570 if (ignoreAccess(I, BasePtr))
1571 return;
1572 MaybeAlign Alignment = BasePtr->getPointerAlignment(*DL);
1573 Type *Ty = IsWrite ? CI->getArgOperand(0)->getType() : CI->getType();
1574
1575 IRBuilder IB(I);
1576 Value *Mask = CI->getOperand(1 + OpOffset);
1577 // Use the popcount of Mask as the effective vector length.
1578 Type *ExtTy = VectorType::get(IntptrTy, cast<VectorType>(Ty));
1579 Value *ExtMask = IB.CreateZExt(Mask, ExtTy);
1580 Value *EVL = IB.CreateAddReduce(ExtMask);
1581 Value *TrueMask = ConstantInt::get(Mask->getType(), 1);
1582 Interesting.emplace_back(I, OpOffset, IsWrite, Ty, Alignment, TrueMask,
1583 EVL);
1584 break;
1585 }
1586 case Intrinsic::vp_load:
1587 case Intrinsic::vp_store:
1588 case Intrinsic::experimental_vp_strided_load:
1589 case Intrinsic::experimental_vp_strided_store: {
1590 auto *VPI = cast<VPIntrinsic>(CI);
1591 unsigned IID = CI->getIntrinsicID();
1592 bool IsWrite = CI->getType()->isVoidTy();
1593 if (IsWrite ? !ClInstrumentWrites : !ClInstrumentReads)
1594 return;
1595 unsigned PtrOpNo = *VPI->getMemoryPointerParamPos(IID);
1596 Type *Ty = IsWrite ? CI->getArgOperand(0)->getType() : CI->getType();
1597 MaybeAlign Alignment = VPI->getOperand(PtrOpNo)->getPointerAlignment(*DL);
1598 Value *Stride = nullptr;
1599 if (IID == Intrinsic::experimental_vp_strided_store ||
1600 IID == Intrinsic::experimental_vp_strided_load) {
1601 Stride = VPI->getOperand(PtrOpNo + 1);
1602 // Use the pointer alignment as the element alignment if the stride is a
1603 // multiple of the pointer alignment. Otherwise, the element alignment
1604 // should be Align(1).
1605 unsigned PointerAlign = Alignment.valueOrOne().value();
1606 if (!isa<ConstantInt>(Stride) ||
1607 cast<ConstantInt>(Stride)->getZExtValue() % PointerAlign != 0)
1608 Alignment = Align(1);
1609 }
1610 Interesting.emplace_back(I, PtrOpNo, IsWrite, Ty, Alignment,
1611 VPI->getMaskParam(), VPI->getVectorLengthParam(),
1612 Stride);
1613 break;
1614 }
1615 case Intrinsic::vp_gather:
1616 case Intrinsic::vp_scatter: {
1617 auto *VPI = cast<VPIntrinsic>(CI);
1618 unsigned IID = CI->getIntrinsicID();
1619 bool IsWrite = IID == Intrinsic::vp_scatter;
1620 if (IsWrite ? !ClInstrumentWrites : !ClInstrumentReads)
1621 return;
1622 unsigned PtrOpNo = *VPI->getMemoryPointerParamPos(IID);
1623 Type *Ty = IsWrite ? CI->getArgOperand(0)->getType() : CI->getType();
1624 MaybeAlign Alignment = VPI->getPointerAlignment();
1625 Interesting.emplace_back(I, PtrOpNo, IsWrite, Ty, Alignment,
1626 VPI->getMaskParam(),
1627 VPI->getVectorLengthParam());
1628 break;
1629 }
1630 default:
1631 if (auto *II = dyn_cast<IntrinsicInst>(I)) {
1632 MemIntrinsicInfo IntrInfo;
1633 if (TTI->getTgtMemIntrinsic(II, IntrInfo))
1634 Interesting = IntrInfo.InterestingOperands;
1635 return;
1636 }
1637 for (unsigned ArgNo = 0; ArgNo < CI->arg_size(); ArgNo++) {
1638 if (!ClInstrumentByval || !CI->isByValArgument(ArgNo) ||
1639 ignoreAccess(I, CI->getArgOperand(ArgNo)))
1640 continue;
1641 Type *Ty = CI->getParamByValType(ArgNo);
1642 Interesting.emplace_back(I, ArgNo, false, Ty, Align(1));
1643 }
1644 }
1645 }
1646}
1647
1648static bool isPointerOperand(Value *V) {
1649 return V->getType()->isPointerTy() || isa<PtrToIntInst>(V);
1650}
1651
1652// This is a rough heuristic; it may cause both false positives and
1653// false negatives. The proper implementation requires cooperation with
1654// the frontend.
1656 if (ICmpInst *Cmp = dyn_cast<ICmpInst>(I)) {
1657 if (!Cmp->isRelational())
1658 return false;
1659 } else {
1660 return false;
1661 }
1662 return isPointerOperand(I->getOperand(0)) &&
1663 isPointerOperand(I->getOperand(1));
1664}
1665
1666// This is a rough heuristic; it may cause both false positives and
1667// false negatives. The proper implementation requires cooperation with
1668// the frontend.
1671 if (BO->getOpcode() != Instruction::Sub)
1672 return false;
1673 } else {
1674 return false;
1675 }
1676 return isPointerOperand(I->getOperand(0)) &&
1677 isPointerOperand(I->getOperand(1));
1678}
1679
1680bool AddressSanitizer::GlobalIsLinkerInitialized(GlobalVariable *G) {
1681 // If a global variable does not have dynamic initialization we don't
1682 // have to instrument it. However, if a global does not have initializer
1683 // at all, we assume it has dynamic initializer (in other TU).
1684 if (!G->hasInitializer())
1685 return false;
1686
1687 if (G->hasSanitizerMetadata() && G->getSanitizerMetadata().IsDynInit)
1688 return false;
1689
1690 return true;
1691}
1692
1693void AddressSanitizer::instrumentPointerComparisonOrSubtraction(
1694 Instruction *I, RuntimeCallInserter &RTCI) {
1695 IRBuilder<> IRB(I);
1696 FunctionCallee F = isa<ICmpInst>(I) ? AsanPtrCmpFunction : AsanPtrSubFunction;
1697 Value *Param[2] = {I->getOperand(0), I->getOperand(1)};
1698 for (Value *&i : Param) {
1699 if (i->getType()->isPointerTy())
1700 i = IRB.CreatePointerCast(i, IntptrTy);
1701 }
1702 RTCI.createRuntimeCall(IRB, F, Param);
1703}
1704
1705static void doInstrumentAddress(AddressSanitizer *Pass, Instruction *I,
1706 Instruction *InsertBefore, Value *Addr,
1707 MaybeAlign Alignment, unsigned Granularity,
1708 TypeSize TypeStoreSize, bool IsWrite,
1709 Value *SizeArgument, bool UseCalls,
1710 uint32_t Exp, RuntimeCallInserter &RTCI) {
1711 // Instrument a 1-, 2-, 4-, 8-, or 16- byte access with one check
1712 // if the data is properly aligned.
1713 if (!TypeStoreSize.isScalable()) {
1714 const auto FixedSize = TypeStoreSize.getFixedValue();
1715 switch (FixedSize) {
1716 case 8:
1717 case 16:
1718 case 32:
1719 case 64:
1720 case 128:
1721 if (!Alignment || *Alignment >= Granularity ||
1722 *Alignment >= FixedSize / 8)
1723 return Pass->instrumentAddress(I, InsertBefore, Addr, Alignment,
1724 FixedSize, IsWrite, nullptr, UseCalls,
1725 Exp, RTCI);
1726 }
1727 }
1728 Pass->instrumentUnusualSizeOrAlignment(I, InsertBefore, Addr, TypeStoreSize,
1729 IsWrite, nullptr, UseCalls, Exp, RTCI);
1730}
1731
1732void AddressSanitizer::instrumentMaskedLoadOrStore(
1733 AddressSanitizer *Pass, const DataLayout &DL, Type *IntptrTy, Value *Mask,
1734 Value *EVL, Value *Stride, Instruction *I, Value *Addr,
1735 MaybeAlign Alignment, unsigned Granularity, Type *OpType, bool IsWrite,
1736 Value *SizeArgument, bool UseCalls, uint32_t Exp,
1737 RuntimeCallInserter &RTCI) {
1738 auto *VTy = cast<VectorType>(OpType);
1739 TypeSize ElemTypeSize = DL.getTypeStoreSizeInBits(VTy->getScalarType());
1740 auto Zero = ConstantInt::get(IntptrTy, 0);
1741
1742 IRBuilder IB(I);
1743 Instruction *LoopInsertBefore = I;
1744 if (EVL) {
1745 // The end argument of SplitBlockAndInsertForLane is assumed bigger
1746 // than zero, so we should check whether EVL is zero here.
1747 Type *EVLType = EVL->getType();
1748 Value *IsEVLZero = IB.CreateICmpNE(EVL, ConstantInt::get(EVLType, 0));
1749 LoopInsertBefore = SplitBlockAndInsertIfThen(IsEVLZero, I, false);
1750 IB.SetInsertPoint(LoopInsertBefore);
1751 // Cast EVL to IntptrTy.
1752 EVL = IB.CreateZExtOrTrunc(EVL, IntptrTy);
1753 // To avoid undefined behavior for extracting with out of range index, use
1754 // the minimum of evl and element count as trip count.
1755 Value *EC = IB.CreateElementCount(IntptrTy, VTy->getElementCount());
1756 EVL = IB.CreateBinaryIntrinsic(Intrinsic::umin, EVL, EC);
1757 } else {
1758 EVL = IB.CreateElementCount(IntptrTy, VTy->getElementCount());
1759 }
1760
1761 // Cast Stride to IntptrTy.
1762 if (Stride)
1763 Stride = IB.CreateZExtOrTrunc(Stride, IntptrTy);
1764
1765 SplitBlockAndInsertForEachLane(EVL, LoopInsertBefore->getIterator(),
1766 [&](IRBuilderBase &IRB, Value *Index) {
1767 Value *MaskElem = IRB.CreateExtractElement(Mask, Index);
1768 if (auto *MaskElemC = dyn_cast<ConstantInt>(MaskElem)) {
1769 if (MaskElemC->isZero())
1770 // No check
1771 return;
1772 // Unconditional check
1773 } else {
1774 // Conditional check
1775 Instruction *ThenTerm = SplitBlockAndInsertIfThen(
1776 MaskElem, &*IRB.GetInsertPoint(), false);
1777 IRB.SetInsertPoint(ThenTerm);
1778 }
1779
1780 Value *InstrumentedAddress;
1781 if (isa<VectorType>(Addr->getType())) {
1782 assert(
1783 cast<VectorType>(Addr->getType())->getElementType()->isPointerTy() &&
1784 "Expected vector of pointer.");
1785 InstrumentedAddress = IRB.CreateExtractElement(Addr, Index);
1786 } else if (Stride) {
1787 Index = IRB.CreateMul(Index, Stride);
1788 InstrumentedAddress = IRB.CreatePtrAdd(Addr, Index);
1789 } else {
1790 InstrumentedAddress = IRB.CreateGEP(VTy, Addr, {Zero, Index});
1791 }
1792 doInstrumentAddress(Pass, I, &*IRB.GetInsertPoint(), InstrumentedAddress,
1793 Alignment, Granularity, ElemTypeSize, IsWrite,
1794 SizeArgument, UseCalls, Exp, RTCI);
1795 });
1796}
1797
1798void AddressSanitizer::instrumentMop(ObjectSizeOffsetVisitor &ObjSizeVis,
1799 InterestingMemoryOperand &O, bool UseCalls,
1800 const DataLayout &DL,
1801 RuntimeCallInserter &RTCI) {
1802 Value *Addr = O.getPtr();
1803
1804 // Optimization experiments.
1805 // The experiments can be used to evaluate potential optimizations that remove
1806 // instrumentation (assess false negatives). Instead of completely removing
1807 // some instrumentation, you set Exp to a non-zero value (mask of optimization
1808 // experiments that want to remove instrumentation of this instruction).
1809 // If Exp is non-zero, this pass will emit special calls into runtime
1810 // (e.g. __asan_report_exp_load1 instead of __asan_report_load1). These calls
1811 // make runtime terminate the program in a special way (with a different
1812 // exit status). Then you run the new compiler on a buggy corpus, collect
1813 // the special terminations (ideally, you don't see them at all -- no false
1814 // negatives) and make the decision on the optimization.
1815 uint32_t Exp = ClForceExperiment;
1816
1817 if (ClOpt && ClOptGlobals) {
1818 // If initialization order checking is disabled, a simple access to a
1819 // dynamically initialized global is always valid.
1821 if (G && (!ClInitializers || GlobalIsLinkerInitialized(G)) &&
1822 isSafeAccess(ObjSizeVis, Addr, O.TypeStoreSize)) {
1823 NumOptimizedAccessesToGlobalVar++;
1824 return;
1825 }
1826 }
1827
1828 if (ClOpt && ClOptStack) {
1829 // A direct inbounds access to a stack variable is always valid.
1831 isSafeAccess(ObjSizeVis, Addr, O.TypeStoreSize)) {
1832 NumOptimizedAccessesToStackVar++;
1833 return;
1834 }
1835 }
1836
1837 if (O.IsWrite)
1838 NumInstrumentedWrites++;
1839 else
1840 NumInstrumentedReads++;
1841
1842 if (O.MaybeByteOffset) {
1843 Type *Ty = Type::getInt8Ty(*C);
1844 IRBuilder IB(O.getInsn());
1845
1846 Value *OffsetOp = O.MaybeByteOffset;
1847 if (TargetTriple.isRISCV()) {
1848 Type *OffsetTy = OffsetOp->getType();
1849 // RVV indexed loads/stores zero-extend offset operands which are narrower
1850 // than XLEN to XLEN.
1851 if (OffsetTy->getScalarType()->getIntegerBitWidth() <
1852 static_cast<unsigned>(LongSize)) {
1853 VectorType *OrigType = cast<VectorType>(OffsetTy);
1854 Type *ExtendTy = VectorType::get(IntptrTy, OrigType);
1855 OffsetOp = IB.CreateZExt(OffsetOp, ExtendTy);
1856 }
1857 }
1858 Addr = IB.CreateGEP(Ty, Addr, {OffsetOp});
1859 }
1860
1861 unsigned Granularity = 1 << Mapping.Scale;
1862 if (O.MaybeMask) {
1863 instrumentMaskedLoadOrStore(this, DL, IntptrTy, O.MaybeMask, O.MaybeEVL,
1864 O.MaybeStride, O.getInsn(), Addr, O.Alignment,
1865 Granularity, O.OpType, O.IsWrite, nullptr,
1866 UseCalls, Exp, RTCI);
1867 } else {
1868 doInstrumentAddress(this, O.getInsn(), O.getInsn(), Addr, O.Alignment,
1869 Granularity, O.TypeStoreSize, O.IsWrite, nullptr,
1870 UseCalls, Exp, RTCI);
1871 }
1872}
1873
1874Instruction *AddressSanitizer::generateCrashCode(Instruction *InsertBefore,
1875 Value *Addr, bool IsWrite,
1876 size_t AccessSizeIndex,
1877 Value *SizeArgument,
1878 uint32_t Exp,
1879 RuntimeCallInserter &RTCI) {
1880 InstrumentationIRBuilder IRB(InsertBefore);
1881 Value *ExpVal = Exp == 0 ? nullptr : ConstantInt::get(IRB.getInt32Ty(), Exp);
1882 CallInst *Call = nullptr;
1883 if (SizeArgument) {
1884 if (Exp == 0)
1885 Call = RTCI.createRuntimeCall(IRB, AsanErrorCallbackSized[IsWrite][0],
1886 {Addr, SizeArgument});
1887 else
1888 Call = RTCI.createRuntimeCall(IRB, AsanErrorCallbackSized[IsWrite][1],
1889 {Addr, SizeArgument, ExpVal});
1890 } else {
1891 if (Exp == 0)
1892 Call = RTCI.createRuntimeCall(
1893 IRB, AsanErrorCallback[IsWrite][0][AccessSizeIndex], Addr);
1894 else
1895 Call = RTCI.createRuntimeCall(
1896 IRB, AsanErrorCallback[IsWrite][1][AccessSizeIndex], {Addr, ExpVal});
1897 }
1898
1900 return Call;
1901}
1902
1903Value *AddressSanitizer::createSlowPathCmp(IRBuilder<> &IRB, Value *AddrLong,
1904 Value *ShadowValue,
1905 uint32_t TypeStoreSize) {
1906 size_t Granularity = static_cast<size_t>(1) << Mapping.Scale;
1907 // Addr & (Granularity - 1)
1908 Value *LastAccessedByte =
1909 IRB.CreateAnd(AddrLong, ConstantInt::get(IntptrTy, Granularity - 1));
1910 // (Addr & (Granularity - 1)) + size - 1
1911 if (TypeStoreSize / 8 > 1)
1912 LastAccessedByte = IRB.CreateAdd(
1913 LastAccessedByte, ConstantInt::get(IntptrTy, TypeStoreSize / 8 - 1));
1914 // (uint8_t) ((Addr & (Granularity-1)) + size - 1)
1915 LastAccessedByte =
1916 IRB.CreateIntCast(LastAccessedByte, ShadowValue->getType(), false);
1917 // ((uint8_t) ((Addr & (Granularity-1)) + size - 1)) >= ShadowValue
1918 return IRB.CreateICmpSGE(LastAccessedByte, ShadowValue);
1919}
1920
1921Instruction *AddressSanitizer::instrumentAMDGPUAddress(
1922 Instruction *OrigIns, Instruction *InsertBefore, Value *Addr,
1923 uint32_t TypeStoreSize, bool IsWrite, Value *SizeArgument) {
1924 // Do not instrument unsupported addrspaces.
1926 return nullptr;
1927 Type *PtrTy = cast<PointerType>(Addr->getType()->getScalarType());
1928 // Follow host instrumentation for global and constant addresses.
1929 if (PtrTy->getPointerAddressSpace() != 0)
1930 return InsertBefore;
1931 // Instrument generic addresses in supported addressspaces.
1932 IRBuilder<> IRB(InsertBefore);
1933 Value *IsShared = IRB.CreateCall(AMDGPUAddressShared, {Addr});
1934 Value *IsPrivate = IRB.CreateCall(AMDGPUAddressPrivate, {Addr});
1935 Value *IsSharedOrPrivate = IRB.CreateOr(IsShared, IsPrivate);
1936 Value *Cmp = IRB.CreateNot(IsSharedOrPrivate);
1937 Value *AddrSpaceZeroLanding =
1938 SplitBlockAndInsertIfThen(Cmp, InsertBefore, false);
1939 InsertBefore = cast<Instruction>(AddrSpaceZeroLanding);
1940 return InsertBefore;
1941}
1942
1943Instruction *AddressSanitizer::genAMDGPUReportBlock(IRBuilder<> &IRB,
1944 Value *Cond, bool Recover) {
1945 Value *ReportCond = Cond;
1946 if (!Recover) {
1947 auto Ballot = Inserter.insertFunction(kAMDGPUBallotName, IRB.getInt64Ty(),
1948 IRB.getInt1Ty());
1949 ReportCond = IRB.CreateIsNotNull(IRB.CreateCall(Ballot, {Cond}));
1950 }
1951
1952 auto *Trm =
1953 SplitBlockAndInsertIfThen(ReportCond, &*IRB.GetInsertPoint(), false,
1955 Trm->getParent()->setName("asan.report");
1956
1957 if (Recover)
1958 return Trm;
1959
1960 Trm = SplitBlockAndInsertIfThen(Cond, Trm, false);
1961 IRB.SetInsertPoint(Trm);
1962 return IRB.CreateCall(
1963 Inserter.insertFunction(kAMDGPUUnreachableName, IRB.getVoidTy()), {});
1964}
1965
1966void AddressSanitizer::instrumentAddress(Instruction *OrigIns,
1967 Instruction *InsertBefore, Value *Addr,
1968 MaybeAlign Alignment,
1969 uint32_t TypeStoreSize, bool IsWrite,
1970 Value *SizeArgument, bool UseCalls,
1971 uint32_t Exp,
1972 RuntimeCallInserter &RTCI) {
1973 if (TargetTriple.isAMDGPU()) {
1974 InsertBefore = instrumentAMDGPUAddress(OrigIns, InsertBefore, Addr,
1975 TypeStoreSize, IsWrite, SizeArgument);
1976 if (!InsertBefore)
1977 return;
1978 }
1979
1980 InstrumentationIRBuilder IRB(InsertBefore);
1981 size_t AccessSizeIndex = TypeStoreSizeToSizeIndex(TypeStoreSize);
1982
1983 if (UseCalls && ClOptimizeCallbacks) {
1984 const ASanAccessInfo AccessInfo(IsWrite, CompileKernel, AccessSizeIndex);
1985 IRB.CreateIntrinsic(Intrinsic::asan_check_memaccess, {},
1986 {IRB.CreatePointerCast(Addr, PtrTy),
1987 ConstantInt::get(Int32Ty, AccessInfo.Packed)});
1988 return;
1989 }
1990
1991 Value *AddrLong = IRB.CreatePointerCast(Addr, IntptrTy);
1992 if (UseCalls) {
1993 if (Exp == 0)
1994 RTCI.createRuntimeCall(
1995 IRB, AsanMemoryAccessCallback[IsWrite][0][AccessSizeIndex], AddrLong);
1996 else
1997 RTCI.createRuntimeCall(
1998 IRB, AsanMemoryAccessCallback[IsWrite][1][AccessSizeIndex],
1999 {AddrLong, ConstantInt::get(IRB.getInt32Ty(), Exp)});
2000 return;
2001 }
2002
2003 Type *ShadowTy =
2004 IntegerType::get(*C, std::max(8U, TypeStoreSize >> Mapping.Scale));
2005 Type *ShadowPtrTy = PointerType::get(*C, ClShadowAddrSpace);
2006 Value *ShadowPtr = memToShadow(AddrLong, IRB);
2007 const uint64_t ShadowAlign =
2008 std::max<uint64_t>(Alignment.valueOrOne().value() >> Mapping.Scale, 1);
2009 Value *ShadowValue = IRB.CreateAlignedLoad(
2010 ShadowTy, IRB.CreateIntToPtr(ShadowPtr, ShadowPtrTy), Align(ShadowAlign));
2011
2012 Value *Cmp = IRB.CreateIsNotNull(ShadowValue);
2013 size_t Granularity = 1ULL << Mapping.Scale;
2014 Instruction *CrashTerm = nullptr;
2015
2016 bool GenSlowPath = (ClAlwaysSlowPath || (TypeStoreSize < 8 * Granularity));
2017
2018 if (TargetTriple.isAMDGCN()) {
2019 if (GenSlowPath) {
2020 auto *Cmp2 = createSlowPathCmp(IRB, AddrLong, ShadowValue, TypeStoreSize);
2021 Cmp = IRB.CreateAnd(Cmp, Cmp2);
2022 }
2023 CrashTerm = genAMDGPUReportBlock(IRB, Cmp, Recover);
2024 } else if (GenSlowPath) {
2025 // We use branch weights for the slow path check, to indicate that the slow
2026 // path is rarely taken. This seems to be the case for SPEC benchmarks.
2028 Cmp, InsertBefore, false, MDBuilder(*C).createUnlikelyBranchWeights());
2029 BasicBlock *NextBB = cast<UncondBrInst>(CheckTerm)->getSuccessor();
2030 IRB.SetInsertPoint(CheckTerm);
2031 Value *Cmp2 = createSlowPathCmp(IRB, AddrLong, ShadowValue, TypeStoreSize);
2032 if (Recover) {
2033 CrashTerm = SplitBlockAndInsertIfThen(Cmp2, CheckTerm, false);
2034 } else {
2035 BasicBlock *CrashBlock =
2036 BasicBlock::Create(*C, "", NextBB->getParent(), NextBB);
2037 CrashTerm = new UnreachableInst(*C, CrashBlock);
2038 CondBrInst *NewTerm = CondBrInst::Create(Cmp2, CrashBlock, NextBB);
2039 ReplaceInstWithInst(CheckTerm, NewTerm);
2040 }
2041 } else {
2042 CrashTerm = SplitBlockAndInsertIfThen(Cmp, InsertBefore, !Recover);
2043 }
2044
2045 Instruction *Crash = generateCrashCode(
2046 CrashTerm, AddrLong, IsWrite, AccessSizeIndex, SizeArgument, Exp, RTCI);
2047 if (OrigIns->getDebugLoc())
2048 Crash->setDebugLoc(OrigIns->getDebugLoc());
2049}
2050
2051// Instrument unusual size or unusual alignment.
2052// We can not do it with a single check, so we do 1-byte check for the first
2053// and the last bytes. We call __asan_report_*_n(addr, real_size) to be able
2054// to report the actual access size.
2055void AddressSanitizer::instrumentUnusualSizeOrAlignment(
2056 Instruction *I, Instruction *InsertBefore, Value *Addr,
2057 TypeSize TypeStoreSize, bool IsWrite, Value *SizeArgument, bool UseCalls,
2058 uint32_t Exp, RuntimeCallInserter &RTCI) {
2059 InstrumentationIRBuilder IRB(InsertBefore);
2060 Value *NumBits = IRB.CreateTypeSize(IntptrTy, TypeStoreSize);
2061 Value *Size = IRB.CreateLShr(NumBits, ConstantInt::get(IntptrTy, 3));
2062
2063 Value *AddrLong = IRB.CreatePointerCast(Addr, IntptrTy);
2064 if (UseCalls) {
2065 if (Exp == 0)
2066 RTCI.createRuntimeCall(IRB, AsanMemoryAccessCallbackSized[IsWrite][0],
2067 {AddrLong, Size});
2068 else
2069 RTCI.createRuntimeCall(
2070 IRB, AsanMemoryAccessCallbackSized[IsWrite][1],
2071 {AddrLong, Size, ConstantInt::get(IRB.getInt32Ty(), Exp)});
2072 } else {
2073 Value *SizeMinusOne = IRB.CreateSub(Size, ConstantInt::get(IntptrTy, 1));
2074 Value *LastByte = IRB.CreateIntToPtr(
2075 IRB.CreateAdd(AddrLong, SizeMinusOne),
2076 Addr->getType());
2077 instrumentAddress(I, InsertBefore, Addr, {}, 8, IsWrite, Size, false, Exp,
2078 RTCI);
2079 instrumentAddress(I, InsertBefore, LastByte, {}, 8, IsWrite, Size, false,
2080 Exp, RTCI);
2081 }
2082}
2083
2084void ModuleAddressSanitizer::poisonOneInitializer(Function &GlobalInit) {
2085 // Set up the arguments to our poison/unpoison functions.
2086 IRBuilder<> IRB(&GlobalInit.front(),
2087 GlobalInit.front().getFirstInsertionPt());
2088
2089 // Add a call to poison all external globals before the given function starts.
2090 Value *ModuleNameAddr =
2091 ConstantExpr::getPointerCast(getOrCreateModuleName(), IntptrTy);
2092 IRB.CreateCall(AsanPoisonGlobals, ModuleNameAddr);
2093
2094 // Add calls to unpoison all globals before each return instruction.
2095 for (auto &BB : GlobalInit)
2097 CallInst::Create(AsanUnpoisonGlobals, "", RI->getIterator());
2098}
2099
2100void ModuleAddressSanitizer::createInitializerPoisonCalls() {
2101 GlobalVariable *GV = M.getGlobalVariable("llvm.global_ctors");
2102 if (!GV)
2103 return;
2104
2106 if (!CA)
2107 return;
2108
2109 for (Use &OP : CA->operands()) {
2110 if (isa<ConstantAggregateZero>(OP)) continue;
2112
2113 // Must have a function or null ptr.
2114 if (Function *F = dyn_cast<Function>(CS->getOperand(1))) {
2115 if (F->getName() == kAsanModuleCtorName) continue;
2116 auto *Priority = cast<ConstantInt>(CS->getOperand(0));
2117 // Don't instrument CTORs that will run before asan.module_ctor.
2118 if (Priority->getLimitedValue() <= GetCtorAndDtorPriority(TargetTriple))
2119 continue;
2120 poisonOneInitializer(*F);
2121 }
2122 }
2123}
2124
2125const GlobalVariable *
2126ModuleAddressSanitizer::getExcludedAliasedGlobal(const GlobalAlias &GA) const {
2127 // In case this function should be expanded to include rules that do not just
2128 // apply when CompileKernel is true, either guard all existing rules with an
2129 // 'if (CompileKernel) { ... }' or be absolutely sure that all these rules
2130 // should also apply to user space.
2131 assert(CompileKernel && "Only expecting to be called when compiling kernel");
2132
2133 const Constant *C = GA.getAliasee();
2134
2135 // When compiling the kernel, globals that are aliased by symbols prefixed
2136 // by "__" are special and cannot be padded with a redzone.
2137 if (GA.getName().starts_with("__"))
2138 return dyn_cast<GlobalVariable>(C->stripPointerCastsAndAliases());
2139
2140 return nullptr;
2141}
2142
2143bool ModuleAddressSanitizer::shouldInstrumentGlobal(GlobalVariable *G) const {
2144 Type *Ty = G->getValueType();
2145 LLVM_DEBUG(dbgs() << "GLOBAL: " << *G << "\n");
2146
2147 if (G->hasSanitizerMetadata() && G->getSanitizerMetadata().NoAddress)
2148 return false;
2149 if (!Ty->isSized()) return false;
2150 if (!G->hasInitializer()) return false;
2151 if (!isSupportedAddrspace(TargetTriple, G))
2152 return false;
2153 if (GlobalWasGeneratedByCompiler(G)) return false; // Our own globals.
2154 // Two problems with thread-locals:
2155 // - The address of the main thread's copy can't be computed at link-time.
2156 // - Need to poison all copies, not just the main thread's one.
2157 if (G->isThreadLocal()) return false;
2158 // For now, just ignore this Global if the alignment is large.
2159 if (G->getAlign() && *G->getAlign() > getMinRedzoneSizeForGlobal()) return false;
2160
2161 // For non-COFF targets, only instrument globals known to be defined by this
2162 // TU.
2163 // FIXME: We can instrument comdat globals on ELF if we are using the
2164 // GC-friendly metadata scheme.
2165 if (!TargetTriple.isOSBinFormatCOFF()) {
2166 if (!G->hasExactDefinition() || G->hasComdat())
2167 return false;
2168 } else {
2169 // On COFF, don't instrument non-ODR linkages.
2170 if (G->isInterposable())
2171 return false;
2172 // If the global has AvailableExternally linkage, then it is not in this
2173 // module, which means it does not need to be instrumented.
2174 if (G->hasAvailableExternallyLinkage())
2175 return false;
2176 }
2177
2178 // If a comdat is present, it must have a selection kind that implies ODR
2179 // semantics: no duplicates, any, or exact match.
2180 if (Comdat *C = G->getComdat()) {
2181 switch (C->getSelectionKind()) {
2182 case Comdat::Any:
2183 case Comdat::ExactMatch:
2185 break;
2186 case Comdat::Largest:
2187 case Comdat::SameSize:
2188 return false;
2189 }
2190 }
2191
2192 if (G->hasSection()) {
2193 // The kernel uses explicit sections for mostly special global variables
2194 // that we should not instrument. E.g. the kernel may rely on their layout
2195 // without redzones, or remove them at link time ("discard.*"), etc.
2196 if (CompileKernel)
2197 return false;
2198
2199 StringRef Section = G->getSection();
2200
2201 // Globals from llvm.metadata aren't emitted, do not instrument them.
2202 if (Section == "llvm.metadata") return false;
2203 // Do not instrument globals from special LLVM sections.
2204 if (Section.contains("__llvm") || Section.contains("__LLVM"))
2205 return false;
2206
2207 // Do not instrument function pointers to initialization and termination
2208 // routines: dynamic linker will not properly handle redzones.
2209 if (Section.starts_with(".preinit_array") ||
2210 Section.starts_with(".init_array") ||
2211 Section.starts_with(".fini_array")) {
2212 return false;
2213 }
2214
2215 // Do not instrument user-defined sections (with names resembling
2216 // valid C identifiers)
2217 if (TargetTriple.isOSBinFormatELF()) {
2218 if (llvm::all_of(Section,
2219 [](char c) { return llvm::isAlnum(c) || c == '_'; }))
2220 return false;
2221 }
2222
2223 // On COFF, if the section name contains '$', it is highly likely that the
2224 // user is using section sorting to create an array of globals similar to
2225 // the way initialization callbacks are registered in .init_array and
2226 // .CRT$XCU. The ATL also registers things in .ATL$__[azm]. Adding redzones
2227 // to such globals is counterproductive, because the intent is that they
2228 // will form an array, and out-of-bounds accesses are expected.
2229 // See https://github.com/google/sanitizers/issues/305
2230 // and http://msdn.microsoft.com/en-US/en-en/library/bb918180(v=vs.120).aspx
2231 if (TargetTriple.isOSBinFormatCOFF() && Section.contains('$')) {
2232 LLVM_DEBUG(dbgs() << "Ignoring global in sorted section (contains '$'): "
2233 << *G << "\n");
2234 return false;
2235 }
2236
2237 if (TargetTriple.isOSBinFormatMachO()) {
2238 StringRef ParsedSegment, ParsedSection;
2239 unsigned TAA = 0, StubSize = 0;
2240 bool TAAParsed;
2242 Section, ParsedSegment, ParsedSection, TAA, TAAParsed, StubSize));
2243
2244 // Ignore the globals from the __OBJC section. The ObjC runtime assumes
2245 // those conform to /usr/lib/objc/runtime.h, so we can't add redzones to
2246 // them.
2247 if (ParsedSegment == "__OBJC" ||
2248 (ParsedSegment == "__DATA" && ParsedSection.starts_with("__objc_"))) {
2249 LLVM_DEBUG(dbgs() << "Ignoring ObjC runtime global: " << *G << "\n");
2250 return false;
2251 }
2252 // See https://github.com/google/sanitizers/issues/32
2253 // Constant CFString instances are compiled in the following way:
2254 // -- the string buffer is emitted into
2255 // __TEXT,__cstring,cstring_literals
2256 // -- the constant NSConstantString structure referencing that buffer
2257 // is placed into __DATA,__cfstring
2258 // Therefore there's no point in placing redzones into __DATA,__cfstring.
2259 // Moreover, it causes the linker to crash on OS X 10.7
2260 if (ParsedSegment == "__DATA" && ParsedSection == "__cfstring") {
2261 LLVM_DEBUG(dbgs() << "Ignoring CFString: " << *G << "\n");
2262 return false;
2263 }
2264 // The linker merges the contents of cstring_literals and removes the
2265 // trailing zeroes.
2266 if (ParsedSegment == "__TEXT" && (TAA & MachO::S_CSTRING_LITERALS)) {
2267 LLVM_DEBUG(dbgs() << "Ignoring a cstring literal: " << *G << "\n");
2268 return false;
2269 }
2270 }
2271 }
2272
2273 if (CompileKernel) {
2274 // Globals that prefixed by "__" are special and cannot be padded with a
2275 // redzone.
2276 if (G->getName().starts_with("__"))
2277 return false;
2278 }
2279
2280 return true;
2281}
2282
2283// On Mach-O platforms, we emit global metadata in a separate section of the
2284// binary in order to allow the linker to properly dead strip. This is only
2285// supported on recent versions of ld64.
2286bool ModuleAddressSanitizer::ShouldUseMachOGlobalsSection() const {
2287 if (!TargetTriple.isOSBinFormatMachO())
2288 return false;
2289
2290 if (TargetTriple.isMacOSX() && !TargetTriple.isMacOSXVersionLT(10, 11))
2291 return true;
2292 if (TargetTriple.isiOS() /* or tvOS */ && !TargetTriple.isOSVersionLT(9))
2293 return true;
2294 if (TargetTriple.isWatchOS() && !TargetTriple.isOSVersionLT(2))
2295 return true;
2296 if (TargetTriple.isDriverKit())
2297 return true;
2298 if (TargetTriple.isXROS())
2299 return true;
2300
2301 return false;
2302}
2303
2304StringRef ModuleAddressSanitizer::getGlobalMetadataSection() const {
2305 switch (TargetTriple.getObjectFormat()) {
2306 case Triple::COFF: return ".ASAN$GL";
2307 case Triple::ELF: return "asan_globals";
2308 case Triple::MachO: return "__DATA,__asan_globals,regular";
2309 case Triple::Wasm:
2310 case Triple::GOFF:
2311 case Triple::SPIRV:
2312 case Triple::XCOFF:
2315 "ModuleAddressSanitizer not implemented for object file format");
2317 break;
2318 }
2319 llvm_unreachable("unsupported object format");
2320}
2321
2322void ModuleAddressSanitizer::initializeCallbacks() {
2323 IRBuilder<> IRB(*C);
2324
2325 // Declare our poisoning and unpoisoning functions.
2326 AsanPoisonGlobals = Inserter.insertFunction(kAsanPoisonGlobalsName,
2327 IRB.getVoidTy(), IntptrTy);
2328 AsanUnpoisonGlobals =
2329 Inserter.insertFunction(kAsanUnpoisonGlobalsName, IRB.getVoidTy());
2330
2331 // Declare functions that register/unregister globals.
2332 AsanRegisterGlobals = Inserter.insertFunction(
2333 kAsanRegisterGlobalsName, IRB.getVoidTy(), IntptrTy, IntptrTy);
2334 AsanUnregisterGlobals = Inserter.insertFunction(
2335 kAsanUnregisterGlobalsName, IRB.getVoidTy(), IntptrTy, IntptrTy);
2336
2337 // Declare the functions that find globals in a shared object and then invoke
2338 // the (un)register function on them.
2339 AsanRegisterImageGlobals = Inserter.insertFunction(
2340 kAsanRegisterImageGlobalsName, IRB.getVoidTy(), IntptrTy);
2341 AsanUnregisterImageGlobals = Inserter.insertFunction(
2343
2344 AsanRegisterElfGlobals =
2345 Inserter.insertFunction(kAsanRegisterElfGlobalsName, IRB.getVoidTy(),
2346 IntptrTy, IntptrTy, IntptrTy);
2347 AsanUnregisterElfGlobals =
2348 Inserter.insertFunction(kAsanUnregisterElfGlobalsName, IRB.getVoidTy(),
2349 IntptrTy, IntptrTy, IntptrTy);
2350}
2351
2352// Put the metadata and the instrumented global in the same group. This ensures
2353// that the metadata is discarded if the instrumented global is discarded.
2354void ModuleAddressSanitizer::SetComdatForGlobalMetadata(
2355 GlobalVariable *G, GlobalVariable *Metadata, StringRef InternalSuffix) {
2356 Module &M = *G->getParent();
2357 Comdat *C = G->getComdat();
2358 if (!C) {
2359 if (!G->hasName()) {
2360 // If G is unnamed, it must be internal. Give it an artificial name
2361 // so we can put it in a comdat.
2362 assert(G->hasLocalLinkage());
2363 G->setName(genName("anon_global"));
2364 }
2365
2366 if (!InternalSuffix.empty() && G->hasLocalLinkage()) {
2367 std::string Name = std::string(G->getName());
2368 Name += InternalSuffix;
2369 C = M.getOrInsertComdat(Name);
2370 } else {
2371 C = M.getOrInsertComdat(G->getName());
2372 }
2373
2374 // Make this IMAGE_COMDAT_SELECT_NODUPLICATES on COFF. Also upgrade private
2375 // linkage to internal linkage so that a symbol table entry is emitted. This
2376 // is necessary in order to create the comdat group.
2377 if (TargetTriple.isOSBinFormatCOFF()) {
2378 C->setSelectionKind(Comdat::NoDeduplicate);
2379 if (G->hasPrivateLinkage())
2380 G->setLinkage(GlobalValue::InternalLinkage);
2381 }
2382 G->setComdat(C);
2383 }
2384
2385 assert(G->hasComdat());
2386 Metadata->setComdat(G->getComdat());
2387}
2388
2389// Create a separate metadata global and put it in the appropriate ASan
2390// global registration section.
2392ModuleAddressSanitizer::CreateMetadataGlobal(Constant *Initializer,
2393 StringRef OriginalName) {
2394 auto Linkage = TargetTriple.isOSBinFormatMachO()
2398 M, Initializer->getType(), false, Linkage, Initializer,
2399 Twine("__asan_global_") + GlobalValue::dropLLVMManglingEscape(OriginalName));
2400 Metadata->setSection(getGlobalMetadataSection());
2401 // Place metadata in a large section for x86-64 ELF binaries to mitigate
2402 // relocation pressure.
2404 return Metadata;
2405}
2406
2407Instruction *ModuleAddressSanitizer::CreateAsanModuleDtor() {
2408 AsanDtorFunction = Function::createWithDefaultAttr(
2411 AsanDtorFunction->addFnAttr(Attribute::NoUnwind);
2412 // Ensure Dtor cannot be discarded, even if in a comdat.
2413 appendToUsed(M, {AsanDtorFunction});
2414 BasicBlock *AsanDtorBB = BasicBlock::Create(*C, "", AsanDtorFunction);
2415
2416 return ReturnInst::Create(*C, AsanDtorBB);
2417}
2418
2419void ModuleAddressSanitizer::InstrumentGlobalsCOFF(
2420 IRBuilder<> &IRB, ArrayRef<GlobalVariable *> ExtendedGlobals,
2421 ArrayRef<Constant *> MetadataInitializers) {
2422 assert(ExtendedGlobals.size() == MetadataInitializers.size());
2423 auto &DL = M.getDataLayout();
2424
2425 SmallVector<GlobalValue *, 16> MetadataGlobals(ExtendedGlobals.size());
2426 for (size_t i = 0; i < ExtendedGlobals.size(); i++) {
2427 Constant *Initializer = MetadataInitializers[i];
2428 GlobalVariable *G = ExtendedGlobals[i];
2429 GlobalVariable *Metadata = CreateMetadataGlobal(Initializer, G->getName());
2430 MDNode *MD = MDNode::get(M.getContext(), ValueAsMetadata::get(G));
2431 Metadata->setMetadata(LLVMContext::MD_associated, MD);
2432 MetadataGlobals[i] = Metadata;
2433
2434 // The MSVC linker always inserts padding when linking incrementally. We
2435 // cope with that by aligning each struct to its size, which must be a power
2436 // of two.
2437 unsigned SizeOfGlobalStruct = DL.getTypeAllocSize(Initializer->getType());
2438 assert(isPowerOf2_32(SizeOfGlobalStruct) &&
2439 "global metadata will not be padded appropriately");
2440 Metadata->setAlignment(assumeAligned(SizeOfGlobalStruct));
2441
2442 SetComdatForGlobalMetadata(G, Metadata, "");
2443 }
2444
2445 // Update llvm.compiler.used, adding the new metadata globals. This is
2446 // needed so that during LTO these variables stay alive.
2447 if (!MetadataGlobals.empty())
2448 appendToCompilerUsed(M, MetadataGlobals);
2449}
2450
2451void ModuleAddressSanitizer::instrumentGlobalsELF(
2452 IRBuilder<> &IRB, ArrayRef<GlobalVariable *> ExtendedGlobals,
2453 ArrayRef<Constant *> MetadataInitializers,
2454 const std::string &UniqueModuleId) {
2455 assert(ExtendedGlobals.size() == MetadataInitializers.size());
2456
2457 // Putting globals in a comdat changes the semantic and potentially cause
2458 // false negative odr violations at link time. If odr indicators are used, we
2459 // keep the comdat sections, as link time odr violations will be detected on
2460 // the odr indicator symbols.
2461 bool UseComdatForGlobalsGC = UseOdrIndicator && !UniqueModuleId.empty();
2462
2463 SmallVector<GlobalValue *, 16> MetadataGlobals(ExtendedGlobals.size());
2464 for (size_t i = 0; i < ExtendedGlobals.size(); i++) {
2465 GlobalVariable *G = ExtendedGlobals[i];
2467 CreateMetadataGlobal(MetadataInitializers[i], G->getName());
2468 MDNode *MD = MDNode::get(M.getContext(), ValueAsMetadata::get(G));
2469 Metadata->setMetadata(LLVMContext::MD_associated, MD);
2470 MetadataGlobals[i] = Metadata;
2471
2472 if (UseComdatForGlobalsGC)
2473 SetComdatForGlobalMetadata(G, Metadata, UniqueModuleId);
2474 }
2475
2476 // Update llvm.compiler.used, adding the new metadata globals. This is
2477 // needed so that during LTO these variables stay alive.
2478 if (!MetadataGlobals.empty())
2479 appendToCompilerUsed(M, MetadataGlobals);
2480
2481 // RegisteredFlag serves two purposes. First, we can pass it to dladdr()
2482 // to look up the loaded image that contains it. Second, we can store in it
2483 // whether registration has already occurred, to prevent duplicate
2484 // registration.
2485 //
2486 // Common linkage ensures that there is only one global per shared library.
2487 GlobalVariable *RegisteredFlag = new GlobalVariable(
2488 M, IntptrTy, false, GlobalVariable::CommonLinkage,
2489 ConstantInt::get(IntptrTy, 0), kAsanGlobalsRegisteredFlagName);
2491
2492 // Create start and stop symbols.
2493 GlobalVariable *StartELFMetadata = new GlobalVariable(
2494 M, IntptrTy, false, GlobalVariable::ExternalWeakLinkage, nullptr,
2495 "__start_" + getGlobalMetadataSection());
2497 GlobalVariable *StopELFMetadata = new GlobalVariable(
2498 M, IntptrTy, false, GlobalVariable::ExternalWeakLinkage, nullptr,
2499 "__stop_" + getGlobalMetadataSection());
2501
2502 // Create a call to register the globals with the runtime.
2503 if (ConstructorKind == AsanCtorKind::Global)
2504 IRB.CreateCall(AsanRegisterElfGlobals,
2505 {IRB.CreatePointerCast(RegisteredFlag, IntptrTy),
2506 IRB.CreatePointerCast(StartELFMetadata, IntptrTy),
2507 IRB.CreatePointerCast(StopELFMetadata, IntptrTy)});
2508
2509 // We also need to unregister globals at the end, e.g., when a shared library
2510 // gets closed.
2511 if (DestructorKind != AsanDtorKind::None && !MetadataGlobals.empty()) {
2512 IRBuilder<> IrbDtor(CreateAsanModuleDtor());
2513 IrbDtor.CreateCall(AsanUnregisterElfGlobals,
2514 {IRB.CreatePointerCast(RegisteredFlag, IntptrTy),
2515 IRB.CreatePointerCast(StartELFMetadata, IntptrTy),
2516 IRB.CreatePointerCast(StopELFMetadata, IntptrTy)});
2517 }
2518}
2519
2520void ModuleAddressSanitizer::InstrumentGlobalsMachO(
2521 IRBuilder<> &IRB, ArrayRef<GlobalVariable *> ExtendedGlobals,
2522 ArrayRef<Constant *> MetadataInitializers) {
2523 assert(ExtendedGlobals.size() == MetadataInitializers.size());
2524
2525 // On recent Mach-O platforms, use a structure which binds the liveness of
2526 // the global variable to the metadata struct. Keep the list of "Liveness" GV
2527 // created to be added to llvm.compiler.used
2528 StructType *LivenessTy = StructType::get(IntptrTy, IntptrTy);
2529 SmallVector<GlobalValue *, 16> LivenessGlobals(ExtendedGlobals.size());
2530
2531 for (size_t i = 0; i < ExtendedGlobals.size(); i++) {
2532 Constant *Initializer = MetadataInitializers[i];
2533 GlobalVariable *G = ExtendedGlobals[i];
2534 GlobalVariable *Metadata = CreateMetadataGlobal(Initializer, G->getName());
2535
2536 // On recent Mach-O platforms, we emit the global metadata in a way that
2537 // allows the linker to properly strip dead globals.
2538 auto LivenessBinder =
2539 ConstantStruct::get(LivenessTy, Initializer->getAggregateElement(0u),
2541 GlobalVariable *Liveness = new GlobalVariable(
2542 M, LivenessTy, false, GlobalVariable::InternalLinkage, LivenessBinder,
2543 Twine("__asan_binder_") + G->getName());
2544 Liveness->setSection("__DATA,__asan_liveness,regular,live_support");
2545 LivenessGlobals[i] = Liveness;
2546 }
2547
2548 // Update llvm.compiler.used, adding the new liveness globals. This is
2549 // needed so that during LTO these variables stay alive. The alternative
2550 // would be to have the linker handling the LTO symbols, but libLTO
2551 // current API does not expose access to the section for each symbol.
2552 if (!LivenessGlobals.empty())
2553 appendToCompilerUsed(M, LivenessGlobals);
2554
2555 // RegisteredFlag serves two purposes. First, we can pass it to dladdr()
2556 // to look up the loaded image that contains it. Second, we can store in it
2557 // whether registration has already occurred, to prevent duplicate
2558 // registration.
2559 //
2560 // common linkage ensures that there is only one global per shared library.
2561 GlobalVariable *RegisteredFlag = new GlobalVariable(
2562 M, IntptrTy, false, GlobalVariable::CommonLinkage,
2563 ConstantInt::get(IntptrTy, 0), kAsanGlobalsRegisteredFlagName);
2565
2566 if (ConstructorKind == AsanCtorKind::Global)
2567 IRB.CreateCall(AsanRegisterImageGlobals,
2568 {IRB.CreatePointerCast(RegisteredFlag, IntptrTy)});
2569
2570 // We also need to unregister globals at the end, e.g., when a shared library
2571 // gets closed.
2572 if (DestructorKind != AsanDtorKind::None) {
2573 IRBuilder<> IrbDtor(CreateAsanModuleDtor());
2574 IrbDtor.CreateCall(AsanUnregisterImageGlobals,
2575 {IRB.CreatePointerCast(RegisteredFlag, IntptrTy)});
2576 }
2577}
2578
2579void ModuleAddressSanitizer::InstrumentGlobalsWithMetadataArray(
2580 IRBuilder<> &IRB, ArrayRef<GlobalVariable *> ExtendedGlobals,
2581 ArrayRef<Constant *> MetadataInitializers) {
2582 assert(ExtendedGlobals.size() == MetadataInitializers.size());
2583 unsigned N = ExtendedGlobals.size();
2584 assert(N > 0);
2585
2586 // On platforms that don't have a custom metadata section, we emit an array
2587 // of global metadata structures.
2588 ArrayType *ArrayOfGlobalStructTy =
2589 ArrayType::get(MetadataInitializers[0]->getType(), N);
2590 auto AllGlobals = new GlobalVariable(
2591 M, ArrayOfGlobalStructTy, false, GlobalVariable::InternalLinkage,
2592 ConstantArray::get(ArrayOfGlobalStructTy, MetadataInitializers), "");
2593 if (Mapping.Scale > 3)
2594 AllGlobals->setAlignment(Align(1ULL << Mapping.Scale));
2595
2596 if (ConstructorKind == AsanCtorKind::Global)
2597 IRB.CreateCall(AsanRegisterGlobals,
2598 {IRB.CreatePointerCast(AllGlobals, IntptrTy),
2599 ConstantInt::get(IntptrTy, N)});
2600
2601 // We also need to unregister globals at the end, e.g., when a shared library
2602 // gets closed.
2603 if (DestructorKind != AsanDtorKind::None) {
2604 IRBuilder<> IrbDtor(CreateAsanModuleDtor());
2605 IrbDtor.CreateCall(AsanUnregisterGlobals,
2606 {IRB.CreatePointerCast(AllGlobals, IntptrTy),
2607 ConstantInt::get(IntptrTy, N)});
2608 }
2609}
2610
2611// This function replaces all global variables with new variables that have
2612// trailing redzones. It also creates a function that poisons
2613// redzones and inserts this function into llvm.global_ctors.
2614// Sets *CtorComdat to true if the global registration code emitted into the
2615// asan constructor is comdat-compatible.
2616void ModuleAddressSanitizer::instrumentGlobals(IRBuilder<> &IRB,
2617 bool *CtorComdat) {
2618 // Build set of globals that are aliased by some GA, where
2619 // getExcludedAliasedGlobal(GA) returns the relevant GlobalVariable.
2620 SmallPtrSet<const GlobalVariable *, 16> AliasedGlobalExclusions;
2621 if (CompileKernel) {
2622 for (auto &GA : M.aliases()) {
2623 if (const GlobalVariable *GV = getExcludedAliasedGlobal(GA))
2624 AliasedGlobalExclusions.insert(GV);
2625 }
2626 }
2627
2628 SmallVector<GlobalVariable *, 16> GlobalsToChange;
2629 for (auto &G : M.globals()) {
2630 if (!AliasedGlobalExclusions.count(&G) && shouldInstrumentGlobal(&G))
2631 GlobalsToChange.push_back(&G);
2632 }
2633
2634 size_t n = GlobalsToChange.size();
2635 auto &DL = M.getDataLayout();
2636
2637 // A global is described by a structure
2638 // size_t beg;
2639 // size_t size;
2640 // size_t size_with_redzone;
2641 // const char *name;
2642 // const char *module_name;
2643 // size_t has_dynamic_init;
2644 // size_t padding_for_windows_msvc_incremental_link;
2645 // size_t odr_indicator;
2646 // We initialize an array of such structures and pass it to a run-time call.
2647 StructType *GlobalStructTy =
2648 StructType::get(IntptrTy, IntptrTy, IntptrTy, IntptrTy, IntptrTy,
2649 IntptrTy, IntptrTy, IntptrTy);
2651 SmallVector<Constant *, 16> Initializers(n);
2652
2653 for (size_t i = 0; i < n; i++) {
2654 GlobalVariable *G = GlobalsToChange[i];
2655
2657 if (G->hasSanitizerMetadata())
2658 MD = G->getSanitizerMetadata();
2659
2660 // The runtime library tries demangling symbol names in the descriptor but
2661 // functionality like __cxa_demangle may be unavailable (e.g.
2662 // -static-libstdc++). So we demangle the symbol names here.
2663 std::string NameForGlobal = G->getName().str();
2666 /*AllowMerging*/ true, genName("global"));
2667
2668 Type *Ty = G->getValueType();
2669 const uint64_t SizeInBytes = DL.getTypeAllocSize(Ty);
2670 const uint64_t RightRedzoneSize = getRedzoneSizeForGlobal(SizeInBytes);
2671 Type *RightRedZoneTy = ArrayType::get(IRB.getInt8Ty(), RightRedzoneSize);
2672
2673 StructType *NewTy = StructType::get(Ty, RightRedZoneTy);
2674 Constant *NewInitializer = ConstantStruct::get(
2675 NewTy, G->getInitializer(), Constant::getNullValue(RightRedZoneTy));
2676
2677 // Create a new global variable with enough space for a redzone.
2678 GlobalValue::LinkageTypes Linkage = G->getLinkage();
2679 if (G->isConstant() && Linkage == GlobalValue::PrivateLinkage)
2681 GlobalVariable *NewGlobal = new GlobalVariable(
2682 M, NewTy, G->isConstant(), Linkage, NewInitializer, "", G,
2683 G->getThreadLocalMode(), G->getAddressSpace());
2684 NewGlobal->copyAttributesFrom(G);
2685 NewGlobal->setComdat(G->getComdat());
2686 NewGlobal->setAlignment(Align(getMinRedzoneSizeForGlobal()));
2687 // Don't fold globals with redzones. ODR violation detector and redzone
2688 // poisoning implicitly creates a dependence on the global's address, so it
2689 // is no longer valid for it to be marked unnamed_addr.
2691
2692 // Move null-terminated C strings to "__asan_cstring" section on Darwin.
2693 if (TargetTriple.isOSBinFormatMachO() && !G->hasSection() &&
2694 G->isConstant()) {
2695 auto Seq = dyn_cast<ConstantDataSequential>(G->getInitializer());
2696 if (Seq && Seq->isCString())
2697 NewGlobal->setSection("__TEXT,__asan_cstring,regular");
2698 }
2699
2700 // Transfer the debug info and type metadata. The payload starts at offset
2701 // zero so we can copy the metadata over as is.
2702 NewGlobal->copyMetadata(G, 0);
2703
2704 G->replaceAllUsesWith(NewGlobal);
2705 NewGlobal->takeName(G);
2706 G->eraseFromParent();
2707 NewGlobals[i] = NewGlobal;
2708
2709 Constant *ODRIndicator = Constant::getNullValue(IntptrTy);
2710 GlobalValue *InstrumentedGlobal = NewGlobal;
2711
2712 bool CanUsePrivateAliases =
2713 TargetTriple.isOSBinFormatELF() || TargetTriple.isOSBinFormatMachO() ||
2714 TargetTriple.isOSBinFormatWasm();
2715 if (CanUsePrivateAliases && UsePrivateAlias) {
2716 // Create local alias for NewGlobal to avoid crash on ODR between
2717 // instrumented and non-instrumented libraries.
2718 InstrumentedGlobal =
2720 }
2721
2722 // ODR should not happen for local linkage.
2723 if (NewGlobal->hasLocalLinkage()) {
2724 ODRIndicator = ConstantInt::getAllOnesValue(IntptrTy);
2725 } else if (UseOdrIndicator) {
2726 // With local aliases, we need to provide another externally visible
2727 // symbol __odr_asan_XXX to detect ODR violation.
2728 auto *ODRIndicatorSym =
2729 new GlobalVariable(M, IRB.getInt8Ty(), false, Linkage,
2731 kODRGenPrefix + NameForGlobal, nullptr,
2732 NewGlobal->getThreadLocalMode());
2733
2734 // Set meaningful attributes for indicator symbol.
2735 ODRIndicatorSym->setVisibility(NewGlobal->getVisibility());
2736 ODRIndicatorSym->setDLLStorageClass(NewGlobal->getDLLStorageClass());
2737 ODRIndicatorSym->setAlignment(Align(1));
2738 ODRIndicator = ConstantExpr::getPtrToInt(ODRIndicatorSym, IntptrTy);
2739 }
2740
2741 Constant *Initializer = ConstantStruct::get(
2742 GlobalStructTy,
2743 ConstantExpr::getPointerCast(InstrumentedGlobal, IntptrTy),
2744 ConstantInt::get(IntptrTy, SizeInBytes),
2745 ConstantInt::get(IntptrTy, SizeInBytes + RightRedzoneSize),
2746 ConstantExpr::getPointerCast(Name, IntptrTy),
2747 ConstantExpr::getPointerCast(getOrCreateModuleName(), IntptrTy),
2748 ConstantInt::get(IntptrTy, MD.IsDynInit),
2749 Constant::getNullValue(IntptrTy), ODRIndicator);
2750
2751 LLVM_DEBUG(dbgs() << "NEW GLOBAL: " << *NewGlobal << "\n");
2752
2753 Initializers[i] = Initializer;
2754 }
2755
2756 // Add instrumented globals to llvm.compiler.used list to avoid LTO from
2757 // ConstantMerge'ing them.
2758 SmallVector<GlobalValue *, 16> GlobalsToAddToUsedList;
2759 for (size_t i = 0; i < n; i++) {
2760 GlobalVariable *G = NewGlobals[i];
2761 if (G->getName().empty()) continue;
2762 GlobalsToAddToUsedList.push_back(G);
2763 }
2764 appendToCompilerUsed(M, ArrayRef<GlobalValue *>(GlobalsToAddToUsedList));
2765
2766 if (UseGlobalsGC && TargetTriple.isOSBinFormatELF()) {
2767 // Use COMDAT and register globals even if n == 0 to ensure that (a) the
2768 // linkage unit will only have one module constructor, and (b) the register
2769 // function will be called. The module destructor is not created when n ==
2770 // 0.
2771 *CtorComdat = true;
2772 instrumentGlobalsELF(IRB, NewGlobals, Initializers, getUniqueModuleId(&M));
2773 } else if (n == 0) {
2774 // When UseGlobalsGC is false, COMDAT can still be used if n == 0, because
2775 // all compile units will have identical module constructor/destructor.
2776 *CtorComdat = TargetTriple.isOSBinFormatELF();
2777 } else {
2778 *CtorComdat = false;
2779 if (UseGlobalsGC && TargetTriple.isOSBinFormatCOFF()) {
2780 InstrumentGlobalsCOFF(IRB, NewGlobals, Initializers);
2781 } else if (UseGlobalsGC && ShouldUseMachOGlobalsSection()) {
2782 InstrumentGlobalsMachO(IRB, NewGlobals, Initializers);
2783 } else {
2784 InstrumentGlobalsWithMetadataArray(IRB, NewGlobals, Initializers);
2785 }
2786 }
2787
2788 // Create calls for poisoning before initializers run and unpoisoning after.
2789 if (ClInitializers)
2790 createInitializerPoisonCalls();
2791
2792 LLVM_DEBUG(dbgs() << M);
2793}
2794
2795uint64_t
2796ModuleAddressSanitizer::getRedzoneSizeForGlobal(uint64_t SizeInBytes) const {
2797 constexpr uint64_t kMaxRZ = 1 << 18;
2798 const uint64_t MinRZ = getMinRedzoneSizeForGlobal();
2799
2800 uint64_t RZ = 0;
2801 if (SizeInBytes <= MinRZ / 2) {
2802 // Reduce redzone size for small size objects, e.g. int, char[1]. MinRZ is
2803 // at least 32 bytes, optimize when SizeInBytes is less than or equal to
2804 // half of MinRZ.
2805 RZ = MinRZ - SizeInBytes;
2806 } else {
2807 // Calculate RZ, where MinRZ <= RZ <= MaxRZ, and RZ ~ 1/4 * SizeInBytes.
2808 RZ = std::clamp((SizeInBytes / MinRZ / 4) * MinRZ, MinRZ, kMaxRZ);
2809
2810 // Round up to multiple of MinRZ.
2811 if (SizeInBytes % MinRZ)
2812 RZ += MinRZ - (SizeInBytes % MinRZ);
2813 }
2814
2815 assert((RZ + SizeInBytes) % MinRZ == 0);
2816
2817 return RZ;
2818}
2819
2820int ModuleAddressSanitizer::GetAsanVersion() const {
2821 int LongSize = M.getDataLayout().getPointerSizeInBits();
2822 bool isAndroid = M.getTargetTriple().isAndroid();
2823 int Version = 8;
2824 // 32-bit Android is one version ahead because of the switch to dynamic
2825 // shadow.
2826 Version += (LongSize == 32 && isAndroid);
2827 return Version;
2828}
2829
2830GlobalVariable *ModuleAddressSanitizer::getOrCreateModuleName() {
2831 if (!ModuleName) {
2832 // We shouldn't merge same module names, as this string serves as unique
2833 // module ID in runtime.
2834 ModuleName =
2835 createPrivateGlobalForString(M, M.getModuleIdentifier(),
2836 /*AllowMerging*/ false, genName("module"));
2837 }
2838 return ModuleName;
2839}
2840
2841bool ModuleAddressSanitizer::instrumentModule() {
2842 initializeCallbacks();
2843
2844 for (Function &F : M)
2845 removeASanIncompatibleFnAttributes(F, /*ReadsArgMem=*/false);
2846
2847 // Create a module constructor. A destructor is created lazily because not all
2848 // platforms, and not all modules need it.
2849 if (ConstructorKind == AsanCtorKind::Global) {
2850 if (CompileKernel) {
2851 // The kernel always builds with its own runtime, and therefore does not
2852 // need the init and version check calls.
2853 AsanCtorFunction = createSanitizerCtor(M, kAsanModuleCtorName);
2854 } else {
2855 std::string AsanVersion = std::to_string(GetAsanVersion());
2856 std::string VersionCheckName =
2857 InsertVersionCheck ? (kAsanVersionCheckNamePrefix + AsanVersion) : "";
2858 std::tie(AsanCtorFunction, std::ignore) =
2860 M, kAsanModuleCtorName, kAsanInitName, /*InitArgTypes=*/{},
2861 /*InitArgs=*/{}, VersionCheckName);
2862 }
2863 }
2864
2865 bool CtorComdat = true;
2866 if (ClGlobals) {
2867 assert(AsanCtorFunction || ConstructorKind == AsanCtorKind::None);
2868 if (AsanCtorFunction) {
2869 IRBuilder<> IRB(AsanCtorFunction->getEntryBlock().getTerminator());
2870 instrumentGlobals(IRB, &CtorComdat);
2871 } else {
2872 IRBuilder<> IRB(*C);
2873 instrumentGlobals(IRB, &CtorComdat);
2874 }
2875 }
2876
2877 const uint64_t Priority = GetCtorAndDtorPriority(TargetTriple);
2878
2879 // Put the constructor and destructor in comdat if both
2880 // (1) global instrumentation is not TU-specific
2881 // (2) target is ELF.
2882 if (UseCtorComdat && TargetTriple.isOSBinFormatELF() && CtorComdat) {
2883 if (AsanCtorFunction) {
2884 AsanCtorFunction->setComdat(M.getOrInsertComdat(kAsanModuleCtorName));
2885 appendToGlobalCtors(M, AsanCtorFunction, Priority, AsanCtorFunction);
2886 }
2887 if (AsanDtorFunction) {
2888 AsanDtorFunction->setComdat(M.getOrInsertComdat(kAsanModuleDtorName));
2889 appendToGlobalDtors(M, AsanDtorFunction, Priority, AsanDtorFunction);
2890 }
2891 } else {
2892 if (AsanCtorFunction)
2893 appendToGlobalCtors(M, AsanCtorFunction, Priority);
2894 if (AsanDtorFunction)
2895 appendToGlobalDtors(M, AsanDtorFunction, Priority);
2896 }
2897
2898 return true;
2899}
2900
2901void AddressSanitizer::initializeCallbacks(const TargetLibraryInfo *TLI) {
2902 IRBuilder<> IRB(*C);
2903 // Create __asan_report* callbacks.
2904 // IsWrite, TypeSize and Exp are encoded in the function name.
2905 for (int Exp = 0; Exp < 2; Exp++) {
2906 for (size_t AccessIsWrite = 0; AccessIsWrite <= 1; AccessIsWrite++) {
2907 const std::string TypeStr = AccessIsWrite ? "store" : "load";
2908 const std::string ExpStr = Exp ? "exp_" : "";
2909 const std::string EndingStr = Recover ? "_noabort" : "";
2910
2911 SmallVector<Type *, 3> Args2 = {IntptrTy, IntptrTy};
2912 SmallVector<Type *, 2> Args1{1, IntptrTy};
2913 AttributeList AL2;
2914 AttributeList AL1;
2915 if (Exp) {
2916 Type *ExpType = Type::getInt32Ty(*C);
2917 Args2.push_back(ExpType);
2918 Args1.push_back(ExpType);
2919 if (auto AK = TLI->getExtAttrForI32Param(false)) {
2920 AL2 = AL2.addParamAttribute(*C, 2, AK);
2921 AL1 = AL1.addParamAttribute(*C, 1, AK);
2922 }
2923 }
2924 AsanErrorCallbackSized[AccessIsWrite][Exp] = Inserter.insertFunction(
2925 kAsanReportErrorTemplate + ExpStr + TypeStr + "_n" + EndingStr,
2926 FunctionType::get(IRB.getVoidTy(), Args2, false), AL2);
2927
2928 AsanMemoryAccessCallbackSized[AccessIsWrite][Exp] =
2929 Inserter.insertFunction(
2930 ClMemoryAccessCallbackPrefix + ExpStr + TypeStr + "N" + EndingStr,
2931 FunctionType::get(IRB.getVoidTy(), Args2, false), AL2);
2932
2933 for (size_t AccessSizeIndex = 0; AccessSizeIndex < kNumberOfAccessSizes;
2934 AccessSizeIndex++) {
2935 const std::string Suffix = TypeStr + itostr(1ULL << AccessSizeIndex);
2936 AsanErrorCallback[AccessIsWrite][Exp][AccessSizeIndex] =
2937 Inserter.insertFunction(
2938 kAsanReportErrorTemplate + ExpStr + Suffix + EndingStr,
2939 FunctionType::get(IRB.getVoidTy(), Args1, false), AL1);
2940
2941 AsanMemoryAccessCallback[AccessIsWrite][Exp][AccessSizeIndex] =
2942 Inserter.insertFunction(
2943 ClMemoryAccessCallbackPrefix + ExpStr + Suffix + EndingStr,
2944 FunctionType::get(IRB.getVoidTy(), Args1, false), AL1);
2945 }
2946 }
2947 }
2948
2949 const std::string MemIntrinCallbackPrefix =
2950 (CompileKernel && !ClKasanMemIntrinCallbackPrefix)
2951 ? std::string("")
2953 AsanMemmove = Inserter.insertFunction(MemIntrinCallbackPrefix + "memmove",
2954 PtrTy, PtrTy, PtrTy, IntptrTy);
2955 AsanMemcpy = Inserter.insertFunction(MemIntrinCallbackPrefix + "memcpy",
2956 PtrTy, PtrTy, PtrTy, IntptrTy);
2957 AsanMemset =
2958 Inserter.insertFunction(MemIntrinCallbackPrefix + "memset",
2959 TLI->getAttrList(C, {1},
2960 /*Signed=*/false),
2961 PtrTy, PtrTy, IRB.getInt32Ty(), IntptrTy);
2962
2963 AsanHandleNoReturnFunc =
2964 Inserter.insertFunction(kAsanHandleNoReturnName, IRB.getVoidTy());
2965
2966 AsanPtrCmpFunction =
2967 Inserter.insertFunction(kAsanPtrCmp, IRB.getVoidTy(), IntptrTy, IntptrTy);
2968 AsanPtrSubFunction =
2969 Inserter.insertFunction(kAsanPtrSub, IRB.getVoidTy(), IntptrTy, IntptrTy);
2970 if (Mapping.InGlobal)
2971 AsanShadowGlobal = M.getOrInsertGlobal("__asan_shadow",
2972 ArrayType::get(IRB.getInt8Ty(), 0));
2973
2974 AMDGPUAddressShared =
2975 Inserter.insertFunction(kAMDGPUAddressSharedName, IRB.getInt1Ty(), PtrTy);
2976 AMDGPUAddressPrivate = Inserter.insertFunction(kAMDGPUAddressPrivateName,
2977 IRB.getInt1Ty(), PtrTy);
2978}
2979
2980bool AddressSanitizer::maybeInsertAsanInitAtFunctionEntry(Function &F) {
2981 // For each NSObject descendant having a +load method, this method is invoked
2982 // by the ObjC runtime before any of the static constructors is called.
2983 // Therefore we need to instrument such methods with a call to __asan_init
2984 // at the beginning in order to initialize our runtime before any access to
2985 // the shadow memory.
2986 // We cannot just ignore these methods, because they may call other
2987 // instrumented functions.
2988 if (F.getName().contains(" load]")) {
2989 FunctionCallee AsanInitFunction =
2990 declareSanitizerInitFunction(*F.getParent(), kAsanInitName, {});
2991 IRBuilder<> IRB(&F.front(), F.front().begin());
2992 IRB.CreateCall(AsanInitFunction, {});
2993 return true;
2994 }
2995 return false;
2996}
2997
2998bool AddressSanitizer::maybeInsertDynamicShadowAtFunctionEntry(Function &F) {
2999 // Generate code only when dynamic addressing is needed.
3000 if (Mapping.Offset != kDynamicShadowSentinel)
3001 return false;
3002
3003 IRBuilder<> IRB(&F.front().front());
3004 if (Mapping.InGlobal) {
3006 // An empty inline asm with input reg == output reg.
3007 // An opaque pointer-to-int cast, basically.
3009 FunctionType::get(IntptrTy, {AsanShadowGlobal->getType()}, false),
3010 StringRef(""), StringRef("=r,0"),
3011 /*hasSideEffects=*/false);
3012 LocalDynamicShadow =
3013 IRB.CreateCall(Asm, {AsanShadowGlobal}, ".asan.shadow");
3014 } else {
3015 LocalDynamicShadow =
3016 IRB.CreatePointerCast(AsanShadowGlobal, IntptrTy, ".asan.shadow");
3017 }
3018 } else {
3019 Value *GlobalDynamicAddress = F.getParent()->getOrInsertGlobal(
3021 LocalDynamicShadow = IRB.CreateLoad(IntptrTy, GlobalDynamicAddress);
3022 }
3023 return true;
3024}
3025
3026void AddressSanitizer::markEscapedLocalAllocas(Function &F) {
3027 // Find the one possible call to llvm.localescape and pre-mark allocas passed
3028 // to it as uninteresting. This assumes we haven't started processing allocas
3029 // yet. This check is done up front because iterating the use list in
3030 // isInterestingAlloca would be algorithmically slower.
3031 assert(ProcessedAllocas.empty() && "must process localescape before allocas");
3032
3033 // Try to get the declaration of llvm.localescape. If it's not in the module,
3034 // we can exit early.
3035 if (!F.getParent()->getFunction("llvm.localescape")) return;
3036
3037 // Look for a call to llvm.localescape call in the entry block. It can't be in
3038 // any other block.
3039 for (Instruction &I : F.getEntryBlock()) {
3041 if (II && II->getIntrinsicID() == Intrinsic::localescape) {
3042 // We found a call. Mark all the allocas passed in as uninteresting.
3043 for (Value *Arg : II->args()) {
3044 AllocaInst *AI = dyn_cast<AllocaInst>(Arg->stripPointerCasts());
3045 assert(AI && AI->isStaticAlloca() &&
3046 "non-static alloca arg to localescape");
3047 ProcessedAllocas[AI] = false;
3048 }
3049 break;
3050 }
3051 }
3052}
3053// Mitigation for https://github.com/google/sanitizers/issues/749
3054// We don't instrument Windows catch-block parameters to avoid
3055// interfering with exception handling assumptions.
3056void AddressSanitizer::markCatchParametersAsUninteresting(Function &F) {
3057 for (BasicBlock &BB : F) {
3058 for (Instruction &I : BB) {
3059 if (auto *CatchPad = dyn_cast<CatchPadInst>(&I)) {
3060 // Mark the parameters to a catch-block as uninteresting to avoid
3061 // instrumenting them.
3062 for (Value *Operand : CatchPad->arg_operands())
3063 if (auto *AI = dyn_cast<AllocaInst>(Operand))
3064 ProcessedAllocas[AI] = false;
3065 }
3066 }
3067 }
3068}
3069
3070bool AddressSanitizer::suppressInstrumentationSiteForDebug(int &Instrumented) {
3071 bool ShouldInstrument =
3072 ClDebugMin < 0 || ClDebugMax < 0 ||
3073 (Instrumented >= ClDebugMin && Instrumented <= ClDebugMax);
3074 Instrumented++;
3075 return !ShouldInstrument;
3076}
3077
3078bool AddressSanitizer::instrumentFunction(Function &F,
3079 const TargetLibraryInfo *TLI,
3080 const TargetTransformInfo *TTI) {
3081 bool FunctionModified = false;
3082
3083 // Do not apply any instrumentation for naked functions.
3084 if (F.hasFnAttribute(Attribute::Naked))
3085 return FunctionModified;
3086
3087 // If needed, insert __asan_init before checking for SanitizeAddress attr.
3088 // This function needs to be called even if the function body is not
3089 // instrumented.
3090 if (maybeInsertAsanInitAtFunctionEntry(F))
3091 FunctionModified = true;
3092
3093 // Leave if the function doesn't need instrumentation.
3094 if (!F.hasFnAttribute(Attribute::SanitizeAddress)) return FunctionModified;
3095
3096 if (F.hasFnAttribute(Attribute::DisableSanitizerInstrumentation))
3097 return FunctionModified;
3098
3099 LLVM_DEBUG(dbgs() << "ASAN instrumenting:\n" << F << "\n");
3100
3101 initializeCallbacks(TLI);
3102
3103 FunctionStateRAII CleanupObj(this);
3104
3105 RuntimeCallInserter RTCI(F);
3106
3107 FunctionModified |= maybeInsertDynamicShadowAtFunctionEntry(F);
3108
3109 // We can't instrument allocas used with llvm.localescape. Only static allocas
3110 // can be passed to that intrinsic.
3111 markEscapedLocalAllocas(F);
3112
3113 if (TargetTriple.isOSWindows())
3114 markCatchParametersAsUninteresting(F);
3115
3116 // We want to instrument every address only once per basic block (unless there
3117 // are calls between uses).
3118 SmallPtrSet<Value *, 16> TempsToInstrument;
3119 SmallVector<InterestingMemoryOperand, 16> OperandsToInstrument;
3120 SmallVector<MemIntrinsic *, 16> IntrinToInstrument;
3121 SmallVector<Instruction *, 8> NoReturnCalls;
3123 SmallVector<Instruction *, 16> PointerComparisonsOrSubtracts;
3124
3125 // Fill the set of memory operations to instrument.
3126 for (auto &BB : F) {
3127 AllBlocks.push_back(&BB);
3128 TempsToInstrument.clear();
3129 int NumInsnsPerBB = 0;
3130 for (auto &Inst : BB) {
3131 if (LooksLikeCodeInBug11395(&Inst)) return false;
3132 // Skip instructions inserted by another instrumentation.
3133 if (Inst.hasMetadata(LLVMContext::MD_nosanitize))
3134 continue;
3135 SmallVector<InterestingMemoryOperand, 1> InterestingOperands;
3136 getInterestingMemoryOperands(&Inst, InterestingOperands, TTI);
3137
3138 if (!InterestingOperands.empty()) {
3139 for (auto &Operand : InterestingOperands) {
3140 if (ClOpt && ClOptSameTemp) {
3141 Value *Ptr = Operand.getPtr();
3142 // If we have a mask, skip instrumentation if we've already
3143 // instrumented the full object. But don't add to TempsToInstrument
3144 // because we might get another load/store with a different mask.
3145 if (Operand.MaybeMask) {
3146 if (TempsToInstrument.count(Ptr))
3147 continue; // We've seen this (whole) temp in the current BB.
3148 } else {
3149 if (!TempsToInstrument.insert(Ptr).second)
3150 continue; // We've seen this temp in the current BB.
3151 }
3152 }
3153 OperandsToInstrument.push_back(Operand);
3154 NumInsnsPerBB++;
3155 }
3156 } else if (((ClInvalidPointerPairs || ClInvalidPointerCmp) &&
3160 PointerComparisonsOrSubtracts.push_back(&Inst);
3161 } else if (MemIntrinsic *MI = dyn_cast<MemIntrinsic>(&Inst)) {
3162 // ok, take it.
3163 IntrinToInstrument.push_back(MI);
3164 NumInsnsPerBB++;
3165 } else {
3166 if (auto *CB = dyn_cast<CallBase>(&Inst)) {
3167 // A call inside BB.
3168 TempsToInstrument.clear();
3169 if (CB->doesNotReturn())
3170 NoReturnCalls.push_back(CB);
3171 }
3172 if (CallInst *CI = dyn_cast<CallInst>(&Inst))
3174 }
3175 if (NumInsnsPerBB >= ClMaxInsnsToInstrumentPerBB) break;
3176 }
3177 }
3178
3179 bool UseCalls = (InstrumentationWithCallsThreshold >= 0 &&
3180 OperandsToInstrument.size() + IntrinToInstrument.size() >
3181 (unsigned)InstrumentationWithCallsThreshold);
3182 const DataLayout &DL = F.getDataLayout();
3183 ObjectSizeOffsetVisitor ObjSizeVis(DL, TLI, F.getContext());
3184
3185 // Instrument.
3186 int NumInstrumented = 0;
3187 for (auto &Operand : OperandsToInstrument) {
3188 if (!suppressInstrumentationSiteForDebug(NumInstrumented))
3189 instrumentMop(ObjSizeVis, Operand, UseCalls,
3190 F.getDataLayout(), RTCI);
3191 FunctionModified = true;
3192 }
3193 for (auto *Inst : IntrinToInstrument) {
3194 if (!suppressInstrumentationSiteForDebug(NumInstrumented))
3195 instrumentMemIntrinsic(Inst, RTCI);
3196 FunctionModified = true;
3197 }
3198
3199 FunctionStackPoisoner FSP(F, *this, RTCI);
3200 bool ChangedStack = FSP.runOnFunction();
3201
3202 // We must unpoison the stack before NoReturn calls (throw, _exit, etc).
3203 // See e.g. https://github.com/google/sanitizers/issues/37
3204 for (auto *CI : NoReturnCalls) {
3205 IRBuilder<> IRB(CI);
3206 RTCI.createRuntimeCall(IRB, AsanHandleNoReturnFunc, {});
3207 }
3208
3209 for (auto *Inst : PointerComparisonsOrSubtracts) {
3210 instrumentPointerComparisonOrSubtraction(Inst, RTCI);
3211 FunctionModified = true;
3212 }
3213
3214 if (ChangedStack || !NoReturnCalls.empty())
3215 FunctionModified = true;
3216
3217 LLVM_DEBUG(dbgs() << "ASAN done instrumenting: " << FunctionModified << " "
3218 << F << "\n");
3219
3220 return FunctionModified;
3221}
3222
3223// Workaround for bug 11395: we don't want to instrument stack in functions
3224// with large assembly blobs (32-bit only), otherwise reg alloc may crash.
3225// FIXME: remove once the bug 11395 is fixed.
3226bool AddressSanitizer::LooksLikeCodeInBug11395(Instruction *I) {
3227 if (LongSize != 32) return false;
3229 if (!CI || !CI->isInlineAsm()) return false;
3230 if (CI->arg_size() <= 5)
3231 return false;
3232 // We have inline assembly with quite a few arguments.
3233 return true;
3234}
3235
3236void FunctionStackPoisoner::initializeCallbacks(Module &) {
3237 IRBuilder<> IRB(*C);
3238 if (ASan.UseAfterReturn == AsanDetectStackUseAfterReturnMode::Always ||
3239 ASan.UseAfterReturn == AsanDetectStackUseAfterReturnMode::Runtime) {
3240 const char *MallocNameTemplate =
3241 ASan.UseAfterReturn == AsanDetectStackUseAfterReturnMode::Always
3244 for (int Index = 0; Index <= kMaxAsanStackMallocSizeClass; Index++) {
3245 std::string Suffix = itostr(Index);
3246 AsanStackMallocFunc[Index] = ASan.Inserter.insertFunction(
3247 MallocNameTemplate + Suffix, IntptrTy, IntptrTy);
3248 AsanStackFreeFunc[Index] =
3249 ASan.Inserter.insertFunction(kAsanStackFreeNameTemplate + Suffix,
3250 IRB.getVoidTy(), IntptrTy, IntptrTy);
3251 }
3252 }
3253 if (ASan.UseAfterScope) {
3254 AsanPoisonStackMemoryFunc = ASan.Inserter.insertFunction(
3255 kAsanPoisonStackMemoryName, IRB.getVoidTy(), IntptrTy, IntptrTy);
3256 AsanUnpoisonStackMemoryFunc = ASan.Inserter.insertFunction(
3257 kAsanUnpoisonStackMemoryName, IRB.getVoidTy(), IntptrTy, IntptrTy);
3258 }
3259
3260 for (size_t Val : {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0xf1, 0xf2,
3261 0xf3, 0xf5, 0xf8}) {
3262 std::ostringstream Name;
3264 Name << std::setw(2) << std::setfill('0') << std::hex << Val;
3265 AsanSetShadowFunc[Val] = ASan.Inserter.insertFunction(
3266 Name.str(), IRB.getVoidTy(), IntptrTy, IntptrTy);
3267 }
3268
3269 AsanAllocaPoisonFunc = ASan.Inserter.insertFunction(
3270 kAsanAllocaPoison, IRB.getVoidTy(), IntptrTy, IntptrTy);
3271 AsanAllocasUnpoisonFunc = ASan.Inserter.insertFunction(
3272 kAsanAllocasUnpoison, IRB.getVoidTy(), IntptrTy, IntptrTy);
3273}
3274
3275void FunctionStackPoisoner::copyToShadowInline(ArrayRef<uint8_t> ShadowMask,
3276 ArrayRef<uint8_t> ShadowBytes,
3277 size_t Begin, size_t End,
3278 IRBuilder<> &IRB,
3279 Value *ShadowBase) {
3280 if (Begin >= End)
3281 return;
3282
3283 const size_t LargestStoreSizeInBytes =
3284 std::min<size_t>(sizeof(uint64_t), ASan.LongSize / 8);
3285
3286 const bool IsLittleEndian = F.getDataLayout().isLittleEndian();
3287
3288 // Poison given range in shadow using larges store size with out leading and
3289 // trailing zeros in ShadowMask. Zeros never change, so they need neither
3290 // poisoning nor up-poisoning. Still we don't mind if some of them get into a
3291 // middle of a store.
3292 for (size_t i = Begin; i < End;) {
3293 if (!ShadowMask[i]) {
3294 assert(!ShadowBytes[i]);
3295 ++i;
3296 continue;
3297 }
3298
3299 size_t StoreSizeInBytes = LargestStoreSizeInBytes;
3300 // Fit store size into the range.
3301 while (StoreSizeInBytes > End - i)
3302 StoreSizeInBytes /= 2;
3303
3304 // Minimize store size by trimming trailing zeros.
3305 for (size_t j = StoreSizeInBytes - 1; j && !ShadowMask[i + j]; --j) {
3306 while (j <= StoreSizeInBytes / 2)
3307 StoreSizeInBytes /= 2;
3308 }
3309
3310 uint64_t Val = 0;
3311 for (size_t j = 0; j < StoreSizeInBytes; j++) {
3312 if (IsLittleEndian)
3313 Val |= (uint64_t)ShadowBytes[i + j] << (8 * j);
3314 else
3315 Val = (Val << 8) | ShadowBytes[i + j];
3316 }
3317
3318 Value *Ptr = IRB.CreateAdd(ShadowBase, ConstantInt::get(IntptrTy, i));
3319 Value *Poison = IRB.getIntN(StoreSizeInBytes * 8, Val);
3321 Poison, IRB.CreateIntToPtr(Ptr, PointerType::getUnqual(Poison->getContext())),
3322 Align(1));
3323
3324 i += StoreSizeInBytes;
3325 }
3326}
3327
3328void FunctionStackPoisoner::copyToShadow(ArrayRef<uint8_t> ShadowMask,
3329 ArrayRef<uint8_t> ShadowBytes,
3330 IRBuilder<> &IRB, Value *ShadowBase) {
3331 copyToShadow(ShadowMask, ShadowBytes, 0, ShadowMask.size(), IRB, ShadowBase);
3332}
3333
3334void FunctionStackPoisoner::copyToShadow(ArrayRef<uint8_t> ShadowMask,
3335 ArrayRef<uint8_t> ShadowBytes,
3336 size_t Begin, size_t End,
3337 IRBuilder<> &IRB, Value *ShadowBase) {
3338 assert(ShadowMask.size() == ShadowBytes.size());
3339 size_t Done = Begin;
3340 for (size_t i = Begin, j = Begin + 1; i < End; i = j++) {
3341 if (!ShadowMask[i]) {
3342 assert(!ShadowBytes[i]);
3343 continue;
3344 }
3345 uint8_t Val = ShadowBytes[i];
3346 if (!AsanSetShadowFunc[Val])
3347 continue;
3348
3349 // Skip same values.
3350 for (; j < End && ShadowMask[j] && Val == ShadowBytes[j]; ++j) {
3351 }
3352
3353 if (j - i >= ASan.MaxInlinePoisoningSize) {
3354 copyToShadowInline(ShadowMask, ShadowBytes, Done, i, IRB, ShadowBase);
3355 RTCI.createRuntimeCall(
3356 IRB, AsanSetShadowFunc[Val],
3357 {IRB.CreateAdd(ShadowBase, ConstantInt::get(IntptrTy, i)),
3358 ConstantInt::get(IntptrTy, j - i)});
3359 Done = j;
3360 }
3361 }
3362
3363 copyToShadowInline(ShadowMask, ShadowBytes, Done, End, IRB, ShadowBase);
3364}
3365
3366// Fake stack allocator (asan_fake_stack.h) has 11 size classes
3367// for every power of 2 from kMinStackMallocSize to kMaxAsanStackMallocSizeClass
3368static int StackMallocSizeClass(uint64_t LocalStackSize) {
3369 assert(LocalStackSize <= kMaxStackMallocSize);
3370 uint64_t MaxSize = kMinStackMallocSize;
3371 for (int i = 0;; i++, MaxSize *= 2)
3372 if (LocalStackSize <= MaxSize) return i;
3373 llvm_unreachable("impossible LocalStackSize");
3374}
3375
3376void FunctionStackPoisoner::copyArgsPassedByValToAllocas() {
3377 Instruction *CopyInsertPoint = &F.front().front();
3378 if (CopyInsertPoint == ASan.LocalDynamicShadow) {
3379 // Insert after the dynamic shadow location is determined
3380 CopyInsertPoint = CopyInsertPoint->getNextNode();
3381 assert(CopyInsertPoint);
3382 }
3383 IRBuilder<> IRB(CopyInsertPoint);
3384 const DataLayout &DL = F.getDataLayout();
3385 for (Argument &Arg : F.args()) {
3386 if (Arg.hasByValAttr()) {
3387 Type *Ty = Arg.getParamByValType();
3388 const Align Alignment =
3389 DL.getValueOrABITypeAlignment(Arg.getParamAlign(), Ty);
3390
3391 AllocaInst *AI = IRB.CreateAlloca(
3392 Ty, nullptr,
3393 (Arg.hasName() ? Arg.getName() : "Arg" + Twine(Arg.getArgNo())) +
3394 ".byval");
3395 AI->setAlignment(Alignment);
3396 Arg.replaceAllUsesWith(AI);
3397
3398 uint64_t AllocSize = DL.getTypeAllocSize(Ty);
3399 IRB.CreateMemCpy(AI, Alignment, &Arg, Alignment, AllocSize);
3400 }
3401 }
3402}
3403
3404PHINode *FunctionStackPoisoner::createPHI(IRBuilder<> &IRB, Value *Cond,
3405 Value *ValueIfTrue,
3406 Instruction *ThenTerm,
3407 Value *ValueIfFalse) {
3408 PHINode *PHI = IRB.CreatePHI(ValueIfTrue->getType(), 2);
3409 BasicBlock *CondBlock = cast<Instruction>(Cond)->getParent();
3410 PHI->addIncoming(ValueIfFalse, CondBlock);
3411 BasicBlock *ThenBlock = ThenTerm->getParent();
3412 PHI->addIncoming(ValueIfTrue, ThenBlock);
3413 return PHI;
3414}
3415
3416Value *FunctionStackPoisoner::createAllocaForLayout(
3417 IRBuilder<> &IRB, const ASanStackFrameLayout &L, bool Dynamic) {
3418 AllocaInst *Alloca;
3419 if (Dynamic) {
3420 Alloca = IRB.CreateAlloca(IRB.getInt8Ty(),
3421 ConstantInt::get(IRB.getInt64Ty(), L.FrameSize),
3422 "MyAlloca");
3423 } else {
3424 Alloca = IRB.CreateAlloca(ArrayType::get(IRB.getInt8Ty(), L.FrameSize),
3425 nullptr, "MyAlloca");
3426 assert(Alloca->isStaticAlloca());
3427 }
3428 assert((ClRealignStack & (ClRealignStack - 1)) == 0);
3429 uint64_t FrameAlignment = std::max(L.FrameAlignment, uint64_t(ClRealignStack));
3430 Alloca->setAlignment(Align(FrameAlignment));
3431 return Alloca;
3432}
3433
3434void FunctionStackPoisoner::createDynamicAllocasInitStorage() {
3435 BasicBlock &FirstBB = *F.begin();
3436 IRBuilder<> IRB(dyn_cast<Instruction>(FirstBB.begin()));
3437 DynamicAllocaLayout = IRB.CreateAlloca(IntptrTy, nullptr);
3438 IRB.CreateStore(Constant::getNullValue(IntptrTy), DynamicAllocaLayout);
3439 DynamicAllocaLayout->setAlignment(Align(32));
3440}
3441
3442void FunctionStackPoisoner::processDynamicAllocas() {
3443 if (!ClInstrumentDynamicAllocas || DynamicAllocaVec.empty()) {
3444 assert(DynamicAllocaPoisonCallVec.empty());
3445 return;
3446 }
3447
3448 // Insert poison calls for lifetime intrinsics for dynamic allocas.
3449 for (const auto &APC : DynamicAllocaPoisonCallVec) {
3450 assert(APC.InsBefore);
3451 assert(APC.AI);
3452 assert(ASan.isInterestingAlloca(*APC.AI));
3453 assert(!APC.AI->isStaticAlloca());
3454
3455 IRBuilder<> IRB(APC.InsBefore);
3456 poisonAlloca(APC.AI, APC.Size, IRB, APC.DoPoison);
3457 // Dynamic allocas will be unpoisoned unconditionally below in
3458 // unpoisonDynamicAllocas.
3459 // Flag that we need unpoison static allocas.
3460 }
3461
3462 // Handle dynamic allocas.
3463 createDynamicAllocasInitStorage();
3464 for (auto &AI : DynamicAllocaVec)
3465 handleDynamicAllocaCall(AI);
3466 unpoisonDynamicAllocas();
3467}
3468
3469/// Collect instructions in the entry block after \p InsBefore which initialize
3470/// permanent storage for a function argument. These instructions must remain in
3471/// the entry block so that uninitialized values do not appear in backtraces. An
3472/// added benefit is that this conserves spill slots. This does not move stores
3473/// before instrumented / "interesting" allocas.
3475 AddressSanitizer &ASan, Instruction &InsBefore,
3476 SmallVectorImpl<Instruction *> &InitInsts) {
3477 Instruction *Start = InsBefore.getNextNode();
3478 for (Instruction *It = Start; It; It = It->getNextNode()) {
3479 // Argument initialization looks like:
3480 // 1) store <Argument>, <Alloca> OR
3481 // 2) <CastArgument> = cast <Argument> to ...
3482 // store <CastArgument> to <Alloca>
3483 // Do not consider any other kind of instruction.
3484 //
3485 // Note: This covers all known cases, but may not be exhaustive. An
3486 // alternative to pattern-matching stores is to DFS over all Argument uses:
3487 // this might be more general, but is probably much more complicated.
3488 if (isa<AllocaInst>(It) || isa<CastInst>(It))
3489 continue;
3490 if (auto *Store = dyn_cast<StoreInst>(It)) {
3491 // The store destination must be an alloca that isn't interesting for
3492 // ASan to instrument. These are moved up before InsBefore, and they're
3493 // not interesting because allocas for arguments can be mem2reg'd.
3494 auto *Alloca = dyn_cast<AllocaInst>(Store->getPointerOperand());
3495 if (!Alloca || ASan.isInterestingAlloca(*Alloca))
3496 continue;
3497
3498 Value *Val = Store->getValueOperand();
3499 bool IsDirectArgInit = isa<Argument>(Val);
3500 bool IsArgInitViaCast =
3501 isa<CastInst>(Val) &&
3502 isa<Argument>(cast<CastInst>(Val)->getOperand(0)) &&
3503 // Check that the cast appears directly before the store. Otherwise
3504 // moving the cast before InsBefore may break the IR.
3505 Val == It->getPrevNode();
3506 bool IsArgInit = IsDirectArgInit || IsArgInitViaCast;
3507 if (!IsArgInit)
3508 continue;
3509
3510 if (IsArgInitViaCast)
3511 InitInsts.push_back(cast<Instruction>(Val));
3512 InitInsts.push_back(Store);
3513 continue;
3514 }
3515
3516 // Do not reorder past unknown instructions: argument initialization should
3517 // only involve casts and stores.
3518 return;
3519 }
3520}
3521
3523 // Alloca could have been renamed for uniqueness. Its true name will have been
3524 // recorded as an annotation.
3525 if (AI->hasMetadata(LLVMContext::MD_annotation)) {
3526 MDTuple *AllocaAnnotations =
3527 cast<MDTuple>(AI->getMetadata(LLVMContext::MD_annotation));
3528 for (auto &Annotation : AllocaAnnotations->operands()) {
3529 if (!isa<MDTuple>(Annotation))
3530 continue;
3531 auto AnnotationTuple = cast<MDTuple>(Annotation);
3532 for (unsigned Index = 0; Index < AnnotationTuple->getNumOperands();
3533 Index++) {
3534 // All annotations are strings
3535 auto MetadataString =
3536 cast<MDString>(AnnotationTuple->getOperand(Index));
3537 if (MetadataString->getString() == "alloca_name_altered")
3538 return cast<MDString>(AnnotationTuple->getOperand(Index + 1))
3539 ->getString();
3540 }
3541 }
3542 }
3543 return AI->getName();
3544}
3545
3546void FunctionStackPoisoner::processStaticAllocas() {
3547 if (AllocaVec.empty()) {
3548 assert(StaticAllocaPoisonCallVec.empty());
3549 return;
3550 }
3551
3552 int StackMallocIdx = -1;
3553 DebugLoc EntryDebugLocation;
3554 if (auto SP = F.getSubprogram())
3555 EntryDebugLocation =
3556 DILocation::get(SP->getContext(), SP->getScopeLine(), 0, SP);
3557
3558 Instruction *InsBefore = AllocaVec[0];
3559 IRBuilder<> IRB(InsBefore);
3560
3561 // Make sure non-instrumented allocas stay in the entry block. Otherwise,
3562 // debug info is broken, because only entry-block allocas are treated as
3563 // regular stack slots.
3564 auto InsBeforeB = InsBefore->getParent();
3565 assert(InsBeforeB == &F.getEntryBlock());
3566 for (auto *AI : StaticAllocasToMoveUp)
3567 if (AI->getParent() == InsBeforeB)
3568 AI->moveBefore(InsBefore->getIterator());
3569
3570 // Move stores of arguments into entry-block allocas as well. This prevents
3571 // extra stack slots from being generated (to house the argument values until
3572 // they can be stored into the allocas). This also prevents uninitialized
3573 // values from being shown in backtraces.
3574 SmallVector<Instruction *, 8> ArgInitInsts;
3575 findStoresToUninstrumentedArgAllocas(ASan, *InsBefore, ArgInitInsts);
3576 for (Instruction *ArgInitInst : ArgInitInsts)
3577 ArgInitInst->moveBefore(InsBefore->getIterator());
3578
3579 // If we have a call to llvm.localescape, keep it in the entry block.
3580 if (LocalEscapeCall)
3581 LocalEscapeCall->moveBefore(InsBefore->getIterator());
3582
3584 SVD.reserve(AllocaVec.size());
3585 for (AllocaInst *AI : AllocaVec) {
3588 ASan.getAllocaSizeInBytes(*AI),
3589 0,
3590 AI->getAlign().value(),
3591 AI,
3592 0,
3593 0};
3594 SVD.push_back(D);
3595 }
3596
3597 // Minimal header size (left redzone) is 4 pointers,
3598 // i.e. 32 bytes on 64-bit platforms and 16 bytes in 32-bit platforms.
3599 uint64_t Granularity = 1ULL << Mapping.Scale;
3600 uint64_t MinHeaderSize = std::max((uint64_t)ASan.LongSize / 2, Granularity);
3601 const ASanStackFrameLayout &L =
3602 ComputeASanStackFrameLayout(SVD, Granularity, MinHeaderSize);
3603
3604 // Build AllocaToSVDMap for ASanStackVariableDescription lookup.
3606 for (auto &Desc : SVD)
3607 AllocaToSVDMap[Desc.AI] = &Desc;
3608
3609 // Update SVD with information from lifetime intrinsics.
3610 for (const auto &APC : StaticAllocaPoisonCallVec) {
3611 assert(APC.InsBefore);
3612 assert(APC.AI);
3613 assert(ASan.isInterestingAlloca(*APC.AI));
3614 assert(APC.AI->isStaticAlloca());
3615
3616 ASanStackVariableDescription &Desc = *AllocaToSVDMap[APC.AI];
3617 Desc.LifetimeSize = Desc.Size;
3618 if (const DILocation *FnLoc = EntryDebugLocation.get()) {
3619 if (const DILocation *LifetimeLoc = APC.InsBefore->getDebugLoc().get()) {
3620 if (LifetimeLoc->getFile() == FnLoc->getFile())
3621 if (unsigned Line = LifetimeLoc->getLine())
3622 Desc.Line = std::min(Desc.Line ? Desc.Line : Line, Line);
3623 }
3624 }
3625 }
3626
3627 auto DescriptionString = ComputeASanStackFrameDescription(SVD);
3628 LLVM_DEBUG(dbgs() << DescriptionString << " --- " << L.FrameSize << "\n");
3629 uint64_t LocalStackSize = L.FrameSize;
3630 bool DoStackMalloc =
3631 ASan.UseAfterReturn != AsanDetectStackUseAfterReturnMode::Never &&
3632 !ASan.CompileKernel && LocalStackSize <= kMaxStackMallocSize;
3633 bool DoDynamicAlloca = ClDynamicAllocaStack;
3634 // Don't do dynamic alloca or stack malloc if:
3635 // 1) There is inline asm: too often it makes assumptions on which registers
3636 // are available.
3637 // 2) There is a returns_twice call (typically setjmp), which is
3638 // optimization-hostile, and doesn't play well with introduced indirect
3639 // register-relative calculation of local variable addresses.
3640 DoDynamicAlloca &= !HasInlineAsm && !HasReturnsTwiceCall;
3641 DoStackMalloc &= !HasInlineAsm && !HasReturnsTwiceCall;
3642
3643 Type *PtrTy = F.getDataLayout().getAllocaPtrType(F.getContext());
3644 Value *StaticAlloca =
3645 DoDynamicAlloca ? nullptr : createAllocaForLayout(IRB, L, false);
3646
3647 Value *FakeStackPtr;
3648 Value *FakeStackInt;
3649 Value *LocalStackBase;
3650 Value *LocalStackBaseAlloca;
3651 uint8_t DIExprFlags = DIExpression::ApplyOffset;
3652
3653 if (DoStackMalloc) {
3654 LocalStackBaseAlloca =
3655 IRB.CreateAlloca(IntptrTy, nullptr, "asan_local_stack_base");
3656 if (ASan.UseAfterReturn == AsanDetectStackUseAfterReturnMode::Runtime) {
3657 // void *FakeStack = __asan_option_detect_stack_use_after_return
3658 // ? __asan_stack_malloc_N(LocalStackSize)
3659 // : nullptr;
3660 // void *LocalStackBase = (FakeStack) ? FakeStack :
3661 // alloca(LocalStackSize);
3662 Constant *OptionDetectUseAfterReturn = F.getParent()->getOrInsertGlobal(
3664 Value *UseAfterReturnIsEnabled = IRB.CreateICmpNE(
3665 IRB.CreateLoad(IRB.getInt32Ty(), OptionDetectUseAfterReturn),
3667 Instruction *Term =
3668 SplitBlockAndInsertIfThen(UseAfterReturnIsEnabled, InsBefore, false);
3669 IRBuilder<> IRBIf(Term);
3670 StackMallocIdx = StackMallocSizeClass(LocalStackSize);
3671 assert(StackMallocIdx <= kMaxAsanStackMallocSizeClass);
3672 Value *FakeStackValue =
3673 RTCI.createRuntimeCall(IRBIf, AsanStackMallocFunc[StackMallocIdx],
3674 ConstantInt::get(IntptrTy, LocalStackSize));
3675 IRB.SetInsertPoint(InsBefore);
3676 FakeStackInt = createPHI(IRB, UseAfterReturnIsEnabled, FakeStackValue,
3677 Term, ConstantInt::get(IntptrTy, 0));
3678 } else {
3679 // assert(ASan.UseAfterReturn == AsanDetectStackUseAfterReturnMode:Always)
3680 // void *FakeStack = __asan_stack_malloc_N(LocalStackSize);
3681 // void *LocalStackBase = (FakeStack) ? FakeStack :
3682 // alloca(LocalStackSize);
3683 StackMallocIdx = StackMallocSizeClass(LocalStackSize);
3684 FakeStackInt =
3685 RTCI.createRuntimeCall(IRB, AsanStackMallocFunc[StackMallocIdx],
3686 ConstantInt::get(IntptrTy, LocalStackSize));
3687 }
3688 FakeStackPtr = IRB.CreateIntToPtr(FakeStackInt, PtrTy);
3689 Value *NoFakeStack =
3690 IRB.CreateICmpEQ(FakeStackInt, Constant::getNullValue(IntptrTy));
3691 Instruction *Term =
3692 SplitBlockAndInsertIfThen(NoFakeStack, InsBefore, false);
3693 IRBuilder<> IRBIf(Term);
3694 Value *AllocaValue =
3695 DoDynamicAlloca ? createAllocaForLayout(IRBIf, L, true) : StaticAlloca;
3696
3697 IRB.SetInsertPoint(InsBefore);
3698 LocalStackBase =
3699 createPHI(IRB, NoFakeStack, AllocaValue, Term, FakeStackPtr);
3700 IRB.CreateStore(LocalStackBase, LocalStackBaseAlloca);
3701 DIExprFlags |= DIExpression::DerefBefore;
3702 } else {
3703 // void *FakeStack = nullptr;
3704 // void *LocalStackBase = alloca(LocalStackSize);
3705 FakeStackInt = Constant::getNullValue(IntptrTy);
3706 FakeStackPtr = Constant::getNullValue(PtrTy);
3707 LocalStackBase =
3708 DoDynamicAlloca ? createAllocaForLayout(IRB, L, true) : StaticAlloca;
3709 LocalStackBaseAlloca = LocalStackBase;
3710 }
3711
3712 // Replace Alloca instructions with base+offset.
3713 SmallVector<Value *> NewAllocaPtrs;
3714 for (const auto &Desc : SVD) {
3715 AllocaInst *AI = Desc.AI;
3716 replaceDbgDeclare(AI, LocalStackBaseAlloca, DIB, DIExprFlags, Desc.Offset);
3717 Value *NewAllocaPtr = IRB.CreatePtrAdd(
3718 LocalStackBase, ConstantInt::get(IntptrTy, Desc.Offset));
3719 AI->replaceAllUsesWith(NewAllocaPtr);
3720 NewAllocaPtrs.push_back(NewAllocaPtr);
3721 }
3722
3723 // The left-most redzone has enough space for at least 4 pointers.
3724 // Write the Magic value to redzone[0].
3725 IRB.CreateStore(ConstantInt::get(IntptrTy, kCurrentStackFrameMagic),
3726 LocalStackBase);
3727 // Write the frame description constant to redzone[1].
3728 Value *BasePlus1 = IRB.CreatePtrAdd(
3729 LocalStackBase, ConstantInt::get(IntptrTy, ASan.LongSize / 8));
3730 GlobalVariable *StackDescriptionGlobal =
3731 createPrivateGlobalForString(*F.getParent(), DescriptionString,
3732 /*AllowMerging*/ true, genName("stack"));
3733 Value *Description = IRB.CreatePointerCast(StackDescriptionGlobal, IntptrTy);
3734 IRB.CreateStore(Description, BasePlus1);
3735 // Write the PC to redzone[2].
3736 Value *BasePlus2 = IRB.CreatePtrAdd(
3737 LocalStackBase, ConstantInt::get(IntptrTy, 2 * ASan.LongSize / 8));
3738 IRB.CreateStore(IRB.CreatePointerCast(&F, IntptrTy), BasePlus2);
3739
3740 const auto &ShadowAfterScope = GetShadowBytesAfterScope(SVD, L);
3741
3742 // Poison the stack red zones at the entry.
3743 Value *ShadowBase =
3744 ASan.memToShadow(IRB.CreatePtrToInt(LocalStackBase, IntptrTy), IRB);
3745 // As mask we must use most poisoned case: red zones and after scope.
3746 // As bytes we can use either the same or just red zones only.
3747 copyToShadow(ShadowAfterScope, ShadowAfterScope, IRB, ShadowBase);
3748
3749 if (!StaticAllocaPoisonCallVec.empty()) {
3750 const auto &ShadowInScope = GetShadowBytes(SVD, L);
3751
3752 // Poison static allocas near lifetime intrinsics.
3753 for (const auto &APC : StaticAllocaPoisonCallVec) {
3754 const ASanStackVariableDescription &Desc = *AllocaToSVDMap[APC.AI];
3755 assert(Desc.Offset % L.Granularity == 0);
3756 size_t Begin = Desc.Offset / L.Granularity;
3757 size_t End = Begin + (APC.Size + L.Granularity - 1) / L.Granularity;
3758
3759 IRBuilder<> IRB(APC.InsBefore);
3760 copyToShadow(ShadowAfterScope,
3761 APC.DoPoison ? ShadowAfterScope : ShadowInScope, Begin, End,
3762 IRB, ShadowBase);
3763 }
3764 }
3765
3766 // Remove lifetime markers now that these are no longer allocas.
3767 for (Value *NewAllocaPtr : NewAllocaPtrs) {
3768 for (User *U : make_early_inc_range(NewAllocaPtr->users())) {
3769 auto *I = cast<Instruction>(U);
3770 if (I->isLifetimeStartOrEnd())
3771 I->eraseFromParent();
3772 }
3773 }
3774
3775 SmallVector<uint8_t, 64> ShadowClean(ShadowAfterScope.size(), 0);
3776 SmallVector<uint8_t, 64> ShadowAfterReturn;
3777
3778 // (Un)poison the stack before all ret instructions.
3779 for (Instruction *Ret : RetVec) {
3780 IRBuilder<> IRBRet(Ret);
3781 // Mark the current frame as retired.
3782 IRBRet.CreateStore(ConstantInt::get(IntptrTy, kRetiredStackFrameMagic),
3783 LocalStackBase);
3784 if (DoStackMalloc) {
3785 assert(StackMallocIdx >= 0);
3786 // if FakeStack != 0 // LocalStackBase == FakeStack
3787 // // In use-after-return mode, poison the whole stack frame.
3788 // if StackMallocIdx <= 4
3789 // // For small sizes inline the whole thing:
3790 // memset(ShadowBase, kAsanStackAfterReturnMagic, ShadowSize);
3791 // **SavedFlagPtr(FakeStack) = 0
3792 // else
3793 // __asan_stack_free_N(FakeStack, LocalStackSize)
3794 // else
3795 // <This is not a fake stack; unpoison the redzones>
3796 Value *Cmp =
3797 IRBRet.CreateICmpNE(FakeStackInt, Constant::getNullValue(IntptrTy));
3798 Instruction *ThenTerm, *ElseTerm;
3799 SplitBlockAndInsertIfThenElse(Cmp, Ret, &ThenTerm, &ElseTerm);
3800
3801 IRBuilder<> IRBPoison(ThenTerm);
3802 if (ASan.MaxInlinePoisoningSize != 0 && StackMallocIdx <= 4) {
3803 int ClassSize = kMinStackMallocSize << StackMallocIdx;
3804 ShadowAfterReturn.resize(ClassSize / L.Granularity,
3806 copyToShadow(ShadowAfterReturn, ShadowAfterReturn, IRBPoison,
3807 ShadowBase);
3808 Value *SavedFlagPtrPtr = IRBPoison.CreatePtrAdd(
3809 FakeStackPtr,
3810 ConstantInt::get(IntptrTy, ClassSize - ASan.LongSize / 8));
3811 Value *SavedFlagPtr = IRBPoison.CreateLoad(IntptrTy, SavedFlagPtrPtr);
3812 IRBPoison.CreateStore(
3813 Constant::getNullValue(IRBPoison.getInt8Ty()),
3814 IRBPoison.CreateIntToPtr(SavedFlagPtr, IRBPoison.getPtrTy()));
3815 } else {
3816 // For larger frames call __asan_stack_free_*.
3817 RTCI.createRuntimeCall(
3818 IRBPoison, AsanStackFreeFunc[StackMallocIdx],
3819 {FakeStackInt, ConstantInt::get(IntptrTy, LocalStackSize)});
3820 }
3821
3822 IRBuilder<> IRBElse(ElseTerm);
3823 copyToShadow(ShadowAfterScope, ShadowClean, IRBElse, ShadowBase);
3824 } else {
3825 copyToShadow(ShadowAfterScope, ShadowClean, IRBRet, ShadowBase);
3826 }
3827 }
3828
3829 // We are done. Remove the old unused alloca instructions.
3830 for (auto *AI : AllocaVec)
3831 AI->eraseFromParent();
3832}
3833
3834void FunctionStackPoisoner::poisonAlloca(Value *V, uint64_t Size,
3835 IRBuilder<> &IRB, bool DoPoison) {
3836 // For now just insert the call to ASan runtime.
3837 Value *AddrArg = IRB.CreatePointerCast(V, IntptrTy);
3838 Value *SizeArg = ConstantInt::get(IntptrTy, Size);
3839 RTCI.createRuntimeCall(
3840 IRB, DoPoison ? AsanPoisonStackMemoryFunc : AsanUnpoisonStackMemoryFunc,
3841 {AddrArg, SizeArg});
3842}
3843
3844// Handling llvm.lifetime intrinsics for a given %alloca:
3845// (1) collect all llvm.lifetime.xxx(%size, %value) describing the alloca.
3846// (2) if %size is constant, poison memory for llvm.lifetime.end (to detect
3847// invalid accesses) and unpoison it for llvm.lifetime.start (the memory
3848// could be poisoned by previous llvm.lifetime.end instruction, as the
3849// variable may go in and out of scope several times, e.g. in loops).
3850// (3) if we poisoned at least one %alloca in a function,
3851// unpoison the whole stack frame at function exit.
3852void FunctionStackPoisoner::handleDynamicAllocaCall(AllocaInst *AI) {
3853 IRBuilder<> IRB(AI);
3854
3855 const Align Alignment = std::max(Align(kAllocaRzSize), AI->getAlign());
3856 const uint64_t AllocaRedzoneMask = kAllocaRzSize - 1;
3857
3858 Value *Zero = Constant::getNullValue(IntptrTy);
3859 Value *AllocaRzSize = ConstantInt::get(IntptrTy, kAllocaRzSize);
3860 Value *AllocaRzMask = ConstantInt::get(IntptrTy, AllocaRedzoneMask);
3861
3862 // Since we need to extend alloca with additional memory to locate
3863 // redzones, and OldSize is number of allocated blocks with
3864 // ElementSize size, get allocated memory size in bytes by
3865 // OldSize * ElementSize.
3866 Value *OldSize = IRB.CreateAllocationSize(IntptrTy, AI);
3867
3868 // PartialSize = OldSize % 32
3869 Value *PartialSize = IRB.CreateAnd(OldSize, AllocaRzMask);
3870
3871 // Misalign = kAllocaRzSize - PartialSize;
3872 Value *Misalign = IRB.CreateSub(AllocaRzSize, PartialSize);
3873
3874 // PartialPadding = Misalign != kAllocaRzSize ? Misalign : 0;
3875 Value *Cond = IRB.CreateICmpNE(Misalign, AllocaRzSize);
3876 Value *PartialPadding = IRB.CreateSelect(Cond, Misalign, Zero);
3877
3878 // AdditionalChunkSize = Alignment + PartialPadding + kAllocaRzSize
3879 // Alignment is added to locate left redzone, PartialPadding for possible
3880 // partial redzone and kAllocaRzSize for right redzone respectively.
3881 Value *AdditionalChunkSize = IRB.CreateAdd(
3882 ConstantInt::get(IntptrTy, Alignment.value() + kAllocaRzSize),
3883 PartialPadding);
3884
3885 Value *NewSize = IRB.CreateAdd(OldSize, AdditionalChunkSize);
3886
3887 // Insert new alloca with new NewSize and Alignment params.
3888 AllocaInst *NewAlloca = IRB.CreateAlloca(IRB.getInt8Ty(), NewSize);
3889 NewAlloca->setAlignment(Alignment);
3890
3891 // NewAddress = Address + Alignment
3892 Value *NewAddress =
3893 IRB.CreateAdd(IRB.CreatePtrToInt(NewAlloca, IntptrTy),
3894 ConstantInt::get(IntptrTy, Alignment.value()));
3895
3896 // Insert __asan_alloca_poison call for new created alloca.
3897 RTCI.createRuntimeCall(IRB, AsanAllocaPoisonFunc, {NewAddress, OldSize});
3898
3899 // Store the last alloca's address to DynamicAllocaLayout. We'll need this
3900 // for unpoisoning stuff.
3901 IRB.CreateStore(IRB.CreatePtrToInt(NewAlloca, IntptrTy), DynamicAllocaLayout);
3902
3903 Value *NewAddressPtr = IRB.CreateIntToPtr(NewAddress, AI->getType());
3904
3905 // Remove lifetime markers now that this is no longer an alloca.
3906 for (User *U : make_early_inc_range(AI->users())) {
3907 auto *I = cast<Instruction>(U);
3908 if (I->isLifetimeStartOrEnd())
3909 I->eraseFromParent();
3910 }
3911
3912 // Replace all uses of AddressReturnedByAlloca with NewAddressPtr.
3913 AI->replaceAllUsesWith(NewAddressPtr);
3914
3915 // We are done. Erase old alloca from parent.
3916 AI->eraseFromParent();
3917}
3918
3919// isSafeAccess returns true if Addr is always inbounds with respect to its
3920// base object. For example, it is a field access or an array access with
3921// constant inbounds index.
3922bool AddressSanitizer::isSafeAccess(ObjectSizeOffsetVisitor &ObjSizeVis,
3923 Value *Addr, TypeSize TypeStoreSize) const {
3924 if (TypeStoreSize.isScalable())
3925 // TODO: We can use vscale_range to convert a scalable value to an
3926 // upper bound on the access size.
3927 return false;
3928
3929 SizeOffsetAPInt SizeOffset = ObjSizeVis.compute(Addr);
3930 if (!SizeOffset.bothKnown())
3931 return false;
3932
3933 uint64_t Size = SizeOffset.Size.getZExtValue();
3934 int64_t Offset = SizeOffset.Offset.getSExtValue();
3935
3936 // Three checks are required to ensure safety:
3937 // . Offset >= 0 (since the offset is given from the base ptr)
3938 // . Size >= Offset (unsigned)
3939 // . Size - Offset >= NeededSize (unsigned)
3940 return Offset >= 0 && Size >= uint64_t(Offset) &&
3941 Size - uint64_t(Offset) >= TypeStoreSize / 8;
3942}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static cl::opt< bool > ClUseStackSafety("stack-tagging-use-stack-safety", cl::Hidden, cl::init(true), cl::desc("Use Stack Safety analysis results"))
Rewrite undef for PHI
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static void findStoresToUninstrumentedArgAllocas(AddressSanitizer &ASan, Instruction &InsBefore, SmallVectorImpl< Instruction * > &InitInsts)
Collect instructions in the entry block after InsBefore which initialize permanent storage for a func...
static void doInstrumentAddress(AddressSanitizer *Pass, Instruction *I, Instruction *InsertBefore, Value *Addr, MaybeAlign Alignment, unsigned Granularity, TypeSize TypeStoreSize, bool IsWrite, Value *SizeArgument, bool UseCalls, uint32_t Exp, RuntimeCallInserter &RTCI)
static const uint64_t kDefaultShadowScale
const char kAMDGPUUnreachableName[]
constexpr size_t kAccessSizeIndexMask
static cl::opt< int > ClDebugMin("asan-debug-min", cl::desc("Debug min inst"), cl::Hidden, cl::init(-1))
static cl::opt< bool > ClUsePrivateAlias("asan-use-private-alias", cl::desc("Use private aliases for global variables"), cl::Hidden, cl::init(true))
static const uint64_t kPS_ShadowOffset64
static const uint64_t kFreeBSD_ShadowOffset32
constexpr size_t kIsWriteShift
static const uint64_t kSmallX86_64ShadowOffsetAlignMask
static bool isInterestingPointerSubtraction(Instruction *I)
const char kAMDGPUAddressSharedName[]
const char kAsanStackFreeNameTemplate[]
constexpr size_t kCompileKernelMask
static cl::opt< bool > ClForceDynamicShadow("asan-force-dynamic-shadow", cl::desc("Load shadow address into a local variable for each function"), cl::Hidden, cl::init(false))
const char kAsanOptionDetectUseAfterReturn[]
static cl::opt< std::string > ClMemoryAccessCallbackPrefix("asan-memory-access-callback-prefix", cl::desc("Prefix for memory access callbacks"), cl::Hidden, cl::init("__asan_"))
static const uint64_t kRISCV64_ShadowOffset64
static cl::opt< bool > ClInsertVersionCheck("asan-guard-against-version-mismatch", cl::desc("Guard against compiler/runtime version mismatch."), cl::Hidden, cl::init(true))
const char kAsanSetShadowPrefix[]
static cl::opt< AsanDtorKind > ClOverrideDestructorKind("asan-destructor-kind", cl::desc("Sets the ASan destructor kind. The default is to use the value " "provided to the pass constructor"), cl::values(clEnumValN(AsanDtorKind::None, "none", "No destructors"), clEnumValN(AsanDtorKind::Global, "global", "Use global destructors")), cl::init(AsanDtorKind::Invalid), cl::Hidden)
static Twine genName(StringRef suffix)
static cl::opt< bool > ClInstrumentWrites("asan-instrument-writes", cl::desc("instrument write instructions"), cl::Hidden, cl::init(true))
const char kAsanPtrCmp[]
static uint64_t GetCtorAndDtorPriority(Triple &TargetTriple)
const char kAsanStackMallocNameTemplate[]
static cl::opt< bool > ClInstrumentByval("asan-instrument-byval", cl::desc("instrument byval call arguments"), cl::Hidden, cl::init(true))
const char kAsanInitName[]
static cl::opt< bool > ClGlobals("asan-globals", cl::desc("Handle global objects"), cl::Hidden, cl::init(true))
static cl::opt< bool > ClRedzoneByvalArgs("asan-redzone-byval-args", cl::desc("Create redzones for byval " "arguments (extra copy " "required)"), cl::Hidden, cl::init(true))
static const uint64_t kWindowsShadowOffset64
const char kAsanGenPrefix[]
constexpr size_t kIsWriteMask
static uint64_t getRedzoneSizeForScale(int MappingScale)
static const uint64_t kDefaultShadowOffset64
static cl::opt< bool > ClOptimizeCallbacks("asan-optimize-callbacks", cl::desc("Optimize callbacks"), cl::Hidden, cl::init(false))
const char kAsanUnregisterGlobalsName[]
static const uint64_t kAsanCtorAndDtorPriority
const char kAsanUnpoisonGlobalsName[]
static cl::opt< bool > ClWithIfuncSuppressRemat("asan-with-ifunc-suppress-remat", cl::desc("Suppress rematerialization of dynamic shadow address by passing " "it through inline asm in prologue."), cl::Hidden, cl::init(true))
static cl::opt< int > ClDebugStack("asan-debug-stack", cl::desc("debug stack"), cl::Hidden, cl::init(0))
const char kAsanUnregisterElfGlobalsName[]
static bool isUnsupportedAMDGPUAddrspace(Value *Addr)
const char kAsanRegisterImageGlobalsName[]
static const uint64_t kWebAssemblyShadowOffset
static cl::opt< bool > ClOpt("asan-opt", cl::desc("Optimize instrumentation"), cl::Hidden, cl::init(true))
static const uint64_t kAllocaRzSize
const char kODRGenPrefix[]
static const uint64_t kSystemZ_ShadowOffset64
static const uint64_t kDefaultShadowOffset32
const char kAsanShadowMemoryDynamicAddress[]
static cl::opt< bool > ClUseOdrIndicator("asan-use-odr-indicator", cl::desc("Use odr indicators to improve ODR reporting"), cl::Hidden, cl::init(true))
static bool GlobalWasGeneratedByCompiler(GlobalVariable *G)
Check if G has been created by a trusted compiler pass.
const char kAsanStackMallocAlwaysNameTemplate[]
static cl::opt< int > ClShadowAddrSpace("asan-shadow-addr-space", cl::desc("Address space for pointers to the shadow map"), cl::Hidden, cl::init(0))
static cl::opt< bool > ClInvalidPointerCmp("asan-detect-invalid-pointer-cmp", cl::desc("Instrument <, <=, >, >= with pointer operands"), cl::Hidden, cl::init(false))
static const uint64_t kAsanEmscriptenCtorAndDtorPriority
static cl::opt< int > ClInstrumentationWithCallsThreshold("asan-instrumentation-with-call-threshold", cl::desc("If the function being instrumented contains more than " "this number of memory accesses, use callbacks instead of " "inline checks (-1 means never use callbacks)."), cl::Hidden, cl::init(7000))
static cl::opt< int > ClDebugMax("asan-debug-max", cl::desc("Debug max inst"), cl::Hidden, cl::init(-1))
static cl::opt< bool > ClInvalidPointerSub("asan-detect-invalid-pointer-sub", cl::desc("Instrument - operations with pointer operands"), cl::Hidden, cl::init(false))
static const uint64_t kFreeBSD_ShadowOffset64
static cl::opt< uint32_t > ClForceExperiment("asan-force-experiment", cl::desc("Force optimization experiment (for testing)"), cl::Hidden, cl::init(0))
const char kSanCovGenPrefix[]
static const uint64_t kFreeBSDKasan_ShadowOffset64
const char kAsanModuleDtorName[]
static const uint64_t kDynamicShadowSentinel
static bool isInterestingPointerComparison(Instruction *I)
static cl::list< unsigned > ClAddrSpaces("asan-instrument-address-spaces", cl::desc("Only instrument variables in the specified address spaces."), cl::Hidden, cl::CommaSeparated, cl::callback([](const unsigned &AddrSpace) { SrcAddrSpaces.insert(AddrSpace);}))
static cl::opt< bool > ClStack("asan-stack", cl::desc("Handle stack memory"), cl::Hidden, cl::init(true))
static const uint64_t kMIPS64_ShadowOffset64
static const uint64_t kLinuxKasan_ShadowOffset64
static int StackMallocSizeClass(uint64_t LocalStackSize)
static cl::opt< uint32_t > ClMaxInlinePoisoningSize("asan-max-inline-poisoning-size", cl::desc("Inline shadow poisoning for blocks up to the given size in bytes."), cl::Hidden, cl::init(64))
static cl::opt< bool > ClInstrumentAtomics("asan-instrument-atomics", cl::desc("instrument atomic instructions (rmw, cmpxchg)"), cl::Hidden, cl::init(true))
static cl::opt< bool > ClUseAfterScope("asan-use-after-scope", cl::desc("Check stack-use-after-scope"), cl::Hidden, cl::init(false))
constexpr size_t kAccessSizeIndexShift
static cl::opt< int > ClMappingScale("asan-mapping-scale", cl::desc("scale of asan shadow mapping"), cl::Hidden, cl::init(0))
const char kAsanPoisonStackMemoryName[]
static cl::opt< bool > ClEnableKasan("asan-kernel", cl::desc("Enable KernelAddressSanitizer instrumentation"), cl::Hidden, cl::init(false))
static cl::opt< std::string > ClDebugFunc("asan-debug-func", cl::Hidden, cl::desc("Debug func"))
static bool isSupportedAddrspace(const Triple &TargetTriple, Value *Addr)
static cl::opt< bool > ClUseGlobalsGC("asan-globals-live-support", cl::desc("Use linker features to support dead " "code stripping of globals"), cl::Hidden, cl::init(true))
static const size_t kNumberOfAccessSizes
const char kAsanUnpoisonStackMemoryName[]
static const uint64_t kLoongArch64_ShadowOffset64
const char kAsanRegisterGlobalsName[]
static cl::opt< bool > ClInstrumentDynamicAllocas("asan-instrument-dynamic-allocas", cl::desc("instrument dynamic allocas"), cl::Hidden, cl::init(true))
const char kAsanModuleCtorName[]
const char kAsanGlobalsRegisteredFlagName[]
static const size_t kMaxStackMallocSize
static cl::opt< bool > ClRecover("asan-recover", cl::desc("Enable recovery mode (continue-after-error)."), cl::Hidden, cl::init(false))
static cl::opt< bool > ClOptSameTemp("asan-opt-same-temp", cl::desc("Instrument the same temp just once"), cl::Hidden, cl::init(true))
static cl::opt< bool > ClDynamicAllocaStack("asan-stack-dynamic-alloca", cl::desc("Use dynamic alloca to represent stack variables"), cl::Hidden, cl::init(true))
static cl::opt< bool > ClOptStack("asan-opt-stack", cl::desc("Don't instrument scalar stack variables"), cl::Hidden, cl::init(false))
static const uint64_t kMIPS_ShadowOffsetN32
const char kAsanUnregisterImageGlobalsName[]
static cl::opt< AsanDetectStackUseAfterReturnMode > ClUseAfterReturn("asan-use-after-return", cl::desc("Sets the mode of detection for stack-use-after-return."), cl::values(clEnumValN(AsanDetectStackUseAfterReturnMode::Never, "never", "Never detect stack use after return."), clEnumValN(AsanDetectStackUseAfterReturnMode::Runtime, "runtime", "Detect stack use after return if " "binary flag 'ASAN_OPTIONS=detect_stack_use_after_return' is set."), clEnumValN(AsanDetectStackUseAfterReturnMode::Always, "always", "Always detect stack use after return.")), cl::Hidden, cl::init(AsanDetectStackUseAfterReturnMode::Runtime))
static cl::opt< bool > ClOptGlobals("asan-opt-globals", cl::desc("Don't instrument scalar globals"), cl::Hidden, cl::init(true))
static const uintptr_t kCurrentStackFrameMagic
static ShadowMapping getShadowMapping(const Triple &TargetTriple, int LongSize, bool IsKasan)
static const uint64_t kPPC64_ShadowOffset64
static cl::opt< AsanCtorKind > ClConstructorKind("asan-constructor-kind", cl::desc("Sets the ASan constructor kind"), cl::values(clEnumValN(AsanCtorKind::None, "none", "No constructors"), clEnumValN(AsanCtorKind::Global, "global", "Use global constructors")), cl::init(AsanCtorKind::Global), cl::Hidden)
static const int kMaxAsanStackMallocSizeClass
static const uint64_t kMIPS32_ShadowOffset32
static cl::opt< bool > ClAlwaysSlowPath("asan-always-slow-path", cl::desc("use instrumentation with slow path for all accesses"), cl::Hidden, cl::init(false))
static const uint64_t kNetBSD_ShadowOffset32
static const uint64_t kFreeBSDAArch64_ShadowOffset64
static const uint64_t kSmallX86_64ShadowOffsetBase
static cl::opt< bool > ClInitializers("asan-initialization-order", cl::desc("Handle C++ initializer order"), cl::Hidden, cl::init(true))
static const uint64_t kNetBSD_ShadowOffset64
const char kAsanPtrSub[]
static cl::opt< unsigned > ClRealignStack("asan-realign-stack", cl::desc("Realign stack to the value of this flag (power of two)"), cl::Hidden, cl::init(32))
static const uint64_t kWindowsShadowOffset32
static cl::opt< bool > ClInstrumentReads("asan-instrument-reads", cl::desc("instrument read instructions"), cl::Hidden, cl::init(true))
static size_t TypeStoreSizeToSizeIndex(uint32_t TypeSize)
const char kAsanAllocaPoison[]
constexpr size_t kCompileKernelShift
static SmallSet< unsigned, 8 > SrcAddrSpaces
static cl::opt< bool > ClWithIfunc("asan-with-ifunc", cl::desc("Access dynamic shadow through an ifunc global on " "platforms that support this"), cl::Hidden, cl::init(true))
static cl::opt< bool > ClKasanMemIntrinCallbackPrefix("asan-kernel-mem-intrinsic-prefix", cl::desc("Use prefix for memory intrinsics in KASAN mode"), cl::Hidden, cl::init(false))
const char kAsanVersionCheckNamePrefix[]
const char kAMDGPUAddressPrivateName[]
static const uint64_t kNetBSDKasan_ShadowOffset64
const char kAMDGPUBallotName[]
const char kAsanRegisterElfGlobalsName[]
static cl::opt< uint64_t > ClMappingOffset("asan-mapping-offset", cl::desc("offset of asan shadow mapping [EXPERIMENTAL]"), cl::Hidden, cl::init(0))
const char kAsanReportErrorTemplate[]
static cl::opt< bool > ClWithComdat("asan-with-comdat", cl::desc("Place ASan constructors in comdat sections"), cl::Hidden, cl::init(true))
static StringRef getAllocaName(AllocaInst *AI)
static cl::opt< bool > ClSkipPromotableAllocas("asan-skip-promotable-allocas", cl::desc("Do not instrument promotable allocas"), cl::Hidden, cl::init(true))
static cl::opt< int > ClMaxInsnsToInstrumentPerBB("asan-max-ins-per-bb", cl::init(10000), cl::desc("maximal number of instructions to instrument in any given BB"), cl::Hidden)
static const uintptr_t kRetiredStackFrameMagic
static cl::opt< bool > ClUseStackSafety("asan-use-stack-safety", cl::Hidden, cl::init(true), cl::Hidden, cl::desc("Use Stack Safety analysis results"), cl::Optional)
const char kAsanPoisonGlobalsName[]
const char kAsanHandleNoReturnName[]
static const size_t kMinStackMallocSize
static cl::opt< int > ClDebug("asan-debug", cl::desc("debug"), cl::Hidden, cl::init(0))
const char kAsanAllocasUnpoison[]
static const uint64_t kAArch64_ShadowOffset64
static cl::opt< bool > ClInvalidPointerPairs("asan-detect-invalid-pointer-pair", cl::desc("Instrument <, <=, >, >=, - with pointer operands"), cl::Hidden, cl::init(false))
Function Alias Analysis false
This file contains the simple types necessary to represent the attributes associated with functions a...
static bool isPointerOperand(Value *I, User *U)
static const Function * getParent(const Value *V)
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
#define clEnumValN(ENUMVAL, FLAGNAME, DESC)
This file contains the declarations for the subclasses of Constant, which represent the different fla...
DXIL Finalize Linkage
dxil translate DXIL Translate Metadata
This file defines the DenseMap class.
This file builds on the ADT/GraphTraits.h file to build generic depth first graph iterator.
static bool runOnFunction(Function &F, bool PostInlining)
This is the interface for a simple mod/ref and alias analysis over globals.
IRTranslator LLVM IR MI
Module.h This file contains the declarations for the Module class.
This defines the Use class.
std::pair< Instruction::BinaryOps, Value * > OffsetOp
Find all possible pairs (BinOp, RHS) that BinOp V, RHS can be simplified.
static bool isZero(Value *V, const DataLayout &DL, DominatorTree *DT, AssumptionCache *AC)
Definition Lint.cpp:539
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
#define G(x, y, z)
Definition MD5.cpp:55
print mir2vec MIR2Vec Vocabulary Printer Pass
Definition MIR2Vec.cpp:598
Machine Check Debug Module
This file contains the declarations for metadata subclasses.
uint64_t IntrinsicInst * II
FunctionAnalysisManager FAM
ModuleAnalysisManager MAM
if(PassOpts->AAPipeline)
const SmallVectorImpl< MachineOperand > & Cond
static void visit(BasicBlock &Start, std::function< bool(BasicBlock *)> op)
#define OP(OPC)
Definition Instruction.h:46
This file defines the SmallPtrSet class.
This file defines the SmallSet class.
This file defines the SmallVector class.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
Definition Statistic.h:171
This file contains some functions that are useful when dealing with strings.
#define LLVM_DEBUG(...)
Definition Debug.h:119
static SymbolRef::Type getType(const Symbol *Sym)
Definition TapiFile.cpp:39
This pass exposes codegen information to IR-level passes.
uint64_t getZExtValue() const
Get zero extended value.
Definition APInt.h:1563
int64_t getSExtValue() const
Get sign extended value.
Definition APInt.h:1585
LLVM_ABI AddressSanitizerPass(const AddressSanitizerOptions &Options, bool UseGlobalGC=true, bool UseOdrIndicator=true, AsanDtorKind DestructorKind=AsanDtorKind::Global, AsanCtorKind ConstructorKind=AsanCtorKind::Global)
LLVM_ABI PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM)
LLVM_ABI void printPipeline(raw_ostream &OS, function_ref< StringRef(StringRef)> MapClassName2PassName)
an instruction to allocate memory on the stack
bool isSwiftError() const
Return true if this alloca is used as a swifterror argument to a call.
LLVM_ABI bool isStaticAlloca() const
Return true if this alloca is in the entry block of the function and is a constant size.
Align getAlign() const
Return the alignment of the memory that is being allocated by the instruction.
PointerType * getType() const
Overload to return most specific pointer type.
Type * getAllocatedType() const
Return the type that is being allocated by the instruction.
bool isUsedWithInAlloca() const
Return true if this alloca is used as an inalloca argument to a call.
LLVM_ABI std::optional< TypeSize > getAllocationSize(const DataLayout &DL) const
Get allocation size in bytes.
void setAlignment(Align Align)
This class represents an incoming formal argument to a Function.
Definition Argument.h:32
Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
size_t size() const
Get the array size.
Definition ArrayRef.h:141
Class to represent array types.
static LLVM_ABI ArrayType * get(Type *ElementType, uint64_t NumElements)
This static method is the primary way to construct an ArrayType.
An instruction that atomically checks whether a specified value is in a memory location,...
an instruction that atomically reads a memory location, combines it with another value,...
LLVM Basic Block Representation.
Definition BasicBlock.h:62
iterator begin()
Instruction iterator methods.
Definition BasicBlock.h:461
LLVM_ABI const_iterator getFirstInsertionPt() const
Returns an iterator to the first instruction in this block that is suitable for inserting a non-PHI i...
const Function * getParent() const
Return the enclosing method, or null if none.
Definition BasicBlock.h:213
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
Definition BasicBlock.h:206
InstListType::iterator iterator
Instruction iterators...
Definition BasicBlock.h:170
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction; assumes that the block is well-formed.
Definition BasicBlock.h:237
bool isInlineAsm() const
Check if this call is an inline asm statement.
void setCannotMerge()
static LLVM_ABI CallBase * addOperandBundle(CallBase *CB, uint32_t ID, OperandBundleDef OB, InsertPosition InsertPt=nullptr)
Create a clone of CB with operand bundle OB added.
bool doesNotReturn() const
Determine if the call cannot return.
unsigned arg_size() const
This class represents a function call, abstracting a target machine's calling convention.
static CallInst * Create(FunctionType *Ty, Value *F, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
@ Largest
The linker will choose the largest COMDAT.
Definition Comdat.h:39
@ SameSize
The data referenced by the COMDAT must be the same size.
Definition Comdat.h:41
@ Any
The linker may choose any COMDAT.
Definition Comdat.h:37
@ NoDeduplicate
No deduplication is performed.
Definition Comdat.h:40
@ ExactMatch
The data referenced by the COMDAT must be the same.
Definition Comdat.h:38
Conditional Branch instruction.
static CondBrInst * Create(Value *Cond, BasicBlock *IfTrue, BasicBlock *IfFalse, InsertPosition InsertBefore=nullptr)
ConstantArray - Constant Array Declarations.
Definition Constants.h:582
static LLVM_ABI Constant * get(ArrayType *T, ArrayRef< Constant * > V)
static LLVM_ABI Constant * getPointerCast(Constant *C, Type *Ty)
Create a BitCast, AddrSpaceCast, or a PtrToInt cast constant expression.
static LLVM_ABI Constant * getPtrToInt(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static LLVM_ABI bool isValueValidForType(Type *Ty, uint64_t V)
This static method returns true if the type Ty is big enough to represent the value V.
static LLVM_ABI Constant * get(StructType *T, ArrayRef< Constant * > V)
This is an important base class in LLVM.
Definition Constant.h:43
static LLVM_ABI Constant * getAllOnesValue(Type *Ty)
static LLVM_ABI Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
LLVM_ABI Constant * getAggregateElement(unsigned Elt) const
For aggregates (struct/array/vector) return the constant that corresponds to the specified element if...
A parsed version of the target data layout string in and methods for querying it.
Definition DataLayout.h:64
A debug info location.
Definition DebugLoc.h:123
LLVM_ABI DILocation * get() const
Get the underlying DILocation.
Definition DebugLoc.cpp:48
A handy container for a FunctionType+Callee-pointer pair, which can be passed around as a single enti...
static LLVM_ABI FunctionType * get(Type *Result, ArrayRef< Type * > Params, bool isVarArg)
This static method is the primary way of constructing a FunctionType.
const BasicBlock & front() const
Definition Function.h:860
static Function * createWithDefaultAttr(FunctionType *Ty, LinkageTypes Linkage, unsigned AddrSpace, const Twine &N="", Module *M=nullptr)
Creates a function with some attributes recorded in llvm.module.flags and the LLVMContext applied.
Definition Function.cpp:378
bool hasPersonalityFn() const
Check whether this function has a personality function.
Definition Function.h:905
LLVMContext & getContext() const
getContext - Return a reference to the LLVMContext associated with this function.
Definition Function.cpp:358
const Constant * getAliasee() const
Definition GlobalAlias.h:87
static LLVM_ABI GlobalAlias * create(Type *Ty, unsigned AddressSpace, LinkageTypes Linkage, const Twine &Name, Constant *Aliasee, Module *Parent)
If a parent module is specified, the alias is automatically inserted into the end of the specified mo...
Definition Globals.cpp:621
LLVM_ABI void copyMetadata(const GlobalObject *Src, unsigned Offset)
Copy metadata from Src, adjusting offsets by Offset.
LLVM_ABI void setComdat(Comdat *C)
Definition Globals.cpp:223
LLVM_ABI void setSection(StringRef S)
Change the section for this global.
Definition Globals.cpp:284
VisibilityTypes getVisibility() const
void setUnnamedAddr(UnnamedAddr Val)
bool hasLocalLinkage() const
static StringRef dropLLVMManglingEscape(StringRef Name)
If the given string begins with the GlobalValue name mangling escape character '\1',...
ThreadLocalMode getThreadLocalMode() const
@ HiddenVisibility
The GV is hidden.
Definition GlobalValue.h:69
void setVisibility(VisibilityTypes V)
LinkageTypes
An enumeration for the kinds of linkage for global values.
Definition GlobalValue.h:52
@ PrivateLinkage
Like Internal, but omit from symbol table.
Definition GlobalValue.h:61
@ CommonLinkage
Tentative definitions.
Definition GlobalValue.h:63
@ InternalLinkage
Rename collisions when linking (static functions).
Definition GlobalValue.h:60
@ AvailableExternallyLinkage
Available for inspection, not emission.
Definition GlobalValue.h:54
@ ExternalWeakLinkage
ExternalWeak linkage description.
Definition GlobalValue.h:62
DLLStorageClassTypes getDLLStorageClass() const
const Constant * getInitializer() const
getInitializer - Return the initializer for this global variable.
LLVM_ABI void copyAttributesFrom(const GlobalVariable *Src)
copyAttributesFrom - copy all additional attributes (those not needed to create a GlobalVariable) fro...
Definition Globals.cpp:576
void setAlignment(Align Align)
Sets the alignment attribute of the GlobalVariable.
Analysis pass providing a never-invalidated alias analysis result.
This instruction compares its operands according to the predicate given to the constructor.
Common base class shared among various IRBuilders.
Definition IRBuilder.h:114
AllocaInst * CreateAlloca(Type *Ty, unsigned AddrSpace, Value *ArraySize=nullptr, const Twine &Name="")
Definition IRBuilder.h:1891
IntegerType * getInt1Ty()
Fetch the type representing a single bit.
Definition IRBuilder.h:571
LLVM_ABI Value * CreateAllocationSize(Type *DestTy, AllocaInst *AI)
Get allocation size of an alloca as a runtime Value* (handles both static and dynamic allocas and vsc...
LoadInst * CreateAlignedLoad(Type *Ty, Value *Ptr, MaybeAlign Align, const char *Name)
Definition IRBuilder.h:1935
CallInst * CreateMemCpy(Value *Dst, MaybeAlign DstAlign, Value *Src, MaybeAlign SrcAlign, uint64_t Size, bool isVolatile=false, const AAMDNodes &AAInfo=AAMDNodes())
Create and insert a memcpy between the specified pointers.
Definition IRBuilder.h:717
Value * CreatePointerCast(Value *V, Type *DestTy, const Twine &Name="")
Definition IRBuilder.h:2289
LLVM_ABI CallInst * CreateIntrinsic(Intrinsic::ID ID, ArrayRef< Type * > OverloadTypes, ArrayRef< Value * > Args, FMFSource FMFSource={}, const Twine &Name="", ArrayRef< OperandBundleDef > OpBundles={})
Create a call to intrinsic ID with Args, mangled using OverloadTypes.
Value * CreateICmpSGE(Value *LHS, Value *RHS, const Twine &Name="")
Definition IRBuilder.h:2402
LLVM_ABI Value * CreateSelect(Value *C, Value *True, Value *False, const Twine &Name="", Instruction *MDFrom=nullptr)
BasicBlock::iterator GetInsertPoint() const
Definition IRBuilder.h:202
Value * CreateIntToPtr(Value *V, Type *DestTy, const Twine &Name="")
Definition IRBuilder.h:2237
Value * CreateLShr(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
Definition IRBuilder.h:1554
IntegerType * getInt32Ty()
Fetch the type representing a 32-bit integer.
Definition IRBuilder.h:586
Value * CreatePtrAdd(Value *Ptr, Value *Offset, const Twine &Name="", GEPNoWrapFlags NW=GEPNoWrapFlags::none())
Definition IRBuilder.h:2091
BasicBlock * GetInsertBlock() const
Definition IRBuilder.h:201
IntegerType * getInt64Ty()
Fetch the type representing a 64-bit integer.
Definition IRBuilder.h:591
Value * CreateICmpNE(Value *LHS, Value *RHS, const Twine &Name="")
Definition IRBuilder.h:2378
Value * CreateGEP(Type *Ty, Value *Ptr, ArrayRef< Value * > IdxList, const Twine &Name="", GEPNoWrapFlags NW=GEPNoWrapFlags::none())
Definition IRBuilder.h:2010
PHINode * CreatePHI(Type *Ty, unsigned NumReservedValues, const Twine &Name="")
Definition IRBuilder.h:2539
Value * CreateNot(Value *V, const Twine &Name="")
Definition IRBuilder.h:1866
Value * CreateICmpEQ(Value *LHS, Value *RHS, const Twine &Name="")
Definition IRBuilder.h:2374
Value * CreateSub(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Definition IRBuilder.h:1461
ConstantInt * getIntN(unsigned N, uint64_t C)
Get a constant N-bit value, zero extended from a 64-bit value.
Definition IRBuilder.h:539
LoadInst * CreateLoad(Type *Ty, Value *Ptr, const char *Name)
Provided to resolve 'CreateLoad(Ty, Ptr, "...")' correctly, instead of converting the string to 'bool...
Definition IRBuilder.h:1918
Value * CreateAnd(Value *LHS, Value *RHS, const Twine &Name="")
Definition IRBuilder.h:1592
StoreInst * CreateStore(Value *Val, Value *Ptr, bool isVolatile=false)
Definition IRBuilder.h:1931
Value * CreateAdd(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Definition IRBuilder.h:1444
Value * CreatePtrToInt(Value *V, Type *DestTy, const Twine &Name="")
Definition IRBuilder.h:2232
Value * CreateIsNotNull(Value *Arg, const Twine &Name="")
Return a boolean value testing if Arg != 0.
Definition IRBuilder.h:2707
CallInst * CreateCall(FunctionType *FTy, Value *Callee, ArrayRef< Value * > Args={}, const Twine &Name="", MDNode *FPMathTag=nullptr)
Definition IRBuilder.h:2553
LLVM_ABI Value * CreateTypeSize(Type *Ty, TypeSize Size)
Create an expression which evaluates to the number of units in Size at runtime.
Value * CreateIntCast(Value *V, Type *DestTy, bool isSigned, const Twine &Name="")
Definition IRBuilder.h:2315
void SetInsertPoint(BasicBlock *TheBB)
This specifies that created instructions should be appended to the end of the specified block.
Definition IRBuilder.h:207
Type * getVoidTy()
Fetch the type representing void.
Definition IRBuilder.h:624
StoreInst * CreateAlignedStore(Value *Val, Value *Ptr, MaybeAlign Align, bool isVolatile=false)
Definition IRBuilder.h:1954
Value * CreateOr(Value *LHS, Value *RHS, const Twine &Name="", bool IsDisjoint=false)
Definition IRBuilder.h:1614
IntegerType * getInt8Ty()
Fetch the type representing an 8-bit integer.
Definition IRBuilder.h:576
Value * CreateAddrSpaceCast(Value *V, Type *DestTy, const Twine &Name="")
Definition IRBuilder.h:2247
Value * CreateMul(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Definition IRBuilder.h:1478
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
Definition IRBuilder.h:2858
static LLVM_ABI InlineAsm * get(FunctionType *Ty, StringRef AsmString, StringRef Constraints, bool hasSideEffects, bool isAlignStack=false, AsmDialect asmDialect=AD_ATT, bool canThrow=false)
InlineAsm::get - Return the specified uniqued inline asm string.
Definition InlineAsm.cpp:43
Base class for instruction visitors.
Definition InstVisitor.h:78
const DebugLoc & getDebugLoc() const
Return the debug location for this node as a DebugLoc.
bool hasMetadata() const
Return true if this instruction has any metadata attached to it.
LLVM_ABI void moveBefore(InstListType::iterator InsertPos)
Unlink this instruction from its current basic block and insert it into the basic block that MovePos ...
LLVM_ABI InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
MDNode * getMetadata(unsigned KindID) const
Get the metadata of given kind attached to this Instruction.
void setDebugLoc(DebugLoc Loc)
Set the debug location information for this instruction.
LLVM_ABI const DataLayout & getDataLayout() const
Get the data layout of the module this instruction belongs to.
static LLVM_ABI IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
Definition Type.cpp:354
A wrapper class for inspecting calls to intrinsic functions.
LLVM_ABI void emitError(const Instruction *I, const Twine &ErrorStr)
emitError - Emit an error message to the currently installed error handler with optional location inf...
An instruction for reading from memory.
static Error ParseSectionSpecifier(StringRef Spec, StringRef &Segment, StringRef &Section, unsigned &TAA, bool &TAAParsed, unsigned &StubSize)
Parse the section specifier indicated by "Spec".
LLVM_ABI MDNode * createUnlikelyBranchWeights()
Return metadata containing two branch weights, with significant bias towards false destination.
Definition MDBuilder.cpp:48
Metadata node.
Definition Metadata.h:1080
ArrayRef< MDOperand > operands() const
Definition Metadata.h:1442
static MDTuple * get(LLVMContext &Context, ArrayRef< Metadata * > MDs)
Definition Metadata.h:1572
Tuple of metadata.
Definition Metadata.h:1500
This is the common base class for memset/memcpy/memmove.
static MemoryEffectsBase argMemOnly(ModRefInfo MR=ModRefInfo::ModRef)
Definition ModRef.h:143
static MemoryEffectsBase otherMemOnly(ModRefInfo MR=ModRefInfo::ModRef)
Definition ModRef.h:159
Root of the metadata hierarchy.
Definition Metadata.h:64
A Module instance is used to store all the information related to an LLVM module.
Definition Module.h:67
Evaluate the size and offset of an object pointed to by a Value* statically.
LLVM_ABI SizeOffsetAPInt compute(Value *V)
Pass interface - Implemented by all 'passes'.
Definition Pass.h:99
static PointerType * getUnqual(Type *ElementType)
This constructs a pointer to an object of the specified type in the default address space (address sp...
static LLVM_ABI PointerType * get(Type *ElementType, unsigned AddressSpace)
This constructs a pointer to an object of the specified type in a numbered address space.
A set of analyses that are preserved following a run of a transformation pass.
Definition Analysis.h:112
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
Definition Analysis.h:115
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
Definition Analysis.h:118
PreservedAnalyses & abandon()
Mark an analysis as abandoned.
Definition Analysis.h:171
Return a value (possibly void), from a function.
static ReturnInst * Create(LLVMContext &C, Value *retVal=nullptr, InsertPosition InsertBefore=nullptr)
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
Definition SmallSet.h:134
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
reference emplace_back(ArgTypes &&... Args)
void reserve(size_type N)
void resize(size_type N)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
This pass performs the global (interprocedural) stack safety analysis (new pass manager).
bool stackAccessIsSafe(const Instruction &I) const
bool isSafe(const AllocaInst &AI) const
An instruction for storing to memory.
Represent a constant reference to a string, i.e.
Definition StringRef.h:56
bool starts_with(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition StringRef.h:258
constexpr bool empty() const
Check if the string is empty.
Definition StringRef.h:141
Class to represent struct types.
static LLVM_ABI StructType * get(LLVMContext &Context, ArrayRef< Type * > Elements, bool isPacked=false)
This static method is the primary way to create a literal StructType.
Definition Type.cpp:483
Analysis pass providing the TargetTransformInfo.
Analysis pass providing the TargetLibraryInfo.
Provides information about what library functions are available for the current target.
AttributeList getAttrList(LLVMContext *C, ArrayRef< unsigned > ArgNos, bool Signed, bool Ret=false, AttributeList AL=AttributeList()) const
This pass provides access to the codegen interfaces that are needed for IR-level transformations.
EltTy front() const
unsigned size() const
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:47
bool isThumb() const
Tests whether the target is Thumb (little and big endian).
Definition Triple.h:913
bool isDriverKit() const
Is this an Apple DriverKit triple.
Definition Triple.h:629
bool isBPF() const
Tests whether the target is eBPF.
Definition Triple.h:1151
bool isOSNetBSD() const
Definition Triple.h:666
bool isAndroid() const
Tests whether the target is Android.
Definition Triple.h:826
bool isABIN32() const
Definition Triple.h:1139
bool isMIPS64() const
Tests whether the target is MIPS 64-bit (little and big endian).
Definition Triple.h:1043
ArchType getArch() const
Get the parsed architecture type of this triple.
Definition Triple.h:436
bool isLoongArch64() const
Tests whether the target is 64-bit LoongArch.
Definition Triple.h:1032
bool isMIPS32() const
Tests whether the target is MIPS 32-bit (little and big endian).
Definition Triple.h:1038
bool isOSWindows() const
Tests whether the OS is Windows.
Definition Triple.h:699
@ UnknownObjectFormat
Definition Triple.h:332
bool isARM() const
Tests whether the target is ARM (little and big endian).
Definition Triple.h:918
bool isOSLinux() const
Tests whether the OS is Linux.
Definition Triple.h:746
bool isAMDGPU() const
Definition Triple.h:910
bool isMacOSX() const
Is this a Mac OS X triple.
Definition Triple.h:603
bool isOSFreeBSD() const
Definition Triple.h:670
bool isOSEmscripten() const
Tests whether the OS is Emscripten.
Definition Triple.h:761
bool isWatchOS() const
Is this an Apple watchOS triple.
Definition Triple.h:618
bool isiOS() const
Is this an iOS triple.
Definition Triple.h:612
bool isPS() const
Tests whether the target is the PS4 or PS5 platform.
Definition Triple.h:823
bool isWasm() const
Tests whether the target is wasm (32- and 64-bit).
Definition Triple.h:1125
bool isOSFuchsia() const
Definition Triple.h:672
bool isOSHaiku() const
Tests whether the OS is Haiku.
Definition Triple.h:693
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition Twine.h:82
The instances of the Type class are immutable: once they are created, they are never changed.
Definition Type.h:46
LLVM_ABI unsigned getIntegerBitWidth() const
static LLVM_ABI IntegerType * getInt32Ty(LLVMContext &C)
Definition Type.cpp:313
LLVM_ABI unsigned getPointerAddressSpace() const
Get the address space of this pointer or pointer vector type.
static LLVM_ABI Type * getVoidTy(LLVMContext &C)
Definition Type.cpp:286
static LLVM_ABI IntegerType * getInt8Ty(LLVMContext &C)
Definition Type.cpp:311
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
Definition Type.h:370
bool isSized(SmallPtrSetImpl< Type * > *Visited=nullptr) const
Return true if it makes sense to take the size of this type.
Definition Type.h:328
This function has undefined behavior.
A Use represents the edge between a Value definition and its users.
Definition Use.h:35
op_range operands()
Definition User.h:267
Value * getOperand(unsigned i) const
Definition User.h:207
static LLVM_ABI ValueAsMetadata * get(Value *V)
Definition Metadata.cpp:509
LLVM Value Representation.
Definition Value.h:75
Type * getType() const
All values are typed, get the type of this value.
Definition Value.h:255
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
Definition Value.cpp:549
iterator_range< user_iterator > users()
Definition Value.h:426
LLVM_ABI bool isSwiftError() const
Return true if this value is a swifterror value.
Definition Value.cpp:1126
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
Definition Value.cpp:318
LLVM_ABI void takeName(Value *V)
Transfer the name from V to this value.
Definition Value.cpp:399
Base class of all SIMD vector types.
static LLVM_ABI VectorType * get(Type *ElementType, ElementCount EC)
This static method is the primary way to construct an VectorType.
constexpr ScalarTy getFixedValue() const
Definition TypeSize.h:200
constexpr bool isScalable() const
Returns whether the quantity is scaled by a runtime quantity (vscale).
Definition TypeSize.h:168
An efficient, type-erasing, non-owning reference to a callable.
const ParentTy * getParent() const
Definition ilist_node.h:34
self_iterator getIterator()
Definition ilist_node.h:123
NodeTy * getNextNode()
Get the next node, or nullptr for the list tail.
Definition ilist_node.h:348
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition raw_ostream.h:53
CallInst * Call
Changed
This file contains the declaration of the Comdat class, which represents a single COMDAT in LLVM.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
void getInterestingMemoryOperands(Module &M, Instruction *I, SmallVectorImpl< InterestingMemoryOperand > &Interesting)
Get all the memory operands from the instruction that needs to be instrumented.
void instrumentAddress(Module &M, IRBuilder<> &IRB, Instruction *OrigIns, Instruction *InsertBefore, Value *Addr, Align Alignment, TypeSize TypeStoreSize, bool IsWrite, Value *SizeArgument, bool UseCalls, bool Recover, int AsanScale, int AsanOffset)
Instrument the memory operand Addr.
uint64_t getRedzoneSizeForGlobal(int AsanScale, uint64_t SizeInBytes)
Given SizeInBytes of the Value to be instrunmented, Returns the redzone size corresponding to it.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition CallingConv.h:24
@ C
The default llvm calling convention, compatible with C.
Definition CallingConv.h:34
@ BasicBlock
Various leaf nodes.
Definition ISDOpcodes.h:81
@ S_CSTRING_LITERALS
S_CSTRING_LITERALS - Section with literal C strings.
Definition MachO.h:131
@ OB
OB - OneByte - Set if this instruction has a one byte opcode.
ValuesClass values(OptsTy... Options)
Helper to build a ValuesClass by forwarding a variable number of arguments as an initializer list to ...
initializer< Ty > init(const Ty &Val)
cb< typename detail::callback_traits< F >::result_type, typename detail::callback_traits< F >::arg_type > callback(F CB)
uint64_t getAllocaSizeInBytes(const AllocaInst &AI)
Context & getContext() const
Definition BasicBlock.h:99
friend class Instruction
Iterator for Instructions in a `BasicBlock.
Definition BasicBlock.h:73
This is an optimization pass for GlobalISel generic memory operations.
LLVM_ABI void ReplaceInstWithInst(BasicBlock *BB, BasicBlock::iterator &BI, Instruction *I)
Replace the instruction specified by BI with the instruction specified by I.
@ Offset
Definition DWP.cpp:558
FunctionAddr VTableAddr Value
Definition InstrProf.h:137
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:1738
LLVM_ABI SmallVector< uint8_t, 64 > GetShadowBytesAfterScope(const SmallVectorImpl< ASanStackVariableDescription > &Vars, const ASanStackFrameLayout &Layout)
LLVM_ABI GlobalVariable * createPrivateGlobalForString(Module &M, StringRef Str, bool AllowMerging, Twine NamePrefix="")
LLVM_ABI AllocaInst * findAllocaForValue(Value *V, bool OffsetZero=false)
Returns unique alloca where the value comes from, or nullptr.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
@ Done
Definition Threading.h:60
FunctionAddr VTableAddr uintptr_t uintptr_t Int32Ty
Definition InstrProf.h:328
LLVM_ABI Function * createSanitizerCtor(Module &M, StringRef CtorName)
Creates sanitizer constructor function.
AsanDetectStackUseAfterReturnMode
Mode of ASan detect stack use after return.
@ Always
Always detect stack use after return.
@ Never
Never detect stack use after return.
@ Runtime
Detect stack use after return if not disabled runtime with (ASAN_OPTIONS=detect_stack_use_after_retur...
LLVM_ABI DenseMap< BasicBlock *, ColorVector > colorEHFunclets(Function &F)
If an EH funclet personality is in use (see isFuncletEHPersonality), this will recompute which blocks...
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
Definition STLExtras.h:633
InnerAnalysisManagerProxy< FunctionAnalysisManager, Module > FunctionAnalysisManagerModuleProxy
Provide the FunctionAnalysisManager to Module proxy.
Op::Description Desc
LLVM_ABI bool isAllocaPromotable(const AllocaInst *AI)
Return true if this alloca is legal for promotion.
LLVM_ABI SmallString< 64 > ComputeASanStackFrameDescription(const SmallVectorImpl< ASanStackVariableDescription > &Vars)
LLVM_ABI SmallVector< uint8_t, 64 > GetShadowBytes(const SmallVectorImpl< ASanStackVariableDescription > &Vars, const ASanStackFrameLayout &Layout)
int countr_zero(T Val)
Count number of 0's from the least significant bit to the most stopping at the first 1.
Definition bit.h:204
auto dyn_cast_or_null(const Y &Val)
Definition Casting.h:753
LLVM_ABI FunctionCallee declareSanitizerInitFunction(Module &M, StringRef InitName, ArrayRef< Type * > InitArgTypes, bool Weak=false)
FunctionAddr VTableAddr uintptr_t uintptr_t Version
Definition InstrProf.h:334
LLVM_ABI 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...
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
Definition MathExtras.h:279
LLVM_ABI std::pair< Function *, FunctionCallee > createSanitizerCtorAndInitFunctions(Module &M, StringRef CtorName, StringRef InitName, ArrayRef< Type * > InitArgTypes, ArrayRef< Value * > InitArgs, StringRef VersionCheckName=StringRef(), bool Weak=false)
Creates sanitizer constructor function, and calls sanitizer's init function from it.
decltype(auto) get(const PointerIntPair< PointerTy, IntBits, IntType, PtrTraits, Info > &Pair)
LLVM_ABI void SplitBlockAndInsertIfThenElse(Value *Cond, BasicBlock::iterator SplitBefore, Instruction **ThenTerm, Instruction **ElseTerm, MDNode *BranchWeights=nullptr, DomTreeUpdater *DTU=nullptr, LoopInfo *LI=nullptr)
SplitBlockAndInsertIfThenElse is similar to SplitBlockAndInsertIfThen, but also creates the ElseBlock...
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:209
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
bool isAlnum(char C)
Checks whether character C is either a decimal digit or an uppercase or lowercase letter as classifie...
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Definition Casting.h:547
AsanDtorKind
Types of ASan module destructors supported.
@ Invalid
Not a valid destructor Kind.
@ Global
Append to llvm.global_dtors.
@ None
Do not emit any destructors for ASan.
LLVM_ABI ASanStackFrameLayout ComputeASanStackFrameLayout(SmallVectorImpl< ASanStackVariableDescription > &Vars, uint64_t Granularity, uint64_t MinHeaderSize)
@ Ref
The access may reference the value stored in memory.
Definition ModRef.h:32
@ ModRef
The access may reference and may modify the value stored in memory.
Definition ModRef.h:36
@ Mod
The access may modify the value stored in memory.
Definition ModRef.h:34
@ ArgMem
Access to memory via argument pointers.
Definition ModRef.h:62
@ Other
Any other memory.
Definition ModRef.h:68
@ InaccessibleMem
Memory that is inaccessible via LLVM IR.
Definition ModRef.h:64
TargetTransformInfo TTI
void cantFail(Error Err, const char *Msg=nullptr)
Report a fatal error if Err is a failure value.
Definition Error.h:769
IRBuilder(LLVMContext &, FolderTy, InserterTy, MDNode *, ArrayRef< OperandBundleDef >) -> IRBuilder< FolderTy, InserterTy >
OperandBundleDefT< Value * > OperandBundleDef
Definition AutoUpgrade.h:34
LLVM_ABI void appendToCompilerUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.compiler.used list.
static const int kAsanStackUseAfterReturnMagic
LLVM_ABI void setGlobalVariableLargeSection(const Triple &TargetTriple, GlobalVariable &GV)
void removeASanIncompatibleFnAttributes(Function &F, bool ReadsArgMem)
Remove memory attributes that are incompatible with the instrumentation added by AddressSanitizer and...
@ Dynamic
Denotes mode unknown at compile time.
ArrayRef(const T &OneElt) -> ArrayRef< T >
bool isModAndRefSet(const ModRefInfo MRI)
Definition ModRef.h:46
LLVM_ABI 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.
TinyPtrVector< BasicBlock * > ColorVector
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
Align assumeAligned(uint64_t Value)
Treats the value 0 as a 1, so Align is always at least 1.
Definition Alignment.h:100
iterator_range< df_iterator< T > > depth_first(const T &G)
LLVM_ABI Instruction * SplitBlockAndInsertIfThen(Value *Cond, BasicBlock::iterator SplitBefore, bool Unreachable, MDNode *BranchWeights=nullptr, DomTreeUpdater *DTU=nullptr, LoopInfo *LI=nullptr, BasicBlock *ThenBlock=nullptr)
Split the containing block at the specified instruction - everything before SplitBefore stays in the ...
LLVM_ABI const Value * getUnderlyingObject(const Value *V, unsigned MaxLookup=MaxLookupSearchDepth)
This method strips off any GEP address adjustments, pointer casts or llvm.threadlocal....
AsanCtorKind
Types of ASan module constructors supported.
LLVM_ABI void maybeMarkSanitizerLibraryCallNoBuiltin(CallInst *CI, const TargetLibraryInfo *TLI)
Given a CallInst, check if it calls a string function known to CodeGen, and mark it with NoBuiltin if...
Definition Local.cpp:3915
LLVM_ABI void appendToUsed(Module &M, ArrayRef< GlobalValue * > Values)
Adds global values to the llvm.used list.
LLVM_ABI void appendToGlobalDtors(Module &M, Function *F, int Priority, Constant *Data=nullptr)
Same as appendToGlobalCtors(), but for global dtors.
LLVM_ABI bool checkIfAlreadyInstrumented(Module &M, StringRef Flag)
Check if module has flag attached, if not add the flag.
void getAddressSanitizerParams(const Triple &TargetTriple, int LongSize, bool IsKasan, uint64_t *ShadowBase, int *MappingScale, bool *OrShadowOffset)
DEMANGLE_ABI std::string demangle(std::string_view MangledName)
Attempt to demangle a string using different demangling schemes.
Definition Demangle.cpp:21
std::string itostr(int64_t X)
LLVM_ABI void SplitBlockAndInsertForEachLane(ElementCount EC, Type *IndexTy, BasicBlock::iterator InsertBefore, std::function< void(IRBuilderBase &, Value *)> Func)
Utility function for performing a given action on each lane of a vector with EC elements.
AnalysisManager< Module > ModuleAnalysisManager
Convenience typedef for the Module analysis manager.
Definition MIRParser.h:39
LLVM_ABI bool replaceDbgDeclare(Value *Address, Value *NewAddress, DIBuilder &Builder, uint8_t DIExprFlags, int Offset)
Replaces dbg.declare record when the address it describes is replaced with a new value.
Definition Local.cpp:1983
#define N
LLVM_ABI ASanAccessInfo(int32_t Packed)
const uint8_t AccessSizeIndex
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition Alignment.h:39
constexpr uint64_t value() const
This is a hole in the type system and should not be abused.
Definition Alignment.h:77
This struct is a compact representation of a valid (power of two) or undefined (0) alignment.
Definition Alignment.h:106
Align valueOrOne() const
For convenience, returns a valid alignment or 1 if undefined.
Definition Alignment.h:130
Information about a load/store intrinsic defined by the target.
SmallVector< InterestingMemoryOperand, 1 > InterestingOperands
A CRTP mix-in to automatically provide informational APIs needed for passes.
Definition PassManager.h:89
SizeOffsetAPInt - Used by ObjectSizeOffsetVisitor, which works with APInts.