1 //===-- sanitizer_platform.h ------------------------------------*- C++ -*-===// 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 // Common platform macros. 10 //===----------------------------------------------------------------------===// 11 12 #ifndef SANITIZER_PLATFORM_H 13 #define SANITIZER_PLATFORM_H 14 15 #if !defined(__linux__) && !defined(__FreeBSD__) && !defined(__NetBSD__) && \ 16 !defined(__APPLE__) && !defined(_WIN32) && !defined(__Fuchsia__) && \ 17 !(defined(__sun__) && defined(__svr4__)) 18 # error "This operating system is not supported" 19 #endif 20 21 // Get __GLIBC__ on a glibc platform. Exclude Android: features.h includes C 22 // function declarations into a .S file which doesn't compile. 23 // https://crbug.com/1162741 24 #if __has_include(<features.h>) && !defined(__ANDROID__) 25 # include <features.h> 26 #endif 27 28 #if defined(__linux__) 29 # define SANITIZER_LINUX 1 30 #else 31 # define SANITIZER_LINUX 0 32 #endif 33 34 #if defined(__GLIBC__) 35 # define SANITIZER_GLIBC 1 36 #else 37 # define SANITIZER_GLIBC 0 38 #endif 39 40 #if defined(__FreeBSD__) 41 # define SANITIZER_FREEBSD 1 42 #else 43 # define SANITIZER_FREEBSD 0 44 #endif 45 46 #if defined(__NetBSD__) 47 # define SANITIZER_NETBSD 1 48 #else 49 # define SANITIZER_NETBSD 0 50 #endif 51 52 #if defined(__sun__) && defined(__svr4__) 53 # define SANITIZER_SOLARIS 1 54 #else 55 # define SANITIZER_SOLARIS 0 56 #endif 57 58 #if defined(__APPLE__) 59 # define SANITIZER_MAC 1 60 # include <TargetConditionals.h> 61 # if TARGET_OS_OSX 62 # define SANITIZER_OSX 1 63 # else 64 # define SANITIZER_OSX 0 65 # endif 66 # if TARGET_OS_IPHONE 67 # define SANITIZER_IOS 1 68 # else 69 # define SANITIZER_IOS 0 70 # endif 71 # if TARGET_OS_SIMULATOR 72 # define SANITIZER_IOSSIM 1 73 # else 74 # define SANITIZER_IOSSIM 0 75 # endif 76 #else 77 # define SANITIZER_MAC 0 78 # define SANITIZER_IOS 0 79 # define SANITIZER_IOSSIM 0 80 # define SANITIZER_OSX 0 81 #endif 82 83 #if defined(__APPLE__) && TARGET_OS_IPHONE && TARGET_OS_WATCH 84 # define SANITIZER_WATCHOS 1 85 #else 86 # define SANITIZER_WATCHOS 0 87 #endif 88 89 #if defined(__APPLE__) && TARGET_OS_IPHONE && TARGET_OS_TV 90 # define SANITIZER_TVOS 1 91 #else 92 # define SANITIZER_TVOS 0 93 #endif 94 95 #if defined(_WIN32) 96 # define SANITIZER_WINDOWS 1 97 #else 98 # define SANITIZER_WINDOWS 0 99 #endif 100 101 #if defined(_WIN64) 102 # define SANITIZER_WINDOWS64 1 103 #else 104 # define SANITIZER_WINDOWS64 0 105 #endif 106 107 #if defined(__ANDROID__) 108 # define SANITIZER_ANDROID 1 109 #else 110 # define SANITIZER_ANDROID 0 111 #endif 112 113 #if defined(__Fuchsia__) 114 # define SANITIZER_FUCHSIA 1 115 #else 116 # define SANITIZER_FUCHSIA 0 117 #endif 118 119 #define SANITIZER_POSIX \ 120 (SANITIZER_FREEBSD || SANITIZER_LINUX || SANITIZER_MAC || \ 121 SANITIZER_NETBSD || SANITIZER_SOLARIS) 122 123 #if __LP64__ || defined(_WIN64) 124 # define SANITIZER_WORDSIZE 64 125 #else 126 # define SANITIZER_WORDSIZE 32 127 #endif 128 129 #if SANITIZER_WORDSIZE == 64 130 # define FIRST_32_SECOND_64(a, b) (b) 131 #else 132 # define FIRST_32_SECOND_64(a, b) (a) 133 #endif 134 135 #if defined(__x86_64__) && !defined(_LP64) 136 # define SANITIZER_X32 1 137 #else 138 # define SANITIZER_X32 0 139 #endif 140 141 #if defined(__x86_64__) || defined(_M_X64) 142 # define SANITIZER_X64 1 143 #else 144 # define SANITIZER_X64 0 145 #endif 146 147 #if defined(__i386__) || defined(_M_IX86) 148 # define SANITIZER_I386 1 149 #else 150 # define SANITIZER_I386 0 151 #endif 152 153 #if defined(__mips__) 154 # define SANITIZER_MIPS 1 155 # if defined(__mips64) 156 # define SANITIZER_MIPS32 0 157 # define SANITIZER_MIPS64 1 158 # else 159 # define SANITIZER_MIPS32 1 160 # define SANITIZER_MIPS64 0 161 # endif 162 #else 163 # define SANITIZER_MIPS 0 164 # define SANITIZER_MIPS32 0 165 # define SANITIZER_MIPS64 0 166 #endif 167 168 #if defined(__s390__) 169 # define SANITIZER_S390 1 170 # if defined(__s390x__) 171 # define SANITIZER_S390_31 0 172 # define SANITIZER_S390_64 1 173 # else 174 # define SANITIZER_S390_31 1 175 # define SANITIZER_S390_64 0 176 # endif 177 #else 178 # define SANITIZER_S390 0 179 # define SANITIZER_S390_31 0 180 # define SANITIZER_S390_64 0 181 #endif 182 183 #if defined(__powerpc__) 184 # define SANITIZER_PPC 1 185 # if defined(__powerpc64__) 186 # define SANITIZER_PPC32 0 187 # define SANITIZER_PPC64 1 188 // 64-bit PPC has two ABIs (v1 and v2). The old powerpc64 target is 189 // big-endian, and uses v1 ABI (known for its function descriptors), 190 // while the new powerpc64le target is little-endian and uses v2. 191 // In theory, you could convince gcc to compile for their evil twins 192 // (eg. big-endian v2), but you won't find such combinations in the wild 193 // (it'd require bootstrapping a whole system, which would be quite painful 194 // - there's no target triple for that). LLVM doesn't support them either. 195 # if _CALL_ELF == 2 196 # define SANITIZER_PPC64V1 0 197 # define SANITIZER_PPC64V2 1 198 # else 199 # define SANITIZER_PPC64V1 1 200 # define SANITIZER_PPC64V2 0 201 # endif 202 # else 203 # define SANITIZER_PPC32 1 204 # define SANITIZER_PPC64 0 205 # define SANITIZER_PPC64V1 0 206 # define SANITIZER_PPC64V2 0 207 # endif 208 #else 209 # define SANITIZER_PPC 0 210 # define SANITIZER_PPC32 0 211 # define SANITIZER_PPC64 0 212 # define SANITIZER_PPC64V1 0 213 # define SANITIZER_PPC64V2 0 214 #endif 215 216 #if defined(__arm__) || defined(_M_ARM) 217 # define SANITIZER_ARM 1 218 #else 219 # define SANITIZER_ARM 0 220 #endif 221 222 #if defined(__aarch64__) || defined(_M_ARM64) 223 # define SANITIZER_ARM64 1 224 #else 225 # define SANITIZER_ARM64 0 226 #endif 227 228 #if SANITIZER_SOLARIS && SANITIZER_WORDSIZE == 32 229 # define SANITIZER_SOLARIS32 1 230 #else 231 # define SANITIZER_SOLARIS32 0 232 #endif 233 234 #if defined(__riscv) && (__riscv_xlen == 64) 235 # define SANITIZER_RISCV64 1 236 #else 237 # define SANITIZER_RISCV64 0 238 #endif 239 240 // By default we allow to use SizeClassAllocator64 on 64-bit platform. 241 // But in some cases (e.g. AArch64's 39-bit address space) SizeClassAllocator64 242 // does not work well and we need to fallback to SizeClassAllocator32. 243 // For such platforms build this code with -DSANITIZER_CAN_USE_ALLOCATOR64=0 or 244 // change the definition of SANITIZER_CAN_USE_ALLOCATOR64 here. 245 #ifndef SANITIZER_CAN_USE_ALLOCATOR64 246 # if (SANITIZER_ANDROID && defined(__aarch64__)) || SANITIZER_FUCHSIA 247 # define SANITIZER_CAN_USE_ALLOCATOR64 1 248 # elif defined(__mips64) || defined(__aarch64__) 249 # define SANITIZER_CAN_USE_ALLOCATOR64 0 250 # else 251 # define SANITIZER_CAN_USE_ALLOCATOR64 (SANITIZER_WORDSIZE == 64) 252 # endif 253 #endif 254 255 // The range of addresses which can be returned my mmap. 256 // FIXME: this value should be different on different platforms. Larger values 257 // will still work but will consume more memory for TwoLevelByteMap. 258 #if defined(__mips__) 259 # if SANITIZER_GO && defined(__mips64) 260 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 47) 261 # else 262 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 40) 263 # endif 264 #elif SANITIZER_RISCV64 265 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 38) 266 #elif defined(__aarch64__) 267 # if SANITIZER_MAC 268 # if SANITIZER_OSX || SANITIZER_IOSSIM 269 # define SANITIZER_MMAP_RANGE_SIZE \ 270 FIRST_32_SECOND_64(1ULL << 32, 1ULL << 47) 271 # else 272 // Darwin iOS/ARM64 has a 36-bit VMA, 64GiB VM 273 # define SANITIZER_MMAP_RANGE_SIZE \ 274 FIRST_32_SECOND_64(1ULL << 32, 1ULL << 36) 275 # endif 276 # else 277 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 48) 278 # endif 279 #elif defined(__sparc__) 280 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 52) 281 #else 282 # define SANITIZER_MMAP_RANGE_SIZE FIRST_32_SECOND_64(1ULL << 32, 1ULL << 47) 283 #endif 284 285 // Whether the addresses are sign-extended from the VMA range to the word. 286 // The SPARC64 Linux port implements this to split the VMA space into two 287 // non-contiguous halves with a huge hole in the middle. 288 #if defined(__sparc__) && SANITIZER_WORDSIZE == 64 289 # define SANITIZER_SIGN_EXTENDED_ADDRESSES 1 290 #else 291 # define SANITIZER_SIGN_EXTENDED_ADDRESSES 0 292 #endif 293 294 // The AArch64 and RISC-V linux ports use the canonical syscall set as 295 // mandated by the upstream linux community for all new ports. Other ports 296 // may still use legacy syscalls. 297 #ifndef SANITIZER_USES_CANONICAL_LINUX_SYSCALLS 298 # if (defined(__aarch64__) || defined(__riscv) || defined(__hexagon__)) && \ 299 SANITIZER_LINUX 300 # define SANITIZER_USES_CANONICAL_LINUX_SYSCALLS 1 301 # else 302 # define SANITIZER_USES_CANONICAL_LINUX_SYSCALLS 0 303 # endif 304 #endif 305 306 // udi16 syscalls can only be used when the following conditions are 307 // met: 308 // * target is one of arm32, x86-32, sparc32, sh or m68k 309 // * libc version is libc5, glibc-2.0, glibc-2.1 or glibc-2.2 to 2.15 310 // built against > linux-2.2 kernel headers 311 // Since we don't want to include libc headers here, we check the 312 // target only. 313 #if defined(__arm__) || SANITIZER_X32 || defined(__sparc__) 314 # define SANITIZER_USES_UID16_SYSCALLS 1 315 #else 316 # define SANITIZER_USES_UID16_SYSCALLS 0 317 #endif 318 319 #if defined(__mips__) 320 # define SANITIZER_POINTER_FORMAT_LENGTH FIRST_32_SECOND_64(8, 10) 321 #else 322 # define SANITIZER_POINTER_FORMAT_LENGTH FIRST_32_SECOND_64(8, 12) 323 #endif 324 325 /// \macro MSC_PREREQ 326 /// \brief Is the compiler MSVC of at least the specified version? 327 /// The common \param version values to check for are: 328 /// * 1800: Microsoft Visual Studio 2013 / 12.0 329 /// * 1900: Microsoft Visual Studio 2015 / 14.0 330 #ifdef _MSC_VER 331 # define MSC_PREREQ(version) (_MSC_VER >= (version)) 332 #else 333 # define MSC_PREREQ(version) 0 334 #endif 335 336 #if SANITIZER_MAC && !(defined(__arm64__) && SANITIZER_IOS) 337 # define SANITIZER_NON_UNIQUE_TYPEINFO 0 338 #else 339 # define SANITIZER_NON_UNIQUE_TYPEINFO 1 340 #endif 341 342 // On linux, some architectures had an ABI transition from 64-bit long double 343 // (ie. same as double) to 128-bit long double. On those, glibc symbols 344 // involving long doubles come in two versions, and we need to pass the 345 // correct one to dlvsym when intercepting them. 346 #if SANITIZER_LINUX && (SANITIZER_S390 || SANITIZER_PPC32 || SANITIZER_PPC64V1) 347 # define SANITIZER_NLDBL_VERSION "GLIBC_2.4" 348 #endif 349 350 #if SANITIZER_GO == 0 351 # define SANITIZER_GO 0 352 #endif 353 354 // On PowerPC and ARM Thumb, calling pthread_exit() causes LSan to detect leaks. 355 // pthread_exit() performs unwinding that leads to dlopen'ing libgcc_s.so. 356 // dlopen mallocs "libgcc_s.so" string which confuses LSan, it fails to realize 357 // that this allocation happens in dynamic linker and should be ignored. 358 #if SANITIZER_PPC || defined(__thumb__) 359 # define SANITIZER_SUPPRESS_LEAK_ON_PTHREAD_EXIT 1 360 #else 361 # define SANITIZER_SUPPRESS_LEAK_ON_PTHREAD_EXIT 0 362 #endif 363 364 #if SANITIZER_FREEBSD || SANITIZER_MAC || SANITIZER_NETBSD || SANITIZER_SOLARIS 365 # define SANITIZER_MADVISE_DONTNEED MADV_FREE 366 #else 367 # define SANITIZER_MADVISE_DONTNEED MADV_DONTNEED 368 #endif 369 370 // Older gcc have issues aligning to a constexpr, and require an integer. 371 // See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56859 among others. 372 #if defined(__powerpc__) || defined(__powerpc64__) 373 # define SANITIZER_CACHE_LINE_SIZE 128 374 #else 375 # define SANITIZER_CACHE_LINE_SIZE 64 376 #endif 377 378 // Enable offline markup symbolizer for Fuchsia. 379 #if SANITIZER_FUCHSIA 380 # define SANITIZER_SYMBOLIZER_MARKUP 1 381 #else 382 # define SANITIZER_SYMBOLIZER_MARKUP 0 383 #endif 384 385 // Enable ability to support sanitizer initialization that is 386 // compatible with the sanitizer library being loaded via 387 // `dlopen()`. 388 #if SANITIZER_MAC 389 # define SANITIZER_SUPPORTS_INIT_FOR_DLOPEN 1 390 #else 391 # define SANITIZER_SUPPORTS_INIT_FOR_DLOPEN 0 392 #endif 393 394 // SANITIZER_SUPPORTS_THREADLOCAL 395 // 1 - THREADLOCAL macro is supported by target 396 // 0 - THREADLOCAL macro is not supported by target 397 #ifndef __has_feature 398 // TODO: Support other compilers here 399 # define SANITIZER_SUPPORTS_THREADLOCAL 1 400 #else 401 # if __has_feature(tls) 402 # define SANITIZER_SUPPORTS_THREADLOCAL 1 403 # else 404 # define SANITIZER_SUPPORTS_THREADLOCAL 0 405 # endif 406 #endif 407 408 #if defined(__thumb__) && defined(__linux__) 409 // Workaround for 410 // https://lab.llvm.org/buildbot/#/builders/clang-thumbv7-full-2stage 411 // or 412 // https://lab.llvm.org/staging/#/builders/clang-thumbv7-full-2stage 413 // It fails *rss_limit_mb_test* without meaningful errors. 414 # define SANITIZER_START_BACKGROUND_THREAD_IN_ASAN_INTERNAL 1 415 #else 416 # define SANITIZER_START_BACKGROUND_THREAD_IN_ASAN_INTERNAL 0 417 #endif 418 419 #endif // SANITIZER_PLATFORM_H 420