1 /* 2 * Copyright (c) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef PANDA_LIBPANDABASE_MACROS_H_ 17 #define PANDA_LIBPANDABASE_MACROS_H_ 18 19 #include <cassert> 20 #include <iostream> 21 #include "os/stacktrace.h" 22 #include "utils/debug.h" 23 24 // Inline (disabled for DEBUG) 25 #ifndef NDEBUG 26 #define ALWAYS_INLINE // NOLINT(cppcoreguidelines-macro-usage) 27 #else // NDEBUG 28 #define ALWAYS_INLINE __attribute__((always_inline)) // NOLINT(cppcoreguidelines-macro-usage) 29 #endif // !NDEBUG 30 31 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 32 #define NO_INLINE __attribute__((noinline)) 33 34 #ifdef __clang__ 35 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 36 #define NO_OPTIMIZE [[clang::optnone]] 37 #else 38 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 39 #define NO_OPTIMIZE __attribute__((optimize("O0"))) 40 #endif 41 42 #ifdef __clang__ 43 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 44 #define FIELD_UNUSED __attribute__((__unused__)) 45 #else 46 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 47 #define FIELD_UNUSED 48 #endif 49 50 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 51 #define PANDA_PUBLIC_API __attribute__((visibility ("default"))) 52 53 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 54 #define MEMBER_OFFSET(T, F) offsetof(T, F) 55 56 #if defined(__cplusplus) 57 58 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 59 #define NO_COPY_CTOR(TypeName) \ 60 TypeName(const TypeName&) = delete; 61 62 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 63 #define NO_COPY_OPERATOR(TypeName) \ 64 void operator=(const TypeName&) = delete 65 66 // Disabling copy ctor and copy assignment operator. 67 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 68 #define NO_COPY_SEMANTIC(TypeName) \ 69 NO_COPY_CTOR(TypeName) \ 70 NO_COPY_OPERATOR(TypeName) 71 72 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 73 #define NO_MOVE_CTOR(TypeName) \ 74 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 75 TypeName(TypeName&&) = delete; 76 77 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 78 #define NO_MOVE_OPERATOR(TypeName) \ 79 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 80 TypeName& operator=(TypeName&&) = delete 81 82 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 83 #define NO_MOVE_SEMANTIC(TypeName) \ 84 NO_MOVE_CTOR(TypeName) \ 85 NO_MOVE_OPERATOR(TypeName) 86 87 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 88 #define DEFAULT_MOVE_CTOR(TypeName) \ 89 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 90 TypeName(TypeName&&) = default; 91 92 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 93 #define DEFAULT_MOVE_OPERATOR(TypeName) \ 94 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 95 TypeName& operator=(TypeName&&) = default 96 97 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 98 #define DEFAULT_MOVE_SEMANTIC(TypeName) \ 99 DEFAULT_MOVE_CTOR(TypeName) \ 100 DEFAULT_MOVE_OPERATOR(TypeName) 101 102 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 103 #define DEFAULT_COPY_CTOR(TypeName) \ 104 TypeName(const TypeName&) = default; \ 105 106 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 107 #define DEFAULT_COPY_OPERATOR(TypeName) \ 108 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 109 TypeName& operator=(const TypeName&) = default 110 111 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 112 #define DEFAULT_COPY_SEMANTIC(TypeName) \ 113 DEFAULT_COPY_CTOR(TypeName) \ 114 DEFAULT_COPY_OPERATOR(TypeName) 115 116 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 117 #define DEFAULT_NOEXCEPT_MOVE_CTOR(TypeName) \ 118 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 119 TypeName(TypeName&&) noexcept = default; 120 121 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 122 #define DEFAULT_NOEXCEPT_MOVE_OPERATOR(TypeName) \ 123 /* NOLINTNEXTLINE(misc-macro-parentheses) */ \ 124 TypeName& operator=(TypeName&&) noexcept = default 125 126 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 127 #define DEFAULT_NOEXCEPT_MOVE_SEMANTIC(TypeName) \ 128 DEFAULT_NOEXCEPT_MOVE_CTOR(TypeName) \ 129 DEFAULT_NOEXCEPT_MOVE_OPERATOR(TypeName) 130 131 #endif // defined(__cplusplus) 132 133 #define LIKELY(exp) (__builtin_expect((exp) != 0, true)) // NOLINT(cppcoreguidelines-macro-usage) 134 #define UNLIKELY(exp) (__builtin_expect((exp) != 0, false)) // NOLINT(cppcoreguidelines-macro-usage) 135 136 #if !defined(NDEBUG) 137 138 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 139 #define ASSERT_FAIL(expr) panda::debug::AssertionFail(expr, __FILE__, __LINE__, __FUNCTION__) 140 141 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 142 #define ASSERT_OP(lhs, op, rhs) do { \ 143 auto __lhs = lhs; \ 144 auto __rhs = rhs; \ 145 if (UNLIKELY(!(__lhs op __rhs))) { \ 146 std::cerr << "CHECK FAILED: " << #lhs << " " #op " " #rhs << std::endl; \ 147 std::cerr << " VALUES: " << __lhs << " " #op " " << __rhs << std::endl; \ 148 panda::PrintStack(std::cerr); \ 149 std::abort(); \ 150 } \ 151 } while (0) 152 153 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 154 #define CHECK_LE(lhs, rhs) ASSERT_OP(lhs, <=, rhs) 155 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 156 #define CHECK_LT(lhs, rhs) ASSERT_OP(lhs, <, rhs) // CODECHECK-NOLINT(C_RULE_ID_HORIZON_SPACE) 157 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 158 #define CHECK_GE(lhs, rhs) ASSERT_OP(lhs, >=, rhs) 159 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 160 #define CHECK_GT(lhs, rhs) ASSERT_OP(lhs, >, rhs) // CODECHECK-NOLINT(C_RULE_ID_HORIZON_SPACE) 161 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 162 #define CHECK_EQ(lhs, rhs) ASSERT_OP(lhs, ==, rhs) 163 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 164 #define CHECK_NE(lhs, rhs) ASSERT_OP(lhs, !=, rhs) 165 166 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 167 #define ASSERT(cond) \ 168 if (UNLIKELY(!(cond))) { \ 169 ASSERT_FAIL(#cond); \ 170 } 171 172 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 173 #define ASSERT_DO(cond, func) \ 174 if (auto cond_val = cond; UNLIKELY(!(cond_val))) { \ 175 func; \ 176 ASSERT_FAIL(#cond); \ 177 } 178 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 179 #define ASSERT_PRINT(cond, message) \ 180 if (auto cond_val = cond; UNLIKELY(!(cond_val))) { \ 181 std::cerr << message << std::endl; \ 182 ASSERT_FAIL(#cond); \ 183 } 184 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 185 #define ASSERT_RETURN(cond) assert(cond) 186 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 187 #define UNREACHABLE() \ 188 do { \ 189 ASSERT_PRINT(false, "This line should be unreachable"); /* NOLINT(misc-static-assert) */ \ 190 __builtin_unreachable(); \ 191 } while (0) 192 #else // NDEBUG 193 #define ASSERT(cond) static_cast<void>(0) // NOLINT(cppcoreguidelines-macro-usage) 194 #define ASSERT_DO(cond, func) static_cast<void>(0) // NOLINT(cppcoreguidelines-macro-usage) 195 #define ASSERT_PRINT(cond, message) static_cast<void>(0) // NOLINT(cppcoreguidelines-macro-usage) 196 #define ASSERT_RETURN(cond) static_cast<void>(cond) // NOLINT(cppcoreguidelines-macro-usage) 197 #define UNREACHABLE __builtin_unreachable // NOLINT(cppcoreguidelines-macro-usage) 198 #define ASSERT_OP(lhs, op, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 199 #define CHECK_LE(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 200 #define CHECK_LT(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 201 #define CHECK_GE(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 202 #define CHECK_GT(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 203 #define CHECK_EQ(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 204 #define CHECK_NE(lhs, rhs) // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 205 #endif // !NDEBUG 206 207 // Due to the impossibility of using asserts in constexpr methods 208 // we need an extra version of UNREACHABLE macro that can be used in such situations 209 #define UNREACHABLE_CONSTEXPR __builtin_unreachable // NOLINT(cppcoreguidelines-macro-usage) 210 211 #define MERGE_WORDS_X(A, B) A ## B // NOLINT(cppcoreguidelines-macro-usage) 212 #define MERGE_WORDS(A, B) MERGE_WORDS_X(A, B) // NOLINT(cppcoreguidelines-macro-usage) 213 214 #if defined(__has_feature) 215 # if __has_feature(thread_sanitizer) 216 #define NO_THREAD_SANITIZE __attribute__((no_sanitize("thread"))) // NOLINT(cppcoreguidelines-macro-usage) 217 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 218 #define TSAN_ANNOTATE_HAPPENS_BEFORE(addr) \ 219 AnnotateHappensBefore(__FILE__, __LINE__, (void*)(addr)) 220 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 221 #define TSAN_ANNOTATE_HAPPENS_AFTER(addr) \ 222 AnnotateHappensAfter(__FILE__, __LINE__, (void*)(addr)) 223 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 224 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 225 #define TSAN_ANNOTATE_IGNORE_WRITES_BEGIN() \ 226 AnnotateIgnoreWritesBegin(__FILE__, __LINE__) 227 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 228 #define TSAN_ANNOTATE_IGNORE_WRITES_END() \ 229 AnnotateIgnoreWritesEnd(__FILE__, __LINE__) 230 extern "C" void AnnotateHappensBefore(const char* f, int l, void* addr); 231 extern "C" void AnnotateHappensAfter(const char* f, int l, void* addr); 232 extern "C" void AnnotateIgnoreWritesBegin(const char* f, int l); 233 extern "C" void AnnotateIgnoreWritesEnd(const char* f, int l); 234 # else 235 #define NO_THREAD_SANITIZE 236 #define TSAN_ANNOTATE_HAPPENS_BEFORE(addr) 237 #define TSAN_ANNOTATE_HAPPENS_AFTER(addr) 238 #define TSAN_ANNOTATE_IGNORE_WRITES_BEGIN() 239 #define TSAN_ANNOTATE_IGNORE_WRITES_END() 240 # endif 241 #else 242 # ifdef __SANITIZE_THREAD__ 243 #define NO_THREAD_SANITIZE __attribute__((no_sanitize("thread"))) // NOLINT(cppcoreguidelines-macro-usage) 244 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 245 #define TSAN_ANNOTATE_HAPPENS_BEFORE(addr) \ 246 AnnotateHappensBefore(__FILE__, __LINE__, (void*)(addr)) 247 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 248 #define TSAN_ANNOTATE_HAPPENS_AFTER(addr) \ 249 AnnotateHappensAfter(__FILE__, __LINE__, (void*)(addr)) 250 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 251 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 252 #define TSAN_ANNOTATE_IGNORE_WRITES_BEGIN() \ 253 AnnotateIgnoreWritesBegin(__FILE__, __LINE__) 254 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 255 #define TSAN_ANNOTATE_IGNORE_WRITES_END() \ 256 AnnotateIgnoreWritesEnd(__FILE__, __LINE__) 257 extern "C" void AnnotateHappensBefore(const char* f, int l, void* addr); 258 extern "C" void AnnotateHappensAfter(const char* f, int l, void* addr); 259 extern "C" void AnnotateIgnoreWritesBegin(const char* f, int l); 260 extern "C" void AnnotateIgnoreWritesEnd(const char* f, int l); 261 # else 262 #define NO_THREAD_SANITIZE 263 #define TSAN_ANNOTATE_HAPPENS_BEFORE(addr) 264 #define TSAN_ANNOTATE_HAPPENS_AFTER(addr) 265 #define TSAN_ANNOTATE_IGNORE_WRITES_BEGIN() 266 #define TSAN_ANNOTATE_IGNORE_WRITES_END() 267 # endif 268 #endif 269 270 #if defined(__has_feature) 271 # if __has_feature(undefined_behavior_sanitizer) 272 #define NO_UB_SANITIZE __attribute__((no_sanitize("undefined"))) // NOLINT(cppcoreguidelines-macro-usage) 273 # else 274 #define NO_UB_SANITIZE 275 # endif 276 #else 277 # ifdef __SANITIZE_UNDEFINED__ 278 #define NO_UB_SANITIZE __attribute__((no_sanitize("undefined"))) // NOLINT(cppcoreguidelines-macro-usage) 279 # else 280 #define NO_UB_SANITIZE 281 # endif 282 #endif 283 284 #if defined(__has_feature) 285 # if __has_feature(address_sanitizer) 286 #define USE_ADDRESS_SANITIZER 287 # endif 288 #elif defined(__SANITIZE_ADDRESS__) 289 #define USE_ADDRESS_SANITIZER 290 #endif 291 292 #ifdef USE_ADDRESS_SANITIZER 293 #define NO_ADDRESS_SANITIZE __attribute__((no_sanitize("address"))) // NOLINT(cppcoreguidelines-macro-usage) 294 #else 295 #define NO_ADDRESS_SANITIZE 296 #endif // USE_ADDRESS_SANITIZER 297 298 #if defined(__has_include) 299 #if __has_include(<filesystem>) 300 #define USE_STD_FILESYSTEM 301 #endif 302 #endif 303 304 #endif // PANDA_LIBPANDABASE_MACROS_H_ 305