tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

notreached.h (4030B)


      1 // Copyright 2020 The Chromium Authors
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef BASE_NOTREACHED_H_
      6 #define BASE_NOTREACHED_H_
      7 
      8 #include "base/base_export.h"
      9 #include "base/check.h"
     10 #include "base/dcheck_is_on.h"
     11 #include "base/logging_buildflags.h"
     12 
     13 namespace logging {
     14 
     15 // NOTREACHED() annotates should-be unreachable code. Under the
     16 // kNotReachedIsFatal experiment all NOTREACHED()s that happen after FeatureList
     17 // initialization are fatal. As of 2023-06-06 this experiment is disabled
     18 // everywhere.
     19 //
     20 // For paths that are intended to eventually be NOTREACHED() but are not yet
     21 // ready for migration (stability risk, known pre-existing failures), consider
     22 // the DUMP_WILL_BE_NOTREACHED_NORETURN() macro below.
     23 //
     24 // Outside the kNotReachedIsFatal experiment behavior is as follows:
     25 //
     26 // On DCHECK builds NOTREACHED() match the fatality of DCHECKs. When DCHECKs are
     27 // non-FATAL a crash report will be generated for the first NOTREACHED() that
     28 // hits per process.
     29 //
     30 // Outside DCHECK builds NOTREACHED() will LOG(ERROR) and also upload a crash
     31 // report without crashing in order to weed out prevalent NOTREACHED()s in the
     32 // wild before always turning NOTREACHED()s FATAL.
     33 //
     34 // TODO(crbug.com/851128): Migrate NOTREACHED() callers to NOTREACHED_NORETURN()
     35 // which is [[noreturn]] and always FATAL. Once that's done, rename
     36 // NOTREACHED_NORETURN() back to NOTREACHED() and remove the non-FATAL version.
     37 // This migration will likely happen through the kNotReachedIsFatal experiment
     38 // for most code as we'll be able to avoid stability issues for pre-existing
     39 // failures.
     40 #if CHECK_WILL_STREAM() || BUILDFLAG(ENABLE_LOG_ERROR_NOT_REACHED)
     41 #define NOTREACHED() \
     42  LOGGING_CHECK_FUNCTION_IMPL(::logging::NotReachedError::NotReached(), false)
     43 #else
     44 #define NOTREACHED()                                       \
     45  (true) ? ::logging::NotReachedError::TriggerNotReached() \
     46         : EAT_CHECK_STREAM_PARAMS()
     47 #endif
     48 
     49 // NOTREACHED_NORETURN() annotates paths that are supposed to be unreachable.
     50 // They crash if they are ever hit.
     51 // TODO(crbug.com/851128): Rename back to NOTREACHED() once there are no callers
     52 // of the old non-CHECK-fatal macro.
     53 #if CHECK_WILL_STREAM()
     54 #define NOTREACHED_NORETURN() ::logging::NotReachedNoreturnError()
     55 #else
     56 // This function is used to be able to detect NOTREACHED() failures in stack
     57 // traces where this symbol is preserved (even if inlined). Its implementation
     58 // matches logging::CheckFailure() but intentionally uses a different signature.
     59 [[noreturn]] IMMEDIATE_CRASH_ALWAYS_INLINE void NotReachedFailure() {
     60  base::ImmediateCrash();
     61 }
     62 
     63 #define NOTREACHED_NORETURN() \
     64  (true) ? ::logging::NotReachedFailure() : EAT_CHECK_STREAM_PARAMS()
     65 #endif
     66 
     67 // The DUMP_WILL_BE_NOTREACHED_NORETURN() macro provides a convenient way to
     68 // non-fatally dump in official builds if ever hit. See DUMP_WILL_BE_CHECK for
     69 // suggested usage.
     70 #define DUMP_WILL_BE_NOTREACHED_NORETURN() \
     71  ::logging::CheckError::DumpWillBeNotReachedNoreturn()
     72 
     73 // The NOTIMPLEMENTED() macro annotates codepaths which have not been
     74 // implemented yet. If output spam is a serious concern,
     75 // NOTIMPLEMENTED_LOG_ONCE can be used.
     76 // Note that the NOTIMPLEMENTED_LOG_ONCE() macro does not allow custom error
     77 // messages to be appended to the macro to log, unlike NOTIMPLEMENTED() which
     78 // does support the pattern of appending a custom error message.  As in, the
     79 // NOTIMPLEMENTED_LOG_ONCE() << "foo message"; pattern is not supported.
     80 #if DCHECK_IS_ON()
     81 #define NOTIMPLEMENTED() \
     82  ::logging::CheckError::NotImplemented(__PRETTY_FUNCTION__)
     83 #else
     84 #define NOTIMPLEMENTED() EAT_CHECK_STREAM_PARAMS()
     85 #endif
     86 
     87 #define NOTIMPLEMENTED_LOG_ONCE()    \
     88  {                                  \
     89    static bool logged_once = false; \
     90    if (!logged_once) {              \
     91      NOTIMPLEMENTED();              \
     92      logged_once = true;            \
     93    }                                \
     94  }
     95 
     96 }  // namespace logging
     97 
     98 #endif  // BASE_NOTREACHED_H_