xref: /freebsd/contrib/llvm-project/compiler-rt/lib/asan/asan_internal.h (revision 68d75eff68281c1b445e3010bb975eae07aac225)
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_stacktrace.h"
210b57cec5SDimitry Andric #include "sanitizer_common/sanitizer_libc.h"
220b57cec5SDimitry Andric 
230b57cec5SDimitry Andric #if __has_feature(address_sanitizer) || defined(__SANITIZE_ADDRESS__)
240b57cec5SDimitry Andric # error "The AddressSanitizer run-time should not be"
250b57cec5SDimitry Andric         " 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
380b57cec5SDimitry Andric # if SANITIZER_IOS || SANITIZER_ANDROID || SANITIZER_RTEMS
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();
630b57cec5SDimitry Andric 
64*68d75effSDimitry Andric // asan_win.cpp
650b57cec5SDimitry Andric void InitializePlatformExceptionHandlers();
660b57cec5SDimitry Andric // Returns whether an address is a valid allocated system heap block.
670b57cec5SDimitry Andric // 'addr' must point to the beginning of the block.
680b57cec5SDimitry Andric bool IsSystemHeapAddress(uptr addr);
690b57cec5SDimitry Andric 
70*68d75effSDimitry Andric // asan_rtl.cpp
710b57cec5SDimitry Andric void PrintAddressSpaceLayout();
720b57cec5SDimitry Andric void NORETURN ShowStatsAndAbort();
730b57cec5SDimitry Andric 
74*68d75effSDimitry Andric // asan_shadow_setup.cpp
750b57cec5SDimitry Andric void InitializeShadowMemory();
760b57cec5SDimitry Andric 
77*68d75effSDimitry Andric // asan_malloc_linux.cpp / asan_malloc_mac.cpp
780b57cec5SDimitry Andric void ReplaceSystemMalloc();
790b57cec5SDimitry Andric 
80*68d75effSDimitry Andric // asan_linux.cpp / asan_mac.cpp / asan_rtems.cpp / asan_win.cpp
810b57cec5SDimitry Andric uptr FindDynamicShadowStart();
820b57cec5SDimitry Andric void *AsanDoesNotSupportStaticLinkage();
830b57cec5SDimitry Andric void AsanCheckDynamicRTPrereqs();
840b57cec5SDimitry Andric void AsanCheckIncompatibleRT();
850b57cec5SDimitry Andric 
86*68d75effSDimitry Andric // asan_thread.cpp
870b57cec5SDimitry Andric AsanThread *CreateMainThread();
880b57cec5SDimitry Andric 
890b57cec5SDimitry Andric // Support function for __asan_(un)register_image_globals. Searches for the
900b57cec5SDimitry Andric // loaded image containing `needle' and then enumerates all global metadata
910b57cec5SDimitry Andric // structures declared in that image, applying `op' (e.g.,
920b57cec5SDimitry Andric // __asan_(un)register_globals) to them.
930b57cec5SDimitry Andric typedef void (*globals_op_fptr)(__asan_global *, uptr);
940b57cec5SDimitry Andric void AsanApplyToGlobals(globals_op_fptr op, const void *needle);
950b57cec5SDimitry Andric 
960b57cec5SDimitry Andric void AsanOnDeadlySignal(int, void *siginfo, void *context);
970b57cec5SDimitry Andric 
980b57cec5SDimitry Andric void ReadContextStack(void *context, uptr *stack, uptr *ssize);
990b57cec5SDimitry Andric void StopInitOrderChecking();
1000b57cec5SDimitry Andric 
1010b57cec5SDimitry Andric // Wrapper for TLS/TSD.
1020b57cec5SDimitry Andric void AsanTSDInit(void (*destructor)(void *tsd));
1030b57cec5SDimitry Andric void *AsanTSDGet();
1040b57cec5SDimitry Andric void AsanTSDSet(void *tsd);
1050b57cec5SDimitry Andric void PlatformTSDDtor(void *tsd);
1060b57cec5SDimitry Andric 
1070b57cec5SDimitry Andric void AppendToErrorMessageBuffer(const char *buffer);
1080b57cec5SDimitry Andric 
1090b57cec5SDimitry Andric void *AsanDlSymNext(const char *sym);
1100b57cec5SDimitry Andric 
1110b57cec5SDimitry Andric void ReserveShadowMemoryRange(uptr beg, uptr end, const char *name);
1120b57cec5SDimitry Andric 
1130b57cec5SDimitry Andric // Returns `true` iff most of ASan init process should be skipped due to the
1140b57cec5SDimitry Andric // ASan library being loaded via `dlopen()`. Platforms may perform any
1150b57cec5SDimitry Andric // `dlopen()` specific initialization inside this function.
1160b57cec5SDimitry Andric bool HandleDlopenInit();
1170b57cec5SDimitry Andric 
1180b57cec5SDimitry Andric // Add convenient macro for interface functions that may be represented as
1190b57cec5SDimitry Andric // weak hooks.
1200b57cec5SDimitry Andric #define ASAN_MALLOC_HOOK(ptr, size)                                   \
1210b57cec5SDimitry Andric   do {                                                                \
1220b57cec5SDimitry Andric     if (&__sanitizer_malloc_hook) __sanitizer_malloc_hook(ptr, size); \
1230b57cec5SDimitry Andric     RunMallocHooks(ptr, size);                                        \
1240b57cec5SDimitry Andric   } while (false)
1250b57cec5SDimitry Andric #define ASAN_FREE_HOOK(ptr)                                 \
1260b57cec5SDimitry Andric   do {                                                      \
1270b57cec5SDimitry Andric     if (&__sanitizer_free_hook) __sanitizer_free_hook(ptr); \
1280b57cec5SDimitry Andric     RunFreeHooks(ptr);                                      \
1290b57cec5SDimitry Andric   } while (false)
1300b57cec5SDimitry Andric #define ASAN_ON_ERROR() \
1310b57cec5SDimitry Andric   if (&__asan_on_error) __asan_on_error()
1320b57cec5SDimitry Andric 
1330b57cec5SDimitry Andric extern int asan_inited;
1340b57cec5SDimitry Andric // Used to avoid infinite recursion in __asan_init().
1350b57cec5SDimitry Andric extern bool asan_init_is_running;
1360b57cec5SDimitry Andric extern void (*death_callback)(void);
1370b57cec5SDimitry Andric // These magic values are written to shadow for better error reporting.
1380b57cec5SDimitry Andric const int kAsanHeapLeftRedzoneMagic = 0xfa;
1390b57cec5SDimitry Andric const int kAsanHeapFreeMagic = 0xfd;
1400b57cec5SDimitry Andric const int kAsanStackLeftRedzoneMagic = 0xf1;
1410b57cec5SDimitry Andric const int kAsanStackMidRedzoneMagic = 0xf2;
1420b57cec5SDimitry Andric const int kAsanStackRightRedzoneMagic = 0xf3;
1430b57cec5SDimitry Andric const int kAsanStackAfterReturnMagic = 0xf5;
1440b57cec5SDimitry Andric const int kAsanInitializationOrderMagic = 0xf6;
1450b57cec5SDimitry Andric const int kAsanUserPoisonedMemoryMagic = 0xf7;
1460b57cec5SDimitry Andric const int kAsanContiguousContainerOOBMagic = 0xfc;
1470b57cec5SDimitry Andric const int kAsanStackUseAfterScopeMagic = 0xf8;
1480b57cec5SDimitry Andric const int kAsanGlobalRedzoneMagic = 0xf9;
1490b57cec5SDimitry Andric const int kAsanInternalHeapMagic = 0xfe;
1500b57cec5SDimitry Andric const int kAsanArrayCookieMagic = 0xac;
1510b57cec5SDimitry Andric const int kAsanIntraObjectRedzone = 0xbb;
1520b57cec5SDimitry Andric const int kAsanAllocaLeftMagic = 0xca;
1530b57cec5SDimitry Andric const int kAsanAllocaRightMagic = 0xcb;
1540b57cec5SDimitry Andric // Used to populate the shadow gap for systems without memory
1550b57cec5SDimitry Andric // protection there (i.e. Myriad).
1560b57cec5SDimitry Andric const int kAsanShadowGap = 0xcc;
1570b57cec5SDimitry Andric 
1580b57cec5SDimitry Andric static const uptr kCurrentStackFrameMagic = 0x41B58AB3;
1590b57cec5SDimitry Andric static const uptr kRetiredStackFrameMagic = 0x45E0360E;
1600b57cec5SDimitry Andric 
1610b57cec5SDimitry Andric }  // namespace __asan
1620b57cec5SDimitry Andric 
1630b57cec5SDimitry Andric #endif  // ASAN_INTERNAL_H
164