1 // Copyright (c) 2011-present, Facebook, Inc.  All rights reserved.
2 //  This source code is licensed under both the GPLv2 (found in the
3 //  COPYING file in the root directory) and Apache 2.0 License
4 //  (found in the LICENSE.Apache file in the root directory).
5 
6 #pragma once
7 
8 #ifndef FALLTHROUGH_INTENDED
9 #if defined(__clang__)
10 #define FALLTHROUGH_INTENDED [[clang::fallthrough]]
11 #elif defined(__GNUC__) && __GNUC__ >= 7
12 #define FALLTHROUGH_INTENDED [[gnu::fallthrough]]
13 #else
14 #define FALLTHROUGH_INTENDED do {} while (0)
15 #endif
16 #endif
17 
18 // ASAN (Address sanitizer)
19 
20 #if defined(__clang__)
21 #if defined(__has_feature)
22 #if __has_feature(address_sanitizer)
23 #define MUST_FREE_HEAP_ALLOCATIONS 1
24 #endif  // __has_feature(address_sanitizer)
25 #endif  // defined(__has_feature)
26 #else   // __clang__
27 #ifdef __SANITIZE_ADDRESS__
28 #define MUST_FREE_HEAP_ALLOCATIONS 1
29 #endif  // __SANITIZE_ADDRESS__
30 #endif  // __clang__
31 
32 #ifdef ROCKSDB_VALGRIND_RUN
33 #define MUST_FREE_HEAP_ALLOCATIONS 1
34 #endif  // ROCKSDB_VALGRIND_RUN
35 
36 // Coding guidelines say to avoid static objects with non-trivial destructors,
37 // because it's easy to cause trouble (UB) in static destruction. This
38 // macro makes it easier to define static objects that are normally never
39 // destructed, except are destructed when running under ASAN. This should
40 // avoid unexpected, unnecessary destruction behavior in production.
41 // Note that constructor arguments can be provided as in
42 //   STATIC_AVOID_DESTRUCTION(Foo, foo)(arg1, arg2);
43 #ifdef MUST_FREE_HEAP_ALLOCATIONS
44 #define STATIC_AVOID_DESTRUCTION(Type, name) static Type name
45 #else
46 #define STATIC_AVOID_DESTRUCTION(Type, name) static Type& name = *new Type
47 #endif
48 
49 // TSAN (Thread sanitizer)
50 
51 // For simplicity, standardize on the GCC define
52 #if defined(__clang__)
53 #if defined(__has_feature) && __has_feature(thread_sanitizer)
54 #define __SANITIZE_THREAD__ 1
55 #endif  // __has_feature(thread_sanitizer)
56 #endif  // __clang__
57 
58 #ifdef __SANITIZE_THREAD__
59 #define TSAN_SUPPRESSION __attribute__((no_sanitize("thread")))
60 #else
61 #define TSAN_SUPPRESSION
62 #endif  // TSAN_SUPPRESSION
63