10b57cec5SDimitry Andric //===-- asan_internal.h -----------------------------------------*- C++ -*-===// 20b57cec5SDimitry Andric // 30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 60b57cec5SDimitry Andric // 70b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 80b57cec5SDimitry Andric // 90b57cec5SDimitry Andric // This file is a part of AddressSanitizer, an address sanity checker. 100b57cec5SDimitry Andric // 110b57cec5SDimitry Andric // ASan-private header which defines various general utilities. 120b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 130b57cec5SDimitry Andric #ifndef ASAN_INTERNAL_H 140b57cec5SDimitry Andric #define ASAN_INTERNAL_H 150b57cec5SDimitry Andric 160b57cec5SDimitry Andric #include "asan_flags.h" 170b57cec5SDimitry Andric #include "asan_interface_internal.h" 180b57cec5SDimitry Andric #include "sanitizer_common/sanitizer_common.h" 190b57cec5SDimitry Andric #include "sanitizer_common/sanitizer_internal_defs.h" 200b57cec5SDimitry Andric #include "sanitizer_common/sanitizer_libc.h" 2181ad6265SDimitry Andric #include "sanitizer_common/sanitizer_stacktrace.h" 220b57cec5SDimitry Andric 230b57cec5SDimitry Andric #if __has_feature(address_sanitizer) || defined(__SANITIZE_ADDRESS__) 2481ad6265SDimitry Andric # error \ 2581ad6265SDimitry Andric "The AddressSanitizer run-time should not be instrumented by AddressSanitizer" 260b57cec5SDimitry Andric #endif 270b57cec5SDimitry Andric 280b57cec5SDimitry Andric // Build-time configuration options. 290b57cec5SDimitry Andric 300b57cec5SDimitry Andric // If set, asan will intercept C++ exception api call(s). 310b57cec5SDimitry Andric #ifndef ASAN_HAS_EXCEPTIONS 320b57cec5SDimitry Andric # define ASAN_HAS_EXCEPTIONS 1 330b57cec5SDimitry Andric #endif 340b57cec5SDimitry Andric 350b57cec5SDimitry Andric // If set, values like allocator chunk size, as well as defaults for some flags 360b57cec5SDimitry Andric // will be changed towards less memory overhead. 370b57cec5SDimitry Andric #ifndef ASAN_LOW_MEMORY 38fe6060f1SDimitry Andric # if SANITIZER_IOS || SANITIZER_ANDROID 390b57cec5SDimitry Andric # define ASAN_LOW_MEMORY 1 400b57cec5SDimitry Andric # else 410b57cec5SDimitry Andric # define ASAN_LOW_MEMORY 0 420b57cec5SDimitry Andric # endif 430b57cec5SDimitry Andric #endif 440b57cec5SDimitry Andric 450b57cec5SDimitry Andric #ifndef ASAN_DYNAMIC 460b57cec5SDimitry Andric # ifdef PIC 470b57cec5SDimitry Andric # define ASAN_DYNAMIC 1 480b57cec5SDimitry Andric # else 490b57cec5SDimitry Andric # define ASAN_DYNAMIC 0 500b57cec5SDimitry Andric # endif 510b57cec5SDimitry Andric #endif 520b57cec5SDimitry Andric 530b57cec5SDimitry Andric // All internal functions in asan reside inside the __asan namespace 540b57cec5SDimitry Andric // to avoid namespace collisions with the user programs. 550b57cec5SDimitry Andric // Separate namespace also makes it simpler to distinguish the asan run-time 560b57cec5SDimitry Andric // functions from the instrumented user code in a profile. 570b57cec5SDimitry Andric namespace __asan { 580b57cec5SDimitry Andric 590b57cec5SDimitry Andric class AsanThread; 600b57cec5SDimitry Andric using __sanitizer::StackTrace; 610b57cec5SDimitry Andric 620b57cec5SDimitry Andric void AsanInitFromRtl(); 63*5f757f3fSDimitry Andric bool TryAsanInitFromRtl(); 640b57cec5SDimitry Andric 6568d75effSDimitry Andric // asan_win.cpp 660b57cec5SDimitry Andric void InitializePlatformExceptionHandlers(); 670b57cec5SDimitry Andric // Returns whether an address is a valid allocated system heap block. 680b57cec5SDimitry Andric // 'addr' must point to the beginning of the block. 690b57cec5SDimitry Andric bool IsSystemHeapAddress(uptr addr); 700b57cec5SDimitry Andric 7168d75effSDimitry Andric // asan_rtl.cpp 720b57cec5SDimitry Andric void PrintAddressSpaceLayout(); 730b57cec5SDimitry Andric void NORETURN ShowStatsAndAbort(); 740b57cec5SDimitry Andric 7568d75effSDimitry Andric // asan_shadow_setup.cpp 760b57cec5SDimitry Andric void InitializeShadowMemory(); 770b57cec5SDimitry Andric 7868d75effSDimitry Andric // asan_malloc_linux.cpp / asan_malloc_mac.cpp 790b57cec5SDimitry Andric void ReplaceSystemMalloc(); 800b57cec5SDimitry Andric 81fe6060f1SDimitry Andric // asan_linux.cpp / asan_mac.cpp / asan_win.cpp 820b57cec5SDimitry Andric uptr FindDynamicShadowStart(); 830b57cec5SDimitry Andric void AsanCheckDynamicRTPrereqs(); 840b57cec5SDimitry Andric void AsanCheckIncompatibleRT(); 850b57cec5SDimitry Andric 865ffd83dbSDimitry Andric // Unpoisons platform-specific stacks. 875ffd83dbSDimitry Andric // Returns true if all stacks have been unpoisoned. 885ffd83dbSDimitry Andric bool PlatformUnpoisonStacks(); 895ffd83dbSDimitry Andric 905ffd83dbSDimitry Andric // asan_rtl.cpp 915ffd83dbSDimitry Andric // Unpoison a region containing a stack. 925ffd83dbSDimitry Andric // Performs a sanity check and warns if the bounds don't look right. 935ffd83dbSDimitry Andric // The warning contains the type string to identify the stack type. 945ffd83dbSDimitry Andric void UnpoisonStack(uptr bottom, uptr top, const char *type); 955ffd83dbSDimitry Andric 9668d75effSDimitry Andric // asan_thread.cpp 970b57cec5SDimitry Andric AsanThread *CreateMainThread(); 980b57cec5SDimitry Andric 990b57cec5SDimitry Andric // Support function for __asan_(un)register_image_globals. Searches for the 1000b57cec5SDimitry Andric // loaded image containing `needle' and then enumerates all global metadata 1010b57cec5SDimitry Andric // structures declared in that image, applying `op' (e.g., 1020b57cec5SDimitry Andric // __asan_(un)register_globals) to them. 1030b57cec5SDimitry Andric typedef void (*globals_op_fptr)(__asan_global *, uptr); 1040b57cec5SDimitry Andric void AsanApplyToGlobals(globals_op_fptr op, const void *needle); 1050b57cec5SDimitry Andric 1060b57cec5SDimitry Andric void AsanOnDeadlySignal(int, void *siginfo, void *context); 1070b57cec5SDimitry Andric 1089e7101a8SDimitry Andric void SignContextStack(void *context); 1090b57cec5SDimitry Andric void ReadContextStack(void *context, uptr *stack, uptr *ssize); 1100b57cec5SDimitry Andric void StopInitOrderChecking(); 1110b57cec5SDimitry Andric 1120b57cec5SDimitry Andric // Wrapper for TLS/TSD. 1130b57cec5SDimitry Andric void AsanTSDInit(void (*destructor)(void *tsd)); 1140b57cec5SDimitry Andric void *AsanTSDGet(); 1150b57cec5SDimitry Andric void AsanTSDSet(void *tsd); 1160b57cec5SDimitry Andric void PlatformTSDDtor(void *tsd); 1170b57cec5SDimitry Andric 1180b57cec5SDimitry Andric void AppendToErrorMessageBuffer(const char *buffer); 1190b57cec5SDimitry Andric 1200b57cec5SDimitry Andric void *AsanDlSymNext(const char *sym); 1210b57cec5SDimitry Andric 1220b57cec5SDimitry Andric // Returns `true` iff most of ASan init process should be skipped due to the 1230b57cec5SDimitry Andric // ASan library being loaded via `dlopen()`. Platforms may perform any 1240b57cec5SDimitry Andric // `dlopen()` specific initialization inside this function. 1250b57cec5SDimitry Andric bool HandleDlopenInit(); 1260b57cec5SDimitry Andric 12781ad6265SDimitry Andric void InstallAtExitCheckLeaks(); 128*5f757f3fSDimitry Andric void InstallAtForkHandler(); 12981ad6265SDimitry Andric 1300b57cec5SDimitry Andric #define ASAN_ON_ERROR() \ 13181ad6265SDimitry Andric if (&__asan_on_error) \ 13281ad6265SDimitry Andric __asan_on_error() 1330b57cec5SDimitry Andric 134*5f757f3fSDimitry Andric bool AsanInited(); 135bdd1243dSDimitry Andric extern bool replace_intrin_cached; 1360b57cec5SDimitry Andric extern void (*death_callback)(void); 13781ad6265SDimitry Andric // These magic values are written to shadow for better error 13881ad6265SDimitry Andric // reporting. 1390b57cec5SDimitry Andric const int kAsanHeapLeftRedzoneMagic = 0xfa; 1400b57cec5SDimitry Andric const int kAsanHeapFreeMagic = 0xfd; 1410b57cec5SDimitry Andric const int kAsanStackLeftRedzoneMagic = 0xf1; 1420b57cec5SDimitry Andric const int kAsanStackMidRedzoneMagic = 0xf2; 1430b57cec5SDimitry Andric const int kAsanStackRightRedzoneMagic = 0xf3; 1440b57cec5SDimitry Andric const int kAsanStackAfterReturnMagic = 0xf5; 1450b57cec5SDimitry Andric const int kAsanInitializationOrderMagic = 0xf6; 1460b57cec5SDimitry Andric const int kAsanUserPoisonedMemoryMagic = 0xf7; 1470b57cec5SDimitry Andric const int kAsanContiguousContainerOOBMagic = 0xfc; 1480b57cec5SDimitry Andric const int kAsanStackUseAfterScopeMagic = 0xf8; 1490b57cec5SDimitry Andric const int kAsanGlobalRedzoneMagic = 0xf9; 1500b57cec5SDimitry Andric const int kAsanInternalHeapMagic = 0xfe; 1510b57cec5SDimitry Andric const int kAsanArrayCookieMagic = 0xac; 1520b57cec5SDimitry Andric const int kAsanIntraObjectRedzone = 0xbb; 1530b57cec5SDimitry Andric const int kAsanAllocaLeftMagic = 0xca; 1540b57cec5SDimitry Andric const int kAsanAllocaRightMagic = 0xcb; 1550b57cec5SDimitry Andric 1560b57cec5SDimitry Andric static const uptr kCurrentStackFrameMagic = 0x41B58AB3; 1570b57cec5SDimitry Andric static const uptr kRetiredStackFrameMagic = 0x45E0360E; 1580b57cec5SDimitry Andric 1590b57cec5SDimitry Andric } // namespace __asan 1600b57cec5SDimitry Andric 1610b57cec5SDimitry Andric #endif // ASAN_INTERNAL_H 162