_ZN11ArgsManagerD2Ev:
  130|      2|ArgsManager::~ArgsManager() = default;

_ZN15ChaCha20AlignedD2Ev:
   42|      4|{
   43|      4|    memory_cleanse(input, sizeof(input));
   44|      4|}
_ZN8ChaCha20D2Ev:
  332|      4|{
  333|      4|    memory_cleanse(m_buffer.data(), m_buffer.size());
  334|      4|}

_ZN9ChainCodeD2Ev:
   28|      2|    ~ChainCode() { memory_cleanse(data(), size()); }

_ZN11CNetCleanupD2Ev:
 3676|      2|    {
 3677|       |#ifdef WIN32
 3678|       |        // Shutdown Windows Sockets
 3679|       |        WSACleanup();
 3680|       |#endif
 3681|      2|    }

_ZNK9prevectorILj16EhjiE9is_directEv:
  126|     16|    bool is_direct() const { return _size <= N; }
_ZN9prevectorILj16EhjiED2Ev:
  422|     16|    ~prevector() {
  423|     16|        if (!is_direct()) {
  ------------------
  |  Branch (423:13): [True: 0, False: 16]
  ------------------
  424|      0|            free(_union.indirect_contents.indirect);
  425|      0|            _union.indirect_contents.indirect = nullptr;
  426|      0|        }
  427|     16|    }
_ZNK9prevectorILj36EhjiE9is_directEv:
  126|     14|    bool is_direct() const { return _size <= N; }
_ZN9prevectorILj36EhjiED2Ev:
  422|     14|    ~prevector() {
  423|     14|        if (!is_direct()) {
  ------------------
  |  Branch (423:13): [True: 0, False: 14]
  ------------------
  424|      0|            free(_union.indirect_contents.indirect);
  425|      0|            _union.indirect_contents.indirect = nullptr;
  426|      0|        }
  427|     14|    }

random.cpp:_ZN12_GLOBAL__N_18RNGStateD2Ev:
  367|      2|    ~RNGState() = default;

_ZN21InsecureRandomContextC2Em:
  439|  15.4k|        : m_s0(SplitMix64(seedval)), m_s1(SplitMix64(seedval)) {}
_ZN11RandomMixinI21InsecureRandomContextEC2Ev:
  195|  15.4k|    constexpr RandomMixin() noexcept = default;
_ZN21InsecureRandomContext10SplitMix64ERm:
  430|  30.8k|    {
  431|  30.8k|        uint64_t z = (seedval += 0x9e3779b97f4a7c15);
  432|  30.8k|        z = (z ^ (z >> 30)) * 0xbf58476d1ce4e5b9;
  433|  30.8k|        z = (z ^ (z >> 27)) * 0x94d049bb133111eb;
  434|  30.8k|        return z ^ (z >> 31);
  435|  30.8k|    }
_ZN21InsecureRandomContext6rand64Ev:
  449|   391k|    {
  450|   391k|        uint64_t s0 = m_s0, s1 = m_s1;
  451|   391k|        const uint64_t result = std::rotl(s0 + s1, 17) + s0;
  452|   391k|        s1 ^= s0;
  453|   391k|        m_s0 = std::rotl(s0, 49) ^ s1 ^ (s1 << 21);
  454|   391k|        m_s1 = std::rotl(s1, 28);
  455|   391k|        return result;
  456|   391k|    }

_ZN20BaseSignatureCheckerD2Ev:
  298|      2|    virtual ~BaseSignatureChecker() = default;

_ZN20BaseSignatureCreatorD2Ev:
   41|      4|    virtual ~BaseSignatureCreator() = default;

_ZN15SigningProviderD2Ev:
  170|      2|    virtual ~SigningProvider() = default;

random.cpp:_ZN16secure_allocatorIN12_GLOBAL__N_18RNGStateEE10deallocateEPS1_m:
   37|      2|    {
   38|      2|        if (p != nullptr) {
  ------------------
  |  Branch (38:13): [True: 2, False: 0]
  ------------------
   39|      2|            memory_cleanse(p, sizeof(T) * n);
   40|      2|        }
   41|      2|        LockedPoolManager::Instance().free(p);
   42|      2|    }

_Z14memory_cleansePvm:
   15|     14|{
   16|       |#if defined(WIN32)
   17|       |    /* SecureZeroMemory is guaranteed not to be optimized out. */
   18|       |    SecureZeroMemory(ptr, len);
   19|       |#else
   20|     14|    std::memset(ptr, 0, len);
   21|       |
   22|       |    /* Memory barrier that scares the compiler away from optimizing out the memset.
   23|       |     *
   24|       |     * Quoting Adam Langley <agl@google.com> in commit ad1907fe73334d6c696c8539646c21b11178f20f
   25|       |     * in BoringSSL (ISC License):
   26|       |     *    As best as we can tell, this is sufficient to break any optimisations that
   27|       |     *    might try to eliminate "superfluous" memsets.
   28|       |     * This method is used in memzero_explicit() the Linux kernel, too. Its advantage is that it
   29|       |     * is pretty efficient because the compiler can still implement the memset() efficiently,
   30|       |     * just not remove it entirely. See "Dead Store Elimination (Still) Considered Harmful" by
   31|       |     * Yang et al. (USENIX Security 2017) for more background.
   32|       |     */
   33|     14|    __asm__ __volatile__("" : : "r"(ptr) : "memory");
   34|     14|#endif
   35|     14|}

_ZN5ArenaD2Ev:
   48|      2|Arena::~Arena() = default;
_ZN5Arena4freeEPv:
   87|      2|{
   88|       |    // Freeing the nullptr pointer is OK.
   89|      2|    if (ptr == nullptr) {
  ------------------
  |  Branch (89:9): [True: 0, False: 2]
  ------------------
   90|      0|        return;
   91|      0|    }
   92|       |
   93|       |    // Remove chunk from used map
   94|      2|    auto i = chunks_used.find(ptr);
   95|      2|    if (i == chunks_used.end()) {
  ------------------
  |  Branch (95:9): [True: 0, False: 2]
  ------------------
   96|      0|        throw std::runtime_error("Arena: invalid or double free");
   97|      0|    }
   98|      2|    auto freed = std::make_pair(static_cast<char*>(i->first), i->second);
   99|      2|    chunks_used.erase(i);
  100|       |
  101|       |    // coalesce freed with previous chunk
  102|      2|    auto prev = chunks_free_end.find(freed.first);
  103|      2|    if (prev != chunks_free_end.end()) {
  ------------------
  |  Branch (103:9): [True: 2, False: 0]
  ------------------
  104|      2|        freed.first -= prev->second->first;
  105|      2|        freed.second += prev->second->first;
  106|      2|        size_to_free_chunk.erase(prev->second);
  107|      2|        chunks_free_end.erase(prev);
  108|      2|    }
  109|       |
  110|       |    // coalesce freed with chunk after freed
  111|      2|    auto next = chunks_free.find(freed.first + freed.second);
  112|      2|    if (next != chunks_free.end()) {
  ------------------
  |  Branch (112:9): [True: 0, False: 2]
  ------------------
  113|      0|        freed.second += next->second->first;
  114|      0|        size_to_free_chunk.erase(next->second);
  115|      0|        chunks_free.erase(next);
  116|      0|    }
  117|       |
  118|       |    // Add/set space with coalesced free chunk
  119|      2|    auto it = size_to_free_chunk.emplace(freed.second, freed.first);
  120|      2|    chunks_free[freed.first] = it;
  121|      2|    chunks_free_end[freed.first + freed.second] = it;
  122|      2|}
_ZN24PosixLockedPageAllocator10FreeLockedEPvm:
  254|      2|{
  255|      2|    len = align_up(len, page_size);
  256|      2|    memory_cleanse(addr, len);
  257|      2|    munlock(addr, len);
  258|      2|    munmap(addr, len);
  259|      2|}
_ZN10LockedPoolD2Ev:
  283|      2|LockedPool::~LockedPool() = default;
_ZN10LockedPool4freeEPv:
  308|      2|{
  309|      2|    std::lock_guard<std::mutex> lock(mutex);
  310|       |    // TODO we can do better than this linear search by keeping a map of arena
  311|       |    // extents to arena, and looking up the address.
  312|      2|    for (auto &arena: arenas) {
  ------------------
  |  Branch (312:21): [True: 2, False: 0]
  ------------------
  313|      2|        if (arena.addressInArena(ptr)) {
  ------------------
  |  Branch (313:13): [True: 2, False: 0]
  ------------------
  314|      2|            arena.free(ptr);
  315|      2|            return;
  316|      2|        }
  317|      2|    }
  318|      0|    throw std::runtime_error("LockedPool: invalid address not pointing to any arena");
  319|      2|}
_ZN10LockedPool15LockedPageArenaD2Ev:
  370|      2|{
  371|      2|    allocator->FreeLocked(base, size);
  372|      2|}
_ZN17LockedPoolManager8InstanceEv:
  405|      2|{
  406|      2|    static std::once_flag init_flag;
  407|      2|    std::call_once(init_flag, LockedPoolManager::CreateInstance);
  408|      2|    return *LockedPoolManager::_instance;
  409|      2|}
lockedpool.cpp:_ZL8align_upmm:
   32|      2|{
   33|      2|    return (x + align - 1) & ~(align - 1);
   34|      2|}

_ZNK5Arena14addressInArenaEPv:
   90|      2|    bool addressInArena(void *ptr) const { return ptr >= base && ptr < end; }
  ------------------
  |  Branch (90:51): [True: 2, False: 0]
  |  Branch (90:66): [True: 2, False: 0]
  ------------------
_ZN19LockedPageAllocatorD2Ev:
   22|      2|    virtual ~LockedPageAllocator() = default;

_ZN14AnnotatedMixinINSt3__115recursive_mutexEED2Ev:
   96|      2|    ~AnnotatedMixin() {
   97|      2|        DeleteLock((void*)this);
   98|      2|    }
_ZN14AnnotatedMixinINSt3__15mutexEED2Ev:
   96|     64|    ~AnnotatedMixin() {
   97|     64|        DeleteLock((void*)this);
   98|     64|    }
_Z10DeleteLockPv:
   74|     66|inline void DeleteLock(void* cs) {}
_Z17MaybeCheckNotHeldR14AnnotatedMixinINSt3__15mutexEE:
  258|     30|inline Mutex& MaybeCheckNotHeld(Mutex& cs) EXCLUSIVE_LOCKS_REQUIRED(!cs) LOCK_RETURNED(cs) { return cs; }
_ZN10UniqueLockI14AnnotatedMixinINSt3__15mutexEEEC2ERS3_PKcS7_ib:
  181|     30|    UniqueLock(MutexType& mutexIn, const char* pszName, const char* pszFile, int nLine, bool fTry = false) EXCLUSIVE_LOCK_FUNCTION(mutexIn) : Base(mutexIn, std::defer_lock)
  182|     30|    {
  183|     30|        if (fTry)
  ------------------
  |  Branch (183:13): [True: 0, False: 30]
  ------------------
  184|      0|            TryEnter(pszName, pszFile, nLine);
  185|     30|        else
  186|     30|            Enter(pszName, pszFile, nLine);
  187|     30|    }
_Z13EnterCriticalINSt3__15mutexEEvPKcS3_iPT_b:
   67|     30|inline void EnterCritical(const char* pszName, const char* pszFile, int nLine, MutexType* cs, bool fTry = false) {}
_Z13LeaveCriticalv:
   68|     30|inline void LeaveCritical() {}
_ZN10UniqueLockI14AnnotatedMixinINSt3__15mutexEEE5EnterEPKcS6_i:
  159|     30|    {
  160|     30|        EnterCritical(pszName, pszFile, nLine, Base::mutex());
  161|       |#ifdef DEBUG_LOCKCONTENTION
  162|       |        if (!Base::try_lock()) {
  163|       |            ContendedLock(pszName, pszFile, nLine, static_cast<Base&>(*this));
  164|       |        }
  165|       |#else
  166|     30|        Base::lock();
  167|     30|#endif
  168|     30|    }
_ZN10UniqueLockI14AnnotatedMixinINSt3__15mutexEEED2Ev:
  201|     30|    {
  202|     30|        if (Base::owns_lock())
  ------------------
  |  Branch (202:13): [True: 30, False: 0]
  ------------------
  203|     30|            LeaveCritical();
  204|     30|    }

_ZN18FuzzedDataProvider15ConsumeIntegralImEET_v:
  195|  15.4k|template <typename T> T FuzzedDataProvider::ConsumeIntegral() {
  196|  15.4k|  return ConsumeIntegralInRange(std::numeric_limits<T>::min(),
  197|  15.4k|                                std::numeric_limits<T>::max());
  198|  15.4k|}
_ZN18FuzzedDataProvider15remaining_bytesEv:
   85|  1.38M|  size_t remaining_bytes() { return remaining_bytes_; }
_ZN18FuzzedDataProviderC2EPKhm:
   37|  15.4k|      : data_ptr_(data), remaining_bytes_(size) {}
_ZN18FuzzedDataProvider15ConsumeIntegralIhEET_v:
  195|  1.36M|template <typename T> T FuzzedDataProvider::ConsumeIntegral() {
  196|  1.36M|  return ConsumeIntegralInRange(std::numeric_limits<T>::min(),
  197|  1.36M|                                std::numeric_limits<T>::max());
  198|  1.36M|}
_ZN18FuzzedDataProvider22ConsumeIntegralInRangeIhEET_S1_S1_:
  205|  1.36M|T FuzzedDataProvider::ConsumeIntegralInRange(T min, T max) {
  206|  1.36M|  static_assert(std::is_integral_v<T>, "An integral type is required.");
  207|  1.36M|  static_assert(sizeof(T) <= sizeof(uint64_t), "Unsupported integral type.");
  208|       |
  209|  1.36M|  if (min > max)
  ------------------
  |  Branch (209:7): [True: 0, False: 1.36M]
  ------------------
  210|      0|    abort();
  211|       |
  212|       |  // Use the biggest type possible to hold the range and the result.
  213|  1.36M|  uint64_t range = static_cast<uint64_t>(max) - static_cast<uint64_t>(min);
  214|  1.36M|  uint64_t result = 0;
  215|  1.36M|  size_t offset = 0;
  216|       |
  217|  2.73M|  while (offset < sizeof(T) * CHAR_BIT && (range >> offset) > 0 &&
  ------------------
  |  Branch (217:10): [True: 1.36M, False: 1.36M]
  |  Branch (217:43): [True: 1.36M, False: 0]
  ------------------
  218|  1.36M|         remaining_bytes_ != 0) {
  ------------------
  |  Branch (218:10): [True: 1.36M, False: 0]
  ------------------
  219|       |    // Pull bytes off the end of the seed data. Experimentally, this seems to
  220|       |    // allow the fuzzer to more easily explore the input space. This makes
  221|       |    // sense, since it works by modifying inputs that caused new code to run,
  222|       |    // and this data is often used to encode length of data read by
  223|       |    // |ConsumeBytes|. Separating out read lengths makes it easier modify the
  224|       |    // contents of the data that is actually read.
  225|  1.36M|    --remaining_bytes_;
  226|  1.36M|    result = (result << CHAR_BIT) | data_ptr_[remaining_bytes_];
  227|  1.36M|    offset += CHAR_BIT;
  228|  1.36M|  }
  229|       |
  230|       |  // Avoid division by 0, in case |range + 1| results in overflow.
  231|  1.36M|  if (range != std::numeric_limits<decltype(range)>::max())
  ------------------
  |  Branch (231:7): [True: 1.36M, False: 0]
  ------------------
  232|  1.36M|    result = result % (range + 1);
  233|       |
  234|  1.36M|  return static_cast<T>(static_cast<uint64_t>(min) + result);
  235|  1.36M|}
_ZN18FuzzedDataProvider22ConsumeIntegralInRangeImEET_S1_S1_:
  205|   329k|T FuzzedDataProvider::ConsumeIntegralInRange(T min, T max) {
  206|   329k|  static_assert(std::is_integral_v<T>, "An integral type is required.");
  207|   329k|  static_assert(sizeof(T) <= sizeof(uint64_t), "Unsupported integral type.");
  208|       |
  209|   329k|  if (min > max)
  ------------------
  |  Branch (209:7): [True: 0, False: 329k]
  ------------------
  210|      0|    abort();
  211|       |
  212|       |  // Use the biggest type possible to hold the range and the result.
  213|   329k|  uint64_t range = static_cast<uint64_t>(max) - static_cast<uint64_t>(min);
  214|   329k|  uint64_t result = 0;
  215|   329k|  size_t offset = 0;
  216|       |
  217|   757k|  while (offset < sizeof(T) * CHAR_BIT && (range >> offset) > 0 &&
  ------------------
  |  Branch (217:10): [True: 741k, False: 15.4k]
  |  Branch (217:43): [True: 428k, False: 313k]
  ------------------
  218|   428k|         remaining_bytes_ != 0) {
  ------------------
  |  Branch (218:10): [True: 427k, False: 910]
  ------------------
  219|       |    // Pull bytes off the end of the seed data. Experimentally, this seems to
  220|       |    // allow the fuzzer to more easily explore the input space. This makes
  221|       |    // sense, since it works by modifying inputs that caused new code to run,
  222|       |    // and this data is often used to encode length of data read by
  223|       |    // |ConsumeBytes|. Separating out read lengths makes it easier modify the
  224|       |    // contents of the data that is actually read.
  225|   427k|    --remaining_bytes_;
  226|   427k|    result = (result << CHAR_BIT) | data_ptr_[remaining_bytes_];
  227|   427k|    offset += CHAR_BIT;
  228|   427k|  }
  229|       |
  230|       |  // Avoid division by 0, in case |range + 1| results in overflow.
  231|   329k|  if (range != std::numeric_limits<decltype(range)>::max())
  ------------------
  |  Branch (231:7): [True: 314k, False: 15.4k]
  ------------------
  232|   314k|    result = result % (range + 1);
  233|       |
  234|   329k|  return static_cast<T>(static_cast<uint64_t>(min) + result);
  235|   329k|}
_ZN18FuzzedDataProvider22ConsumeIntegralInRangeIjEET_S1_S1_:
  205|  1.32M|T FuzzedDataProvider::ConsumeIntegralInRange(T min, T max) {
  206|  1.32M|  static_assert(std::is_integral_v<T>, "An integral type is required.");
  207|  1.32M|  static_assert(sizeof(T) <= sizeof(uint64_t), "Unsupported integral type.");
  208|       |
  209|  1.32M|  if (min > max)
  ------------------
  |  Branch (209:7): [True: 0, False: 1.32M]
  ------------------
  210|      0|    abort();
  211|       |
  212|       |  // Use the biggest type possible to hold the range and the result.
  213|  1.32M|  uint64_t range = static_cast<uint64_t>(max) - static_cast<uint64_t>(min);
  214|  1.32M|  uint64_t result = 0;
  215|  1.32M|  size_t offset = 0;
  216|       |
  217|  1.90M|  while (offset < sizeof(T) * CHAR_BIT && (range >> offset) > 0 &&
  ------------------
  |  Branch (217:10): [True: 1.90M, False: 0]
  |  Branch (217:43): [True: 576k, False: 1.32M]
  ------------------
  218|   576k|         remaining_bytes_ != 0) {
  ------------------
  |  Branch (218:10): [True: 572k, False: 4.02k]
  ------------------
  219|       |    // Pull bytes off the end of the seed data. Experimentally, this seems to
  220|       |    // allow the fuzzer to more easily explore the input space. This makes
  221|       |    // sense, since it works by modifying inputs that caused new code to run,
  222|       |    // and this data is often used to encode length of data read by
  223|       |    // |ConsumeBytes|. Separating out read lengths makes it easier modify the
  224|       |    // contents of the data that is actually read.
  225|   572k|    --remaining_bytes_;
  226|   572k|    result = (result << CHAR_BIT) | data_ptr_[remaining_bytes_];
  227|   572k|    offset += CHAR_BIT;
  228|   572k|  }
  229|       |
  230|       |  // Avoid division by 0, in case |range + 1| results in overflow.
  231|  1.32M|  if (range != std::numeric_limits<decltype(range)>::max())
  ------------------
  |  Branch (231:7): [True: 1.32M, False: 0]
  ------------------
  232|  1.32M|    result = result % (range + 1);
  233|       |
  234|  1.32M|  return static_cast<T>(static_cast<uint64_t>(min) + result);
  235|  1.32M|}

LLVMFuzzerTestOneInput:
  213|  2.20k|{
  214|  2.20k|    test_one_input({data, size});
  215|  2.20k|    return 0;
  216|  2.20k|}
fuzz.cpp:_ZL14test_one_inputNSt3__14spanIKhLm18446744073709551615EEE:
   84|  2.20k|{
   85|  2.20k|    CheckGlobals check{};
   86|  2.20k|    (*Assert(g_test_one_input))(buffer);
  ------------------
  |  |  116|  2.20k|#define Assert(val) inline_assertion_check<true>(val, std::source_location::current(), #val)
  ------------------
   87|  2.20k|}

_ZN12CheckGlobalsC2Ev:
   59|  2.20k|CheckGlobals::CheckGlobals() : m_impl(std::make_unique<CheckGlobalsImpl>()) {}
_ZN12CheckGlobalsD2Ev:
   60|  2.20k|CheckGlobals::~CheckGlobals() = default;
_ZN16CheckGlobalsImplC2Ev:
   17|  2.20k|    {
   18|  2.20k|        g_used_g_prng = false;
   19|  2.20k|        g_seeded_g_prng_zero = false;
   20|  2.20k|        g_used_system_time = false;
   21|  2.20k|        SetMockTime(0s);
   22|  2.20k|        MockableSteadyClock::ClearMockTime();
   23|  2.20k|    }
_ZN16CheckGlobalsImplD2Ev:
   25|  2.20k|    {
   26|  2.20k|        if (g_used_g_prng && !g_seeded_g_prng_zero) {
  ------------------
  |  Branch (26:13): [True: 0, False: 2.20k]
  |  Branch (26:30): [True: 0, False: 0]
  ------------------
   27|      0|            std::cerr << "\n\n"
   28|      0|                         "The current fuzz target used the global random state.\n\n"
   29|       |
   30|      0|                         "This is acceptable, but requires the fuzz target to call \n"
   31|      0|                         "SeedRandomStateForTest(SeedRand::ZEROS) in the first line \n"
   32|      0|                         "of the FUZZ_TARGET function.\n\n"
   33|       |
   34|      0|                         "An alternative solution would be to avoid any use of globals.\n\n"
   35|       |
   36|      0|                         "Without a solution, fuzz instability and non-determinism can lead \n"
   37|      0|                         "to non-reproducible bugs or inefficient fuzzing.\n\n"
   38|      0|                      << std::endl;
   39|      0|            std::abort(); // Abort, because AFL may try to recover from a std::exit
   40|      0|        }
   41|       |
   42|  2.20k|        if (g_used_system_time) {
  ------------------
  |  Branch (42:13): [True: 0, False: 2.20k]
  ------------------
   43|      0|            std::cerr << "\n\n"
   44|      0|                         "The current fuzz target accessed system time.\n\n"
   45|       |
   46|      0|                         "This is acceptable, but requires the fuzz target to use \n"
   47|      0|                         "a FakeNodeClock, FakeSteadyClock or call \n"
   48|      0|                         "SetMockTime() at the \n" "beginning of processing the \n"
   49|      0|                         "fuzz input.\n\n"
   50|       |
   51|      0|                         "Without setting mock time, time-dependent behavior can lead \n"
   52|      0|                         "to non-reproducible bugs or inefficient fuzzing.\n\n"
   53|      0|                      << std::endl;
   54|      0|            std::abort();
   55|      0|        }
   56|  2.20k|    }

_Z20vecdeque_fuzz_targetNSt3__14spanIKhLm18446744073709551615EEE:
  476|  2.20k|{
  477|       |    // Run the test with simple uints (which satisfy all the trivial properties).
  478|  2.20k|    static_assert(std::is_trivially_copyable_v<uint32_t>);
  479|  2.20k|    static_assert(std::is_trivially_destructible_v<uint64_t>);
  480|  2.20k|    TestType<uint8_t, false>(buffer, 1);
  481|  2.20k|    TestType<uint16_t, false>(buffer, 2);
  482|  2.20k|    TestType<uint32_t, false>(buffer, 3);
  483|  2.20k|    TestType<uint64_t, false>(buffer, 4);
  484|       |
  485|       |    // Run the test with TrackedObjs (which do not).
  486|  2.20k|    static_assert(!std::is_trivially_copyable_v<TrackedObj<3>>);
  487|  2.20k|    static_assert(!std::is_trivially_destructible_v<TrackedObj<17>>);
  488|  2.20k|    TestType<TrackedObj<1>, true>(buffer, 5);
  489|  2.20k|    TestType<TrackedObj<3>, true>(buffer, 6);
  490|  2.20k|    TestType<TrackedObj<17>, true>(buffer, 7);
  491|  2.20k|}
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeIhLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|       |    if constexpr (CheckNoneLeft) {
  341|       |        tmp = std::nullopt;
  342|       |        T::CheckNoneExist();
  343|       |    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeIhLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeIhERKNS1_5dequeIhNS1_9allocatorIhEEEEE_clES8_SE_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeItLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|       |    if constexpr (CheckNoneLeft) {
  341|       |        tmp = std::nullopt;
  342|       |        T::CheckNoneExist();
  343|       |    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeItLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeItERKNS1_5dequeItNS1_9allocatorItEEEEE_clES8_SE_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeIjLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|       |    if constexpr (CheckNoneLeft) {
  341|       |        tmp = std::nullopt;
  342|       |        T::CheckNoneExist();
  343|       |    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeIjLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeIjERKNS1_5dequeIjNS1_9allocatorIjEEEEE_clES8_SE_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeImLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|       |    if constexpr (CheckNoneLeft) {
  341|       |        tmp = std::nullopt;
  342|       |        T::CheckNoneExist();
  343|       |    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeImLb0EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeImERKNS1_5dequeImNS1_9allocatorImEEEEE_clES8_SE_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm1EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|  2.20k|    if constexpr (CheckNoneLeft) {
  341|  2.20k|        tmp = std::nullopt;
  342|  2.20k|        T::CheckNoneExist();
  343|  2.20k|    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm1EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeIS2_ERKNS3_5dequeIS2_NS3_9allocatorIS2_EEEEE_clESA_SG_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEC2EOS1_:
  431|   186k|    {
  432|   186k|        Register();
  433|   186k|        Deref() = other.Deref();
  434|   186k|        other.Deref() = std::nullopt;
  435|   186k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EE8RegisterEv:
  380|  1.08M|    {
  381|  1.08M|        auto [it, inserted] = g_tracker.emplace(this, std::nullopt);
  382|  1.08M|        assert(inserted);
  ------------------
  |  Branch (382:9): [True: 1.08M, False: 0]
  ------------------
  383|  2.16M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (383:28): [True: 1.08M, False: 1.08M]
  ------------------
  384|  1.08M|            m_track_entry[i] = it;
  385|  1.08M|        }
  386|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EE5DerefEv:
  400|  1.14M|    {
  401|  1.14M|        Check();
  402|  1.14M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (402:9): [True: 1.14M, False: 0]
  ------------------
  403|  1.14M|        return m_track_entry[0]->second;
  404|  1.14M|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm1EE5CheckEv:
  371|  5.13M|    {
  372|  5.13M|        auto it = g_tracker.find(this);
  373|  10.2M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (373:28): [True: 5.13M, False: 5.13M]
  ------------------
  374|       |            assert(m_track_entry[i] == it);
  ------------------
  |  Branch (374:13): [True: 5.13M, False: 0]
  ------------------
  375|  5.13M|        }
  376|  5.13M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEC2Ev:
  416|   527k|    TrackedObj() { Register(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEC2ERKS1_:
  425|   292k|    {
  426|   292k|        Register();
  427|   292k|        Deref() = other.Deref();
  428|   292k|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm1EE5DerefEv:
  408|  2.90M|    {
  409|  2.90M|        Check();
  410|  2.90M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (410:9): [True: 2.90M, False: 0]
  ------------------
  411|  2.90M|        return m_track_entry[0]->second;
  412|  2.90M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEC2Em:
  419|  76.6k|    {
  420|  76.6k|        Register();
  421|  76.6k|        Deref() = value;
  422|  76.6k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EED2Ev:
  415|  1.08M|    ~TrackedObj() { Deregister(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EE10DeregisterEv:
  389|  1.08M|    {
  390|  1.08M|        Check();
  391|  1.08M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (391:9): [True: 1.08M, False: 0]
  ------------------
  392|  1.08M|        g_tracker.erase(m_track_entry[0]);
  393|  2.16M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (393:28): [True: 1.08M, False: 1.08M]
  ------------------
  394|  1.08M|            m_track_entry[i] = g_tracker.end();
  395|  1.08M|        }
  396|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1eqERKNS_10TrackedObjILm1EEES3_:
  453|   735k|    {
  454|   735k|        return a.Deref() == b.Deref();
  455|   735k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEaSERKS1_:
  438|  98.4k|    {
  439|  98.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (439:13): [True: 0, False: 98.4k]
  ------------------
  440|  98.4k|        Deref() = other.Deref();
  441|  98.4k|        return *this;
  442|  98.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EEaSEOS1_:
  445|  39.4k|    {
  446|  39.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (446:13): [True: 0, False: 39.4k]
  ------------------
  447|  39.4k|        Deref() = other.Deref();
  448|  39.4k|        other.Deref() = std::nullopt;
  449|  39.4k|        return *this;
  450|  39.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1ssERKNS_10TrackedObjILm1EEES3_:
  458|   323k|    {
  459|       |        // Libc++ 15 & 16 do not support std::optional<T>::operator<=> yet. See
  460|       |        // https://reviews.llvm.org/D146392.
  461|   323k|        if (!a.Deref().has_value() || !b.Deref().has_value()) {
  ------------------
  |  Branch (461:13): [True: 251k, False: 72.1k]
  |  Branch (461:39): [True: 128, False: 72.0k]
  ------------------
  462|   251k|            return a.Deref().has_value() <=> b.Deref().has_value();
  463|   251k|        }
  464|  72.0k|        return *a.Deref() <=> *b.Deref();
  465|   323k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm1EE14CheckNoneExistEv:
  468|  2.20k|    {
  469|       |        assert(g_tracker.empty());
  ------------------
  |  Branch (469:9): [True: 2.20k, False: 0]
  ------------------
  470|  2.20k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm3EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|  2.20k|    if constexpr (CheckNoneLeft) {
  341|  2.20k|        tmp = std::nullopt;
  342|  2.20k|        T::CheckNoneExist();
  343|  2.20k|    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm3EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeIS2_ERKNS3_5dequeIS2_NS3_9allocatorIS2_EEEEE_clESA_SG_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEC2EOS1_:
  431|   186k|    {
  432|   186k|        Register();
  433|   186k|        Deref() = other.Deref();
  434|   186k|        other.Deref() = std::nullopt;
  435|   186k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EE8RegisterEv:
  380|  1.08M|    {
  381|  1.08M|        auto [it, inserted] = g_tracker.emplace(this, std::nullopt);
  382|  1.08M|        assert(inserted);
  ------------------
  |  Branch (382:9): [True: 1.08M, False: 0]
  ------------------
  383|  4.33M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (383:28): [True: 3.24M, False: 1.08M]
  ------------------
  384|  3.24M|            m_track_entry[i] = it;
  385|  3.24M|        }
  386|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EE5DerefEv:
  400|  1.14M|    {
  401|  1.14M|        Check();
  402|  1.14M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (402:9): [True: 1.14M, False: 0]
  ------------------
  403|  1.14M|        return m_track_entry[0]->second;
  404|  1.14M|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm3EE5CheckEv:
  371|  5.13M|    {
  372|  5.13M|        auto it = g_tracker.find(this);
  373|  20.5M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (373:28): [True: 15.3M, False: 5.13M]
  ------------------
  374|       |            assert(m_track_entry[i] == it);
  ------------------
  |  Branch (374:13): [True: 15.3M, False: 0]
  ------------------
  375|  15.3M|        }
  376|  5.13M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEC2Ev:
  416|   527k|    TrackedObj() { Register(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEC2ERKS1_:
  425|   292k|    {
  426|   292k|        Register();
  427|   292k|        Deref() = other.Deref();
  428|   292k|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm3EE5DerefEv:
  408|  2.90M|    {
  409|  2.90M|        Check();
  410|  2.90M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (410:9): [True: 2.90M, False: 0]
  ------------------
  411|  2.90M|        return m_track_entry[0]->second;
  412|  2.90M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEC2Em:
  419|  76.6k|    {
  420|  76.6k|        Register();
  421|  76.6k|        Deref() = value;
  422|  76.6k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EED2Ev:
  415|  1.08M|    ~TrackedObj() { Deregister(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EE10DeregisterEv:
  389|  1.08M|    {
  390|  1.08M|        Check();
  391|  1.08M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (391:9): [True: 1.08M, False: 0]
  ------------------
  392|  1.08M|        g_tracker.erase(m_track_entry[0]);
  393|  4.33M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (393:28): [True: 3.24M, False: 1.08M]
  ------------------
  394|  3.24M|            m_track_entry[i] = g_tracker.end();
  395|  3.24M|        }
  396|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1eqERKNS_10TrackedObjILm3EEES3_:
  453|   735k|    {
  454|   735k|        return a.Deref() == b.Deref();
  455|   735k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEaSERKS1_:
  438|  98.4k|    {
  439|  98.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (439:13): [True: 0, False: 98.4k]
  ------------------
  440|  98.4k|        Deref() = other.Deref();
  441|  98.4k|        return *this;
  442|  98.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EEaSEOS1_:
  445|  39.4k|    {
  446|  39.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (446:13): [True: 0, False: 39.4k]
  ------------------
  447|  39.4k|        Deref() = other.Deref();
  448|  39.4k|        other.Deref() = std::nullopt;
  449|  39.4k|        return *this;
  450|  39.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1ssERKNS_10TrackedObjILm3EEES3_:
  458|   323k|    {
  459|       |        // Libc++ 15 & 16 do not support std::optional<T>::operator<=> yet. See
  460|       |        // https://reviews.llvm.org/D146392.
  461|   323k|        if (!a.Deref().has_value() || !b.Deref().has_value()) {
  ------------------
  |  Branch (461:13): [True: 251k, False: 72.1k]
  |  Branch (461:39): [True: 128, False: 72.0k]
  ------------------
  462|   251k|            return a.Deref().has_value() <=> b.Deref().has_value();
  463|   251k|        }
  464|  72.0k|        return *a.Deref() <=> *b.Deref();
  465|   323k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm3EE14CheckNoneExistEv:
  468|  2.20k|    {
  469|       |        assert(g_tracker.empty());
  ------------------
  |  Branch (469:9): [True: 2.20k, False: 0]
  ------------------
  470|  2.20k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm17EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEm:
   28|  2.20k|{
   29|  2.20k|    FuzzedDataProvider provider(buffer.data(), buffer.size());
   30|       |    // Local RNG, only used for the seeds to initialize T objects with.
   31|  2.20k|    InsecureRandomContext rng(provider.ConsumeIntegral<uint64_t>() ^ rng_tweak);
   32|       |
   33|       |    // Real circular buffers.
   34|  2.20k|    std::vector<VecDeque<T>> real;
   35|  2.20k|    real.reserve(MAX_BUFFERS);
   36|       |    // Simulated circular buffers.
   37|  2.20k|    std::vector<std::deque<T>> sim;
   38|  2.20k|    sim.reserve(MAX_BUFFERS);
   39|       |    // Temporary object of type T.
   40|  2.20k|    std::optional<T> tmp;
   41|       |
   42|       |    // Compare a real and a simulated buffer.
   43|  2.20k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  2.20k|        assert(r.size() == s.size());
   45|  2.20k|        assert(r.empty() == s.empty());
   46|  2.20k|        assert(r.capacity() >= r.size());
   47|  2.20k|        if (s.size() == 0) return;
   48|  2.20k|        assert(r.front() == s.front());
   49|  2.20k|        assert(r.back() == s.back());
   50|  2.20k|        for (size_t i = 0; i < s.size(); ++i) {
   51|  2.20k|            assert(r[i] == s[i]);
   52|  2.20k|        }
   53|  2.20k|    };
   54|       |
   55|   195k|    LIMITED_WHILE (provider.remaining_bytes(), MAX_OPERATIONS) {
  ------------------
  |  |   23|   197k|    for (unsigned _count{limit}; (condition) && _count; --_count)
  |  |  ------------------
  |  |  |  Branch (23:34): [True: 195k, False: 2.13k]
  |  |  |  Branch (23:49): [True: 195k, False: 69]
  |  |  ------------------
  ------------------
   56|   195k|        int command = provider.ConsumeIntegral<uint8_t>() % 64;
   57|   195k|        unsigned idx = real.empty() ? 0 : provider.ConsumeIntegralInRange<unsigned>(0, real.size() - 1);
  ------------------
  |  Branch (57:24): [True: 5.91k, False: 189k]
  ------------------
   58|   195k|        const size_t num_buffers = sim.size();
   59|       |        // Pick one operation based on value of command. Not all operations are always applicable.
   60|       |        // Loop through the applicable ones until command reaches 0 (which avoids the need to
   61|       |        // compute the number of applicable commands ahead of time).
   62|   195k|        const bool non_empty{num_buffers != 0};
   63|   195k|        const bool non_full{num_buffers < MAX_BUFFERS};
   64|   195k|        const bool partially_full{non_empty && non_full};
  ------------------
  |  Branch (64:35): [True: 189k, False: 5.91k]
  |  Branch (64:48): [True: 136k, False: 52.8k]
  ------------------
   65|   195k|        const bool multiple_exist{num_buffers > 1};
   66|   195k|        const bool existing_buffer_non_full{non_empty && sim[idx].size() < MAX_BUFFER_SIZE};
  ------------------
  |  Branch (66:45): [True: 189k, False: 5.91k]
  |  Branch (66:58): [True: 184k, False: 5.32k]
  ------------------
   67|   195k|        const bool existing_buffer_non_empty{non_empty && !sim[idx].empty()};
  ------------------
  |  Branch (67:46): [True: 189k, False: 5.91k]
  |  Branch (67:59): [True: 139k, False: 50.5k]
  ------------------
   68|   195k|        assert(non_full || non_empty);
  ------------------
  |  Branch (68:9): [True: 142k, False: 52.8k]
  |  Branch (68:9): [True: 52.8k, False: 0]
  |  Branch (68:9): [True: 195k, False: 0]
  ------------------
   69|   540k|        while (true) {
  ------------------
  |  Branch (69:16): [True: 540k, Folded]
  ------------------
   70|   540k|            if (non_full && command-- == 0) {
  ------------------
  |  Branch (70:17): [True: 437k, False: 102k]
  |  Branch (70:29): [True: 7.16k, False: 430k]
  ------------------
   71|       |                /* Default construct. */
   72|  7.16k|                real.emplace_back();
   73|  7.16k|                sim.emplace_back();
   74|  7.16k|                break;
   75|  7.16k|            }
   76|   533k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (76:17): [True: 342k, False: 190k]
  |  Branch (76:30): [True: 26.7k, False: 315k]
  ------------------
   77|       |                /* resize() */
   78|  26.7k|                compare_fn(real[idx], sim[idx]);
   79|  26.7k|                size_t new_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
   80|  26.7k|                real[idx].resize(new_size);
   81|  26.7k|                sim[idx].resize(new_size);
   82|  26.7k|                assert(real[idx].size() == new_size);
  ------------------
  |  Branch (82:17): [True: 26.7k, False: 0]
  ------------------
   83|  26.7k|                break;
   84|  26.7k|            }
   85|   506k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (85:17): [True: 315k, False: 190k]
  |  Branch (85:30): [True: 7.14k, False: 308k]
  ------------------
   86|       |                /* clear() */
   87|  7.14k|                compare_fn(real[idx], sim[idx]);
   88|  7.14k|                real[idx].clear();
   89|  7.14k|                sim[idx].clear();
   90|  7.14k|                assert(real[idx].empty());
  ------------------
  |  Branch (90:17): [True: 7.14k, False: 0]
  ------------------
   91|  7.14k|                break;
   92|  7.14k|            }
   93|   499k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (93:17): [True: 308k, False: 190k]
  |  Branch (93:30): [True: 5.95k, False: 302k]
  ------------------
   94|       |                /* Copy construct default. */
   95|  5.95k|                compare_fn(real[idx], sim[idx]);
   96|  5.95k|                real[idx] = VecDeque<T>();
   97|  5.95k|                sim[idx].clear();
   98|  5.95k|                assert(real[idx].size() == 0);
  ------------------
  |  Branch (98:17): [True: 5.95k, False: 0]
  ------------------
   99|  5.95k|                break;
  100|  5.95k|            }
  101|   493k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (101:17): [True: 302k, False: 190k]
  |  Branch (101:30): [True: 6.72k, False: 295k]
  ------------------
  102|       |                /* Destruct. */
  103|  6.72k|                compare_fn(real.back(), sim.back());
  104|  6.72k|                real.pop_back();
  105|  6.72k|                sim.pop_back();
  106|  6.72k|                break;
  107|  6.72k|            }
  108|   486k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (108:17): [True: 213k, False: 272k]
  |  Branch (108:35): [True: 1.12k, False: 212k]
  ------------------
  109|       |                /* Copy construct. */
  110|  1.12k|                real.emplace_back(real[idx]);
  111|  1.12k|                sim.emplace_back(sim[idx]);
  112|  1.12k|                break;
  113|  1.12k|            }
  114|   485k|            if (partially_full && command-- == 0) {
  ------------------
  |  Branch (114:17): [True: 212k, False: 272k]
  |  Branch (114:35): [True: 1.80k, False: 211k]
  ------------------
  115|       |                /* Move construct. */
  116|  1.80k|                VecDeque<T> copy(real[idx]);
  117|  1.80k|                real.emplace_back(std::move(copy));
  118|  1.80k|                sim.emplace_back(sim[idx]);
  119|  1.80k|                break;
  120|  1.80k|            }
  121|   483k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (121:17): [True: 133k, False: 350k]
  |  Branch (121:35): [True: 2.59k, False: 130k]
  ------------------
  122|       |                /* swap() */
  123|  2.59k|                swap(real[idx], real[(idx + 1) % num_buffers]);
  124|  2.59k|                swap(sim[idx], sim[(idx + 1) % num_buffers]);
  125|  2.59k|                break;
  126|  2.59k|            }
  127|   481k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (127:17): [True: 130k, False: 350k]
  |  Branch (127:35): [True: 3.60k, False: 126k]
  ------------------
  128|       |                /* Copy assign. */
  129|  3.60k|                compare_fn(real[idx], sim[idx]);
  130|  3.60k|                real[idx] = real[(idx + 1) % num_buffers];
  131|  3.60k|                sim[idx] = sim[(idx + 1) % num_buffers];
  132|  3.60k|                break;
  133|  3.60k|            }
  134|   477k|            if (multiple_exist && command-- == 0) {
  ------------------
  |  Branch (134:17): [True: 126k, False: 350k]
  |  Branch (134:35): [True: 6.83k, False: 120k]
  ------------------
  135|       |                /* Move assign. */
  136|  6.83k|                VecDeque<T> copy(real[(idx + 1) % num_buffers]);
  137|  6.83k|                compare_fn(real[idx], sim[idx]);
  138|  6.83k|                real[idx] = std::move(copy);
  139|  6.83k|                sim[idx] = sim[(idx + 1) % num_buffers];
  140|  6.83k|                break;
  141|  6.83k|            }
  142|   470k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (142:17): [True: 280k, False: 190k]
  |  Branch (142:30): [True: 4.20k, False: 275k]
  ------------------
  143|       |                /* Self swap() */
  144|  4.20k|                swap(real[idx], real[idx]);
  145|  4.20k|                break;
  146|  4.20k|            }
  147|   466k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (147:17): [True: 275k, False: 190k]
  |  Branch (147:30): [True: 2.62k, False: 273k]
  ------------------
  148|       |                /* Self-copy assign. */
  149|  2.62k|                real[idx] = real[idx];
  150|  2.62k|                break;
  151|  2.62k|            }
  152|   463k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (152:17): [True: 273k, False: 190k]
  |  Branch (152:30): [True: 5.48k, False: 267k]
  ------------------
  153|       |                /* Self-move assign. */
  154|       |                // Do not use std::move(real[idx]) here: -Wself-move correctly warns about that.
  155|  5.48k|                real[idx] = static_cast<VecDeque<T>&&>(real[idx]);
  156|  5.48k|                break;
  157|  5.48k|            }
  158|   458k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (158:17): [True: 267k, False: 190k]
  |  Branch (158:30): [True: 14.0k, False: 253k]
  ------------------
  159|       |                /* reserve() */
  160|  14.0k|                size_t res_size = provider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
  161|  14.0k|                size_t old_cap = real[idx].capacity();
  162|  14.0k|                size_t old_size = real[idx].size();
  163|  14.0k|                real[idx].reserve(res_size);
  164|  14.0k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (164:17): [True: 14.0k, False: 0]
  ------------------
  165|  14.0k|                assert(real[idx].capacity() == std::max(old_cap, res_size));
  ------------------
  |  Branch (165:17): [True: 14.0k, False: 0]
  ------------------
  166|  14.0k|                break;
  167|  14.0k|            }
  168|   444k|            if (non_empty && command-- == 0) {
  ------------------
  |  Branch (168:17): [True: 253k, False: 190k]
  |  Branch (168:30): [True: 3.43k, False: 250k]
  ------------------
  169|       |                /* shrink_to_fit() */
  170|  3.43k|                size_t old_size = real[idx].size();
  171|  3.43k|                real[idx].shrink_to_fit();
  172|  3.43k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (172:17): [True: 3.43k, False: 0]
  ------------------
  173|  3.43k|                assert(real[idx].capacity() == old_size);
  ------------------
  |  Branch (173:17): [True: 3.43k, False: 0]
  ------------------
  174|  3.43k|                break;
  175|  3.43k|            }
  176|   440k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (176:17): [True: 238k, False: 201k]
  |  Branch (176:45): [True: 5.93k, False: 232k]
  ------------------
  177|       |                /* push_back() (copying) */
  178|  5.93k|                tmp = T(rng.rand64());
  179|  5.93k|                size_t old_size = real[idx].size();
  180|  5.93k|                size_t old_cap = real[idx].capacity();
  181|  5.93k|                real[idx].push_back(*tmp);
  182|  5.93k|                sim[idx].push_back(*tmp);
  183|  5.93k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (183:17): [True: 5.93k, False: 0]
  ------------------
  184|  5.93k|                if (old_cap > old_size) {
  ------------------
  |  Branch (184:21): [True: 3.08k, False: 2.84k]
  ------------------
  185|  3.08k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (185:21): [True: 3.08k, False: 0]
  ------------------
  186|  3.08k|                } else {
  187|  2.84k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (187:21): [True: 2.84k, False: 0]
  ------------------
  188|  2.84k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (188:21): [True: 2.84k, False: 0]
  ------------------
  189|  2.84k|                }
  190|  5.93k|                break;
  191|  5.93k|            }
  192|   434k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (192:17): [True: 232k, False: 201k]
  |  Branch (192:45): [True: 4.53k, False: 228k]
  ------------------
  193|       |                /* push_back() (moving) */
  194|  4.53k|                tmp = T(rng.rand64());
  195|  4.53k|                size_t old_size = real[idx].size();
  196|  4.53k|                size_t old_cap = real[idx].capacity();
  197|  4.53k|                sim[idx].push_back(*tmp);
  198|  4.53k|                real[idx].push_back(std::move(*tmp));
  199|  4.53k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (199:17): [True: 4.53k, False: 0]
  ------------------
  200|  4.53k|                if (old_cap > old_size) {
  ------------------
  |  Branch (200:21): [True: 2.35k, False: 2.17k]
  ------------------
  201|  2.35k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (201:21): [True: 2.35k, False: 0]
  ------------------
  202|  2.35k|                } else {
  203|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (203:21): [True: 2.17k, False: 0]
  ------------------
  204|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (204:21): [True: 2.17k, False: 0]
  ------------------
  205|  2.17k|                }
  206|  4.53k|                break;
  207|  4.53k|            }
  208|   430k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (208:17): [True: 228k, False: 201k]
  |  Branch (208:45): [True: 4.51k, False: 223k]
  ------------------
  209|       |                /* emplace_back() */
  210|  4.51k|                uint64_t seed{rng.rand64()};
  211|  4.51k|                size_t old_size = real[idx].size();
  212|  4.51k|                size_t old_cap = real[idx].capacity();
  213|  4.51k|                sim[idx].emplace_back(seed);
  214|  4.51k|                real[idx].emplace_back(seed);
  215|  4.51k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (215:17): [True: 4.51k, False: 0]
  ------------------
  216|  4.51k|                if (old_cap > old_size) {
  ------------------
  |  Branch (216:21): [True: 2.60k, False: 1.91k]
  ------------------
  217|  2.60k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (217:21): [True: 2.60k, False: 0]
  ------------------
  218|  2.60k|                } else {
  219|  1.91k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (219:21): [True: 1.91k, False: 0]
  ------------------
  220|  1.91k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (220:21): [True: 1.91k, False: 0]
  ------------------
  221|  1.91k|                }
  222|  4.51k|                break;
  223|  4.51k|            }
  224|   425k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (224:17): [True: 223k, False: 201k]
  |  Branch (224:45): [True: 6.97k, False: 216k]
  ------------------
  225|       |                /* push_front() (copying) */
  226|  6.97k|                tmp = T(rng.rand64());
  227|  6.97k|                size_t old_size = real[idx].size();
  228|  6.97k|                size_t old_cap = real[idx].capacity();
  229|  6.97k|                real[idx].push_front(*tmp);
  230|  6.97k|                sim[idx].push_front(*tmp);
  231|  6.97k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (231:17): [True: 6.97k, False: 0]
  ------------------
  232|  6.97k|                if (old_cap > old_size) {
  ------------------
  |  Branch (232:21): [True: 4.90k, False: 2.07k]
  ------------------
  233|  4.90k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (233:21): [True: 4.90k, False: 0]
  ------------------
  234|  4.90k|                } else {
  235|  2.07k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (235:21): [True: 2.07k, False: 0]
  ------------------
  236|  2.07k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (236:21): [True: 2.07k, False: 0]
  ------------------
  237|  2.07k|                }
  238|  6.97k|                break;
  239|  6.97k|            }
  240|   418k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (240:17): [True: 216k, False: 201k]
  |  Branch (240:45): [True: 10.5k, False: 206k]
  ------------------
  241|       |                /* push_front() (moving) */
  242|  10.5k|                tmp = T(rng.rand64());
  243|  10.5k|                size_t old_size = real[idx].size();
  244|  10.5k|                size_t old_cap = real[idx].capacity();
  245|  10.5k|                sim[idx].push_front(*tmp);
  246|  10.5k|                real[idx].push_front(std::move(*tmp));
  247|  10.5k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (247:17): [True: 10.5k, False: 0]
  ------------------
  248|  10.5k|                if (old_cap > old_size) {
  ------------------
  |  Branch (248:21): [True: 8.23k, False: 2.28k]
  ------------------
  249|  8.23k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (249:21): [True: 8.23k, False: 0]
  ------------------
  250|  8.23k|                } else {
  251|  2.28k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (251:21): [True: 2.28k, False: 0]
  ------------------
  252|  2.28k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (252:21): [True: 2.28k, False: 0]
  ------------------
  253|  2.28k|                }
  254|  10.5k|                break;
  255|  10.5k|            }
  256|   408k|            if (existing_buffer_non_full && command-- == 0) {
  ------------------
  |  Branch (256:17): [True: 206k, False: 201k]
  |  Branch (256:45): [True: 16.2k, False: 190k]
  ------------------
  257|       |                /* emplace_front() */
  258|  16.2k|                uint64_t seed{rng.rand64()};
  259|  16.2k|                size_t old_size = real[idx].size();
  260|  16.2k|                size_t old_cap = real[idx].capacity();
  261|  16.2k|                sim[idx].emplace_front(seed);
  262|  16.2k|                real[idx].emplace_front(seed);
  263|  16.2k|                assert(real[idx].size() == old_size + 1);
  ------------------
  |  Branch (263:17): [True: 16.2k, False: 0]
  ------------------
  264|  16.2k|                if (old_cap > old_size) {
  ------------------
  |  Branch (264:21): [True: 14.0k, False: 2.17k]
  ------------------
  265|  14.0k|                    assert(real[idx].capacity() == old_cap);
  ------------------
  |  Branch (265:21): [True: 14.0k, False: 0]
  ------------------
  266|  14.0k|                } else {
  267|  2.17k|                    assert(real[idx].capacity() > old_cap);
  ------------------
  |  Branch (267:21): [True: 2.17k, False: 0]
  ------------------
  268|  2.17k|                    assert(real[idx].capacity() <= 2 * (old_cap + 1));
  ------------------
  |  Branch (268:21): [True: 2.17k, False: 0]
  ------------------
  269|  2.17k|                }
  270|  16.2k|                break;
  271|  16.2k|            }
  272|   392k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (272:17): [True: 156k, False: 235k]
  |  Branch (272:46): [True: 1.73k, False: 154k]
  ------------------
  273|       |                /* front() [modifying] */
  274|  1.73k|                tmp = T(rng.rand64());
  275|  1.73k|                size_t old_size = real[idx].size();
  276|  1.73k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (276:17): [True: 1.73k, False: 0]
  ------------------
  277|  1.73k|                sim[idx].front() = *tmp;
  278|  1.73k|                real[idx].front() = std::move(*tmp);
  279|  1.73k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (279:17): [True: 1.73k, False: 0]
  ------------------
  280|  1.73k|                break;
  281|  1.73k|            }
  282|   390k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (282:17): [True: 154k, False: 235k]
  |  Branch (282:46): [True: 1.37k, False: 153k]
  ------------------
  283|       |                /* back() [modifying] */
  284|  1.37k|                tmp = T(rng.rand64());
  285|  1.37k|                size_t old_size = real[idx].size();
  286|  1.37k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (286:17): [True: 1.37k, False: 0]
  ------------------
  287|  1.37k|                sim[idx].back() = *tmp;
  288|  1.37k|                real[idx].back() = *tmp;
  289|  1.37k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (289:17): [True: 1.37k, False: 0]
  ------------------
  290|  1.37k|                break;
  291|  1.37k|            }
  292|   389k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (292:17): [True: 153k, False: 235k]
  |  Branch (292:46): [True: 4.09k, False: 149k]
  ------------------
  293|       |                /* operator[] [modifying] */
  294|  4.09k|                tmp = T(rng.rand64());
  295|  4.09k|                size_t pos = provider.ConsumeIntegralInRange<size_t>(0, sim[idx].size() - 1);
  296|  4.09k|                size_t old_size = real[idx].size();
  297|  4.09k|                assert(sim[idx][pos] == real[idx][pos]);
  ------------------
  |  Branch (297:17): [True: 4.09k, False: 0]
  ------------------
  298|  4.09k|                sim[idx][pos] = *tmp;
  299|  4.09k|                real[idx][pos] = std::move(*tmp);
  300|  4.09k|                assert(real[idx].size() == old_size);
  ------------------
  |  Branch (300:17): [True: 4.09k, False: 0]
  ------------------
  301|  4.09k|                break;
  302|  4.09k|            }
  303|   384k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (303:17): [True: 149k, False: 235k]
  |  Branch (303:46): [True: 38.2k, False: 110k]
  ------------------
  304|       |                /* pop_front() */
  305|  38.2k|                assert(sim[idx].front() == real[idx].front());
  ------------------
  |  Branch (305:17): [True: 38.2k, False: 0]
  ------------------
  306|  38.2k|                size_t old_size = real[idx].size();
  307|  38.2k|                sim[idx].pop_front();
  308|  38.2k|                real[idx].pop_front();
  309|  38.2k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (309:17): [True: 38.2k, False: 0]
  ------------------
  310|  38.2k|                break;
  311|  38.2k|            }
  312|   346k|            if (existing_buffer_non_empty && command-- == 0) {
  ------------------
  |  Branch (312:17): [True: 110k, False: 235k]
  |  Branch (312:46): [True: 1.96k, False: 108k]
  ------------------
  313|       |                /* pop_back() */
  314|  1.96k|                assert(sim[idx].back() == real[idx].back());
  ------------------
  |  Branch (314:17): [True: 1.96k, False: 0]
  ------------------
  315|  1.96k|                size_t old_size = real[idx].size();
  316|  1.96k|                sim[idx].pop_back();
  317|  1.96k|                real[idx].pop_back();
  318|  1.96k|                assert(real[idx].size() == old_size - 1);
  ------------------
  |  Branch (318:17): [True: 1.96k, False: 0]
  ------------------
  319|  1.96k|                break;
  320|  1.96k|            }
  321|   346k|        }
  322|   195k|    }
  323|       |
  324|       |    /* Fully compare the final state. */
  325|  5.57k|    for (unsigned i = 0; i < sim.size(); ++i) {
  ------------------
  |  Branch (325:26): [True: 3.36k, False: 2.20k]
  ------------------
  326|       |        // Make sure const getters work.
  327|  3.36k|        const VecDeque<T>& realbuf = real[i];
  328|  3.36k|        const std::deque<T>& simbuf = sim[i];
  329|  3.36k|        compare_fn(realbuf, simbuf);
  330|  9.78k|        for (unsigned j = 0; j < sim.size(); ++j) {
  ------------------
  |  Branch (330:30): [True: 6.42k, False: 3.36k]
  ------------------
  331|  6.42k|            assert((realbuf == real[j]) == (simbuf == sim[j]));
  ------------------
  |  Branch (331:13): [True: 6.42k, False: 0]
  ------------------
  332|  6.42k|            assert(((realbuf <=> real[j]) >= 0) == (simbuf >= sim[j]));
  ------------------
  |  Branch (332:13): [True: 6.42k, False: 0]
  ------------------
  333|  6.42k|            assert(((realbuf <=> real[j]) <= 0) == (simbuf <= sim[j]));
  ------------------
  |  Branch (333:13): [True: 6.42k, False: 0]
  ------------------
  334|  6.42k|        }
  335|       |        // Clear out the buffers so we can check below that no objects exist anymore.
  336|  3.36k|        sim[i].clear();
  337|  3.36k|        real[i].clear();
  338|  3.36k|    }
  339|       |
  340|  2.20k|    if constexpr (CheckNoneLeft) {
  341|  2.20k|        tmp = std::nullopt;
  342|  2.20k|        T::CheckNoneExist();
  343|  2.20k|    }
  344|  2.20k|}
vecdeque.cpp:_ZZN12_GLOBAL__N_18TestTypeINS_10TrackedObjILm17EEELb1EEEvNSt3__14spanIKhLm18446744073709551615EEEmENKUlRK8VecDequeIS2_ERKNS3_5dequeIS2_NS3_9allocatorIS2_EEEEE_clESA_SG_:
   43|  60.3k|    auto compare_fn = [](const VecDeque<T>& r, const std::deque<T>& s) {
   44|  60.3k|        assert(r.size() == s.size());
  ------------------
  |  Branch (44:9): [True: 60.3k, False: 0]
  ------------------
   45|  60.3k|        assert(r.empty() == s.empty());
  ------------------
  |  Branch (45:9): [True: 60.3k, False: 0]
  ------------------
   46|  60.3k|        assert(r.capacity() >= r.size());
  ------------------
  |  Branch (46:9): [True: 60.3k, False: 0]
  ------------------
   47|  60.3k|        if (s.size() == 0) return;
  ------------------
  |  Branch (47:13): [True: 27.6k, False: 32.7k]
  ------------------
   48|  60.3k|        assert(r.front() == s.front());
  ------------------
  |  Branch (48:9): [True: 32.7k, False: 0]
  ------------------
   49|  32.7k|        assert(r.back() == s.back());
  ------------------
  |  Branch (49:9): [True: 32.7k, False: 0]
  ------------------
   50|   548k|        for (size_t i = 0; i < s.size(); ++i) {
  ------------------
  |  Branch (50:28): [True: 515k, False: 32.7k]
  ------------------
   51|       |            assert(r[i] == s[i]);
  ------------------
  |  Branch (51:13): [True: 515k, False: 0]
  ------------------
   52|   515k|        }
   53|  32.7k|    };
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEC2EOS1_:
  431|   186k|    {
  432|   186k|        Register();
  433|   186k|        Deref() = other.Deref();
  434|   186k|        other.Deref() = std::nullopt;
  435|   186k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EE8RegisterEv:
  380|  1.08M|    {
  381|  1.08M|        auto [it, inserted] = g_tracker.emplace(this, std::nullopt);
  382|  1.08M|        assert(inserted);
  ------------------
  |  Branch (382:9): [True: 1.08M, False: 0]
  ------------------
  383|  19.4M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (383:28): [True: 18.4M, False: 1.08M]
  ------------------
  384|  18.4M|            m_track_entry[i] = it;
  385|  18.4M|        }
  386|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EE5DerefEv:
  400|  1.14M|    {
  401|  1.14M|        Check();
  402|  1.14M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (402:9): [True: 1.14M, False: 0]
  ------------------
  403|  1.14M|        return m_track_entry[0]->second;
  404|  1.14M|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm17EE5CheckEv:
  371|  5.13M|    {
  372|  5.13M|        auto it = g_tracker.find(this);
  373|  92.3M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (373:28): [True: 87.2M, False: 5.13M]
  ------------------
  374|       |            assert(m_track_entry[i] == it);
  ------------------
  |  Branch (374:13): [True: 87.2M, False: 0]
  ------------------
  375|  87.2M|        }
  376|  5.13M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEC2Ev:
  416|   527k|    TrackedObj() { Register(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEC2ERKS1_:
  425|   292k|    {
  426|   292k|        Register();
  427|   292k|        Deref() = other.Deref();
  428|   292k|    }
vecdeque.cpp:_ZNK12_GLOBAL__N_110TrackedObjILm17EE5DerefEv:
  408|  2.90M|    {
  409|  2.90M|        Check();
  410|  2.90M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (410:9): [True: 2.90M, False: 0]
  ------------------
  411|  2.90M|        return m_track_entry[0]->second;
  412|  2.90M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEC2Em:
  419|  76.6k|    {
  420|  76.6k|        Register();
  421|  76.6k|        Deref() = value;
  422|  76.6k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EED2Ev:
  415|  1.08M|    ~TrackedObj() { Deregister(); }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EE10DeregisterEv:
  389|  1.08M|    {
  390|  1.08M|        Check();
  391|  1.08M|        assert(m_track_entry[0] != g_tracker.end());
  ------------------
  |  Branch (391:9): [True: 1.08M, False: 0]
  ------------------
  392|  1.08M|        g_tracker.erase(m_track_entry[0]);
  393|  19.4M|        for (size_t i = 0; i < Size; ++i) {
  ------------------
  |  Branch (393:28): [True: 18.4M, False: 1.08M]
  ------------------
  394|  18.4M|            m_track_entry[i] = g_tracker.end();
  395|  18.4M|        }
  396|  1.08M|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1eqERKNS_10TrackedObjILm17EEES3_:
  453|   735k|    {
  454|   735k|        return a.Deref() == b.Deref();
  455|   735k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEaSERKS1_:
  438|  98.4k|    {
  439|  98.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (439:13): [True: 0, False: 98.4k]
  ------------------
  440|  98.4k|        Deref() = other.Deref();
  441|  98.4k|        return *this;
  442|  98.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EEaSEOS1_:
  445|  39.4k|    {
  446|  39.4k|        if (this == &other) return *this;
  ------------------
  |  Branch (446:13): [True: 0, False: 39.4k]
  ------------------
  447|  39.4k|        Deref() = other.Deref();
  448|  39.4k|        other.Deref() = std::nullopt;
  449|  39.4k|        return *this;
  450|  39.4k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_1ssERKNS_10TrackedObjILm17EEES3_:
  458|   323k|    {
  459|       |        // Libc++ 15 & 16 do not support std::optional<T>::operator<=> yet. See
  460|       |        // https://reviews.llvm.org/D146392.
  461|   323k|        if (!a.Deref().has_value() || !b.Deref().has_value()) {
  ------------------
  |  Branch (461:13): [True: 251k, False: 72.1k]
  |  Branch (461:39): [True: 128, False: 72.0k]
  ------------------
  462|   251k|            return a.Deref().has_value() <=> b.Deref().has_value();
  463|   251k|        }
  464|  72.0k|        return *a.Deref() <=> *b.Deref();
  465|   323k|    }
vecdeque.cpp:_ZN12_GLOBAL__N_110TrackedObjILm17EE14CheckNoneExistEv:
  468|  2.20k|    {
  469|       |        assert(g_tracker.empty());
  ------------------
  |  Branch (469:9): [True: 2.20k, False: 0]
  ------------------
  470|  2.20k|    }

__gcov_reset:
   13|      2|extern "C" __attribute__((weak)) void __gcov_reset(void) {}

_ZN9base_blobILj256EE4dataEv:
   99|      2|    constexpr unsigned char* data() { return m_data.data(); }
_ZN9base_blobILj256EE4sizeEv:
  107|      2|    static constexpr unsigned int size() { return WIDTH; }

_ZN10btcsignals6signalIFvvENS_10null_valueEED2Ev:
  175|      6|    ~signal() = default;
_ZN10btcsignals6signalIFv20SynchronizationStatellbENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFv20SynchronizationStateRK11CBlockIndexdENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFvRKNSt3__112basic_stringIcNS1_11char_traitsIcEENS1_9allocatorIcEEEEibENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFvbENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFviENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFvRKNSt3__112basic_stringIcNS1_11char_traitsIcEENS1_9allocatorIcEEEEENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFbRK13bilingual_strRKNSt3__112basic_stringIcNS4_11char_traitsIcEENS4_9allocatorIcEEEEjENS_6any_ofEED2Ev:
  175|      2|    ~signal() = default;
_ZN10btcsignals6signalIFvRK13bilingual_strjENS_10null_valueEED2Ev:
  175|      2|    ~signal() = default;

_Z22inline_assertion_checkILb0ERKmEOT0_S3_RKNSt3__115source_locationENS4_17basic_string_viewIcNS4_11char_traitsIcEEEE:
   90|   459k|{
   91|   459k|    if (IS_ASSERT || std::is_constant_evaluated() || G_ABORT_ON_FAILED_ASSUME) {
  ------------------
  |  Branch (91:9): [Folded, False: 0]
  |  Branch (91:22): [Folded, False: 0]
  |  Branch (91:54): [True: 0, Folded]
  ------------------
   92|   459k|        if (!val) {
  ------------------
  |  Branch (92:13): [True: 0, False: 459k]
  ------------------
   93|      0|            assertion_fail(loc, assertion);
   94|      0|        }
   95|   459k|    }
   96|   459k|    return std::forward<T>(val);
   97|   459k|}
_Z22inline_assertion_checkILb1ERPKNSt3__18functionIFvNS0_4spanIKhLm18446744073709551615EEEEEEEOT0_SB_RKNS0_15source_locationENS0_17basic_string_viewIcNS0_11char_traitsIcEEEE:
   90|  2.20k|{
   91|  2.20k|    if (IS_ASSERT || std::is_constant_evaluated() || G_ABORT_ON_FAILED_ASSUME) {
  ------------------
  |  Branch (91:9): [True: 2.20k, Folded]
  |  Branch (91:22): [Folded, False: 0]
  |  Branch (91:54): [True: 0, Folded]
  ------------------
   92|  2.20k|        if (!val) {
  ------------------
  |  Branch (92:13): [True: 0, False: 2.20k]
  ------------------
   93|      0|            assertion_fail(loc, assertion);
   94|      0|        }
   95|  2.20k|    }
   96|  2.20k|    return std::forward<T>(val);
   97|  2.20k|}
_Z22inline_assertion_checkILb0ERmEOT0_S2_RKNSt3__115source_locationENS3_17basic_string_viewIcNS3_11char_traitsIcEEEE:
   90|   605k|{
   91|   605k|    if (IS_ASSERT || std::is_constant_evaluated() || G_ABORT_ON_FAILED_ASSUME) {
  ------------------
  |  Branch (91:9): [Folded, False: 0]
  |  Branch (91:22): [Folded, False: 0]
  |  Branch (91:54): [True: 0, Folded]
  ------------------
   92|   605k|        if (!val) {
  ------------------
  |  Branch (92:13): [True: 0, False: 605k]
  ------------------
   93|      0|            assertion_fail(loc, assertion);
   94|      0|        }
   95|   605k|    }
   96|   605k|    return std::forward<T>(val);
   97|   605k|}
_Z22inline_assertion_checkILb1EbEOT0_S1_RKNSt3__115source_locationENS2_17basic_string_viewIcNS2_11char_traitsIcEEEE:
   90|  2.20k|{
   91|  2.20k|    if (IS_ASSERT || std::is_constant_evaluated() || G_ABORT_ON_FAILED_ASSUME) {
  ------------------
  |  Branch (91:9): [True: 2.20k, Folded]
  |  Branch (91:22): [Folded, False: 0]
  |  Branch (91:54): [True: 0, Folded]
  ------------------
   92|  2.20k|        if (!val) {
  ------------------
  |  Branch (92:13): [True: 0, False: 2.20k]
  ------------------
   93|      0|            assertion_fail(loc, assertion);
   94|      0|        }
   95|  2.20k|    }
   96|  2.20k|    return std::forward<T>(val);
   97|  2.20k|}
_Z22inline_assertion_checkILb0EbEOT0_S1_RKNSt3__115source_locationENS2_17basic_string_viewIcNS2_11char_traitsIcEEEE:
   90|  18.8M|{
   91|  18.8M|    if (IS_ASSERT || std::is_constant_evaluated() || G_ABORT_ON_FAILED_ASSUME) {
  ------------------
  |  Branch (91:9): [Folded, False: 0]
  |  Branch (91:22): [Folded, False: 0]
  |  Branch (91:54): [True: 0, Folded]
  ------------------
   92|  18.8M|        if (!val) {
  ------------------
  |  Branch (92:13): [True: 0, False: 18.8M]
  ------------------
   93|      0|            assertion_fail(loc, assertion);
   94|      0|        }
   95|  18.8M|    }
   96|  18.8M|    return std::forward<T>(val);
   97|  18.8M|}

_ZN16CThreadInterruptD2Ev:
   32|      4|    virtual ~CThreadInterrupt() = default;

_ZN10ThreadPoolD2Ev:
   93|     10|    {
   94|     10|        Stop(); // In case it hasn't been stopped.
   95|     10|    }
_ZN10ThreadPool4StopEv:
  129|     10|    {
  130|       |        // Notify workers and join them
  131|     10|        std::vector<std::thread> threads_to_join;
  132|     10|        {
  133|     10|            LOCK(m_mutex);
  ------------------
  |  |  268|     10|#define LOCK(cs) UniqueLock BITCOIN_UNIQUE_NAME(criticalblock)(MaybeCheckNotHeld(cs), #cs, __FILE__, __LINE__)
  |  |  ------------------
  |  |  |  |   11|     10|#define BITCOIN_UNIQUE_NAME(name) PASTE2(name, __COUNTER__)
  |  |  |  |  ------------------
  |  |  |  |  |  |    9|     10|#define PASTE2(x, y) PASTE(x, y)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |    8|     10|#define PASTE(x, y) x ## y
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  134|       |            // Ensure Stop() is not called from a worker thread while workers are still registered,
  135|       |            // otherwise a self-join deadlock would occur.
  136|     10|            auto id = std::this_thread::get_id();
  137|     10|            for (const auto& worker : m_workers) assert(worker.get_id() != id);
  ------------------
  |  Branch (137:37): [True: 0, False: 10]
  |  Branch (137:50): [True: 0, False: 0]
  ------------------
  138|       |            // Early shutdown to return right away on any concurrent Submit() call
  139|     10|            m_interrupt = true;
  140|     10|            threads_to_join.swap(m_workers);
  141|     10|        }
  142|      0|        m_cv.notify_all();
  143|       |        // Help draining queue
  144|     10|        while (ProcessTask()) {}
  ------------------
  |  Branch (144:16): [True: 0, False: 10]
  ------------------
  145|       |        // Free resources
  146|     10|        for (auto& worker : threads_to_join) worker.join();
  ------------------
  |  Branch (146:27): [True: 0, False: 10]
  ------------------
  147|       |
  148|       |        // Since we currently wait for tasks completion, sanity-check empty queue
  149|     10|        LOCK(m_mutex);
  ------------------
  |  |  268|     10|#define LOCK(cs) UniqueLock BITCOIN_UNIQUE_NAME(criticalblock)(MaybeCheckNotHeld(cs), #cs, __FILE__, __LINE__)
  |  |  ------------------
  |  |  |  |   11|     10|#define BITCOIN_UNIQUE_NAME(name) PASTE2(name, __COUNTER__)
  |  |  |  |  ------------------
  |  |  |  |  |  |    9|     10|#define PASTE2(x, y) PASTE(x, y)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |    8|     10|#define PASTE(x, y) x ## y
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  150|     10|        Assume(m_work_queue.empty());
  ------------------
  |  |  128|     10|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  151|       |        // Re-allow Start() now that all workers have exited
  152|     10|        m_interrupt = false;
  153|     10|    }
_ZN10ThreadPool11ProcessTaskEv:
  244|     10|    {
  245|     10|        std::packaged_task<void()> task;
  246|     10|        {
  247|     10|            LOCK(m_mutex);
  ------------------
  |  |  268|     10|#define LOCK(cs) UniqueLock BITCOIN_UNIQUE_NAME(criticalblock)(MaybeCheckNotHeld(cs), #cs, __FILE__, __LINE__)
  |  |  ------------------
  |  |  |  |   11|     10|#define BITCOIN_UNIQUE_NAME(name) PASTE2(name, __COUNTER__)
  |  |  |  |  ------------------
  |  |  |  |  |  |    9|     10|#define PASTE2(x, y) PASTE(x, y)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |    8|     10|#define PASTE(x, y) x ## y
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  248|     10|            if (m_work_queue.empty()) return false;
  ------------------
  |  Branch (248:17): [True: 10, False: 0]
  ------------------
  249|       |
  250|       |            // Pop the task
  251|      0|            task = std::move(m_work_queue.front());
  252|      0|            m_work_queue.pop();
  253|      0|        }
  254|      0|        task();
  255|      0|        return true;
  256|     10|    }

_Z11SetMockTimeNSt3__16chrono8durationIxNS_5ratioILl1ELl1EEEEE:
   54|  2.20k|{
   55|  2.20k|    Assert(mock_time_in >= 0s);
  ------------------
  |  |  116|  2.20k|#define Assert(val) inline_assertion_check<true>(val, std::source_location::current(), #val)
  ------------------
   56|  2.20k|    g_mock_time.store(mock_time_in, std::memory_order_relaxed);
   57|  2.20k|}
_ZN19MockableSteadyClock13ClearMockTimeEv:
   84|  2.20k|{
   85|  2.20k|    g_mock_steady_time.store(0ms, std::memory_order_relaxed);
   86|  2.20k|}

_ZN8VecDequeIhEC2EOS0_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
_ZN8VecDequeIhE4swapERS0_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
_ZNK8VecDequeIhE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
_ZNK8VecDequeIhE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
_ZNK8VecDequeIhEixEm:
  304|   838k|    {
  305|   838k|        Assume(idx < m_size);
  ------------------
  |  |  128|   838k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|   838k|        return m_buffer[BufferIndex(idx)];
  307|   838k|    }
_ZN8VecDequeIhE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
_ZN8VecDequeIhEaSEOS0_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
_ZN8VecDequeIhEC2ERKS0_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
_Z4swapR8VecDequeIhES1_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
_ZN8VecDequeIhEaSERKS0_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|  13.3k|        if constexpr (std::is_trivially_copyable_v<T>) {
  142|  13.3k|            size_t first_part = other.FirstPart();
  143|  13.3k|            Assume(first_part > 0 || m_size == 0);
  ------------------
  |  |  128|  15.8k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 10.8k, False: 2.51k]
  |  |  |  Branch (128:51): [True: 2.51k, False: 0]
  |  |  ------------------
  ------------------
  144|  13.3k|            if (first_part != 0) {
  ------------------
  |  Branch (144:17): [True: 10.8k, False: 2.51k]
  ------------------
  145|  10.8k|                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|  10.8k|            }
  147|  13.3k|            if (first_part != other.m_size) {
  ------------------
  |  Branch (147:17): [True: 3.36k, False: 10.0k]
  ------------------
  148|  3.36k|                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|  3.36k|            }
  150|  13.3k|            m_size = other.m_size;
  151|       |        } else {
  152|       |            while (m_size < other.m_size) {
  153|       |                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|       |                ++m_size;
  155|       |            }
  156|       |        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
_ZNK8VecDequeIhE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
_ZN8VecDequeIhE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
_ZN8VecDequeIhE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
_ZN8VecDequeIhE10push_frontERKh:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
_ZN8VecDequeIhE13emplace_frontIJRKhEEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
_ZN8VecDequeIhE10push_frontEOh:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
_ZN8VecDequeIhE13emplace_frontIJhEEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
_ZN8VecDequeIhE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
_ZN8VecDequeIhE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
_ZeqRK8VecDequeIhES2_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 224, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
_ZssRK8VecDequeIhES2_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.58k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 732, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
_ZN8VecDequeItEC2EOS0_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
_ZN8VecDequeItE4swapERS0_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
_ZNK8VecDequeItE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
_ZNK8VecDequeItE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
_ZNK8VecDequeItE11BufferIndexEm:
   76|  1.19M|    {
   77|  1.19M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.19M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.19M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 311k, False: 886k]
  ------------------
   81|   311k|            return (m_offset + pos) - m_capacity;
   82|   886k|        } else {
   83|   886k|            return m_offset + pos;
   84|   886k|        }
   85|  1.19M|    }
_ZNK8VecDequeItEixEm:
  304|   838k|    {
  305|   838k|        Assume(idx < m_size);
  ------------------
  |  |  128|   838k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|   838k|        return m_buffer[BufferIndex(idx)];
  307|   838k|    }
_ZN8VecDequeItE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
_ZN8VecDequeItE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|  53.2k|        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|  53.2k|            m_size = size;
   97|       |        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|       |            while (m_size > size) {
  100|       |                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|       |                --m_size;
  102|       |            }
  103|       |        }
  104|  53.2k|    }
_ZN8VecDequeItE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|  31.3k|            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|  31.3k|                size_t first_part = FirstPart();
   49|  31.3k|                if (first_part != 0) {
  ------------------
  |  Branch (49:21): [True: 9.45k, False: 21.8k]
  ------------------
   50|  9.45k|                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|  9.45k|                }
   52|  31.3k|                if (first_part != m_size) {
  ------------------
  |  Branch (52:21): [True: 2.04k, False: 29.3k]
  ------------------
   53|  2.04k|                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|  2.04k|                }
   55|       |            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|       |                size_t old_pos = m_offset;
   58|       |                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
   59|       |                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|       |                    std::destroy_at(m_buffer + old_pos);
   61|       |                    ++old_pos;
   62|       |                    if (old_pos == m_capacity) old_pos = 0;
   63|       |                }
   64|       |            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
_ZNK8VecDequeItE9FirstPartEv:
   37|  44.7k|    size_t FirstPart() const noexcept { return std::min(m_capacity - m_offset, m_size); }
_ZNK8VecDequeItE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
_ZN8VecDequeItE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
_ZNK8VecDequeItE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
_ZN8VecDequeItEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
_ZN8VecDequeItEaSEOS0_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
_ZN8VecDequeItED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
_ZN8VecDequeItEC2ERKS0_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
_Z4swapR8VecDequeItES1_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
_ZN8VecDequeItEaSERKS0_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|  13.3k|        if constexpr (std::is_trivially_copyable_v<T>) {
  142|  13.3k|            size_t first_part = other.FirstPart();
  143|  13.3k|            Assume(first_part > 0 || m_size == 0);
  ------------------
  |  |  128|  15.8k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 10.8k, False: 2.51k]
  |  |  |  Branch (128:51): [True: 2.51k, False: 0]
  |  |  ------------------
  ------------------
  144|  13.3k|            if (first_part != 0) {
  ------------------
  |  Branch (144:17): [True: 10.8k, False: 2.51k]
  ------------------
  145|  10.8k|                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|  10.8k|            }
  147|  13.3k|            if (first_part != other.m_size) {
  ------------------
  |  Branch (147:17): [True: 3.36k, False: 10.0k]
  ------------------
  148|  3.36k|                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|  3.36k|            }
  150|  13.3k|            m_size = other.m_size;
  151|       |        } else {
  152|       |            while (m_size < other.m_size) {
  153|       |                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|       |                ++m_size;
  155|       |            }
  156|       |        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
_ZNK8VecDequeItE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
_ZN8VecDequeItE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
_ZN8VecDequeItE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
_ZN8VecDequeItE9push_backERKt:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
_ZN8VecDequeItE12emplace_backIJRKtEEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
_ZN8VecDequeItE9push_backEOt:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
_ZN8VecDequeItE12emplace_backIJtEEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
_ZN8VecDequeItE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
_ZN8VecDequeItE10push_frontERKt:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
_ZN8VecDequeItE13emplace_frontIJRKtEEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
_ZN8VecDequeItE10push_frontEOt:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
_ZN8VecDequeItE13emplace_frontIJtEEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
_ZN8VecDequeItE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
_ZN8VecDequeItE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
_ZN8VecDequeItE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
_ZN8VecDequeItEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
_ZN8VecDequeItE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
_ZN8VecDequeItE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
_ZeqRK8VecDequeItES2_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
_ZssRK8VecDequeItES2_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
_ZN8VecDequeIjEC2EOS0_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
_ZN8VecDequeIjE4swapERS0_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
_ZNK8VecDequeIjE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
_ZNK8VecDequeIjE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
_ZNK8VecDequeIjE11BufferIndexEm:
   76|  1.19M|    {
   77|  1.19M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.19M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.19M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 311k, False: 886k]
  ------------------
   81|   311k|            return (m_offset + pos) - m_capacity;
   82|   886k|        } else {
   83|   886k|            return m_offset + pos;
   84|   886k|        }
   85|  1.19M|    }
_ZNK8VecDequeIjEixEm:
  304|   838k|    {
  305|   838k|        Assume(idx < m_size);
  ------------------
  |  |  128|   838k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|   838k|        return m_buffer[BufferIndex(idx)];
  307|   838k|    }
_ZN8VecDequeIjE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
_ZN8VecDequeIjE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|  53.2k|        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|  53.2k|            m_size = size;
   97|       |        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|       |            while (m_size > size) {
  100|       |                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|       |                --m_size;
  102|       |            }
  103|       |        }
  104|  53.2k|    }
_ZN8VecDequeIjE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|  31.3k|            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|  31.3k|                size_t first_part = FirstPart();
   49|  31.3k|                if (first_part != 0) {
  ------------------
  |  Branch (49:21): [True: 9.45k, False: 21.8k]
  ------------------
   50|  9.45k|                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|  9.45k|                }
   52|  31.3k|                if (first_part != m_size) {
  ------------------
  |  Branch (52:21): [True: 2.04k, False: 29.3k]
  ------------------
   53|  2.04k|                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|  2.04k|                }
   55|       |            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|       |                size_t old_pos = m_offset;
   58|       |                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
   59|       |                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|       |                    std::destroy_at(m_buffer + old_pos);
   61|       |                    ++old_pos;
   62|       |                    if (old_pos == m_capacity) old_pos = 0;
   63|       |                }
   64|       |            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
_ZNK8VecDequeIjE9FirstPartEv:
   37|  44.7k|    size_t FirstPart() const noexcept { return std::min(m_capacity - m_offset, m_size); }
_ZNK8VecDequeIjE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
_ZN8VecDequeIjE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
_ZNK8VecDequeIjE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
_ZN8VecDequeIjEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
_ZN8VecDequeIjEaSEOS0_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
_ZN8VecDequeIjED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
_ZN8VecDequeIjEC2ERKS0_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
_Z4swapR8VecDequeIjES1_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
_ZN8VecDequeIjEaSERKS0_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|  13.3k|        if constexpr (std::is_trivially_copyable_v<T>) {
  142|  13.3k|            size_t first_part = other.FirstPart();
  143|  13.3k|            Assume(first_part > 0 || m_size == 0);
  ------------------
  |  |  128|  15.8k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 10.8k, False: 2.51k]
  |  |  |  Branch (128:51): [True: 2.51k, False: 0]
  |  |  ------------------
  ------------------
  144|  13.3k|            if (first_part != 0) {
  ------------------
  |  Branch (144:17): [True: 10.8k, False: 2.51k]
  ------------------
  145|  10.8k|                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|  10.8k|            }
  147|  13.3k|            if (first_part != other.m_size) {
  ------------------
  |  Branch (147:17): [True: 3.36k, False: 10.0k]
  ------------------
  148|  3.36k|                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|  3.36k|            }
  150|  13.3k|            m_size = other.m_size;
  151|       |        } else {
  152|       |            while (m_size < other.m_size) {
  153|       |                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|       |                ++m_size;
  155|       |            }
  156|       |        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
_ZNK8VecDequeIjE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
_ZN8VecDequeIjE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
_ZN8VecDequeIjE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
_ZN8VecDequeIjE9push_backERKj:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
_ZN8VecDequeIjE12emplace_backIJRKjEEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
_ZN8VecDequeIjE9push_backEOj:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
_ZN8VecDequeIjE12emplace_backIJjEEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
_ZN8VecDequeIjE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
_ZN8VecDequeIjE10push_frontERKj:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
_ZN8VecDequeIjE13emplace_frontIJRKjEEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
_ZN8VecDequeIjE10push_frontEOj:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
_ZN8VecDequeIjE13emplace_frontIJjEEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
_ZN8VecDequeIjE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
_ZN8VecDequeIjE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
_ZN8VecDequeIjE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
_ZN8VecDequeIjEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
_ZN8VecDequeIjE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
_ZN8VecDequeIjE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
_ZeqRK8VecDequeIjES2_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
_ZssRK8VecDequeIjES2_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
_ZN8VecDequeImEC2EOS0_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
_ZN8VecDequeImE4swapERS0_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
_ZNK8VecDequeImE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
_ZNK8VecDequeImE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
_ZNK8VecDequeImE11BufferIndexEm:
   76|  1.19M|    {
   77|  1.19M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.19M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.19M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 311k, False: 886k]
  ------------------
   81|   311k|            return (m_offset + pos) - m_capacity;
   82|   886k|        } else {
   83|   886k|            return m_offset + pos;
   84|   886k|        }
   85|  1.19M|    }
_ZNK8VecDequeImEixEm:
  304|   838k|    {
  305|   838k|        Assume(idx < m_size);
  ------------------
  |  |  128|   838k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|   838k|        return m_buffer[BufferIndex(idx)];
  307|   838k|    }
_ZN8VecDequeImE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
_ZN8VecDequeImE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|  53.2k|        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|  53.2k|            m_size = size;
   97|       |        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|       |            while (m_size > size) {
  100|       |                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|       |                --m_size;
  102|       |            }
  103|       |        }
  104|  53.2k|    }
_ZN8VecDequeImE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|  31.3k|            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|  31.3k|                size_t first_part = FirstPart();
   49|  31.3k|                if (first_part != 0) {
  ------------------
  |  Branch (49:21): [True: 9.45k, False: 21.8k]
  ------------------
   50|  9.45k|                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|  9.45k|                }
   52|  31.3k|                if (first_part != m_size) {
  ------------------
  |  Branch (52:21): [True: 2.04k, False: 29.3k]
  ------------------
   53|  2.04k|                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|  2.04k|                }
   55|       |            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|       |                size_t old_pos = m_offset;
   58|       |                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
   59|       |                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|       |                    std::destroy_at(m_buffer + old_pos);
   61|       |                    ++old_pos;
   62|       |                    if (old_pos == m_capacity) old_pos = 0;
   63|       |                }
   64|       |            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
_ZNK8VecDequeImE9FirstPartEv:
   37|  44.7k|    size_t FirstPart() const noexcept { return std::min(m_capacity - m_offset, m_size); }
_ZNK8VecDequeImE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
_ZN8VecDequeImE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
_ZNK8VecDequeImE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
_ZN8VecDequeImEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
_ZN8VecDequeImEaSEOS0_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
_ZN8VecDequeImED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
_ZN8VecDequeImEC2ERKS0_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
_Z4swapR8VecDequeImES1_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
_ZN8VecDequeImEaSERKS0_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|  13.3k|        if constexpr (std::is_trivially_copyable_v<T>) {
  142|  13.3k|            size_t first_part = other.FirstPart();
  143|  13.3k|            Assume(first_part > 0 || m_size == 0);
  ------------------
  |  |  128|  15.8k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 10.8k, False: 2.51k]
  |  |  |  Branch (128:51): [True: 2.51k, False: 0]
  |  |  ------------------
  ------------------
  144|  13.3k|            if (first_part != 0) {
  ------------------
  |  Branch (144:17): [True: 10.8k, False: 2.51k]
  ------------------
  145|  10.8k|                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|  10.8k|            }
  147|  13.3k|            if (first_part != other.m_size) {
  ------------------
  |  Branch (147:17): [True: 3.36k, False: 10.0k]
  ------------------
  148|  3.36k|                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|  3.36k|            }
  150|  13.3k|            m_size = other.m_size;
  151|       |        } else {
  152|       |            while (m_size < other.m_size) {
  153|       |                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|       |                ++m_size;
  155|       |            }
  156|       |        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
_ZNK8VecDequeImE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
_ZN8VecDequeImE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
_ZN8VecDequeImE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
_ZN8VecDequeImE9push_backERKm:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
_ZN8VecDequeImE12emplace_backIJRKmEEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
_ZN8VecDequeImE9push_backEOm:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
_ZN8VecDequeImE12emplace_backIJmEEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
_ZN8VecDequeImE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
_ZN8VecDequeImE10push_frontERKm:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
_ZN8VecDequeImE13emplace_frontIJRKmEEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
_ZN8VecDequeImE10push_frontEOm:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
_ZN8VecDequeImE13emplace_frontIJmEEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
_ZN8VecDequeImE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
_ZN8VecDequeImE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
_ZN8VecDequeImE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
_ZN8VecDequeImEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
_ZN8VecDequeImE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
_ZN8VecDequeImE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
_ZeqRK8VecDequeImES2_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
_ZssRK8VecDequeImES2_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEC2EOS3_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE4swapERS3_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE11BufferIndexEm:
   76|  1.98M|    {
   77|  1.98M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.98M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.98M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 475k, False: 1.50M]
  ------------------
   81|   475k|            return (m_offset + pos) - m_capacity;
   82|  1.50M|        } else {
   83|  1.50M|            return m_offset + pos;
   84|  1.50M|        }
   85|  1.98M|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEixEm:
  304|  1.00M|    {
  305|  1.00M|        Assume(idx < m_size);
  ------------------
  |  |  128|  1.00M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|  1.00M|        return m_buffer[BufferIndex(idx)];
  307|  1.00M|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|       |        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|       |            m_size = size;
   97|  53.2k|        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|   496k|            while (m_size > size) {
  ------------------
  |  Branch (99:20): [True: 443k, False: 53.2k]
  ------------------
  100|   443k|                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|   443k|                --m_size;
  102|   443k|            }
  103|  53.2k|        }
  104|  53.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|       |            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|       |                size_t first_part = FirstPart();
   49|       |                if (first_part != 0) {
   50|       |                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|       |                }
   52|       |                if (first_part != m_size) {
   53|       |                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|       |                }
   55|  31.3k|            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|  31.3k|                size_t old_pos = m_offset;
   58|   200k|                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
  ------------------
  |  Branch (58:42): [True: 169k, False: 31.3k]
  ------------------
   59|   169k|                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|   169k|                    std::destroy_at(m_buffer + old_pos);
   61|   169k|                    ++old_pos;
   62|   169k|                    if (old_pos == m_capacity) old_pos = 0;
  ------------------
  |  Branch (62:25): [True: 8.31k, False: 161k]
  ------------------
   63|   169k|                }
   64|  31.3k|            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEaSEOS3_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEC2ERKS3_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
vecdeque.cpp:_Z4swapR8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEES4_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEaSERKS3_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|       |        if constexpr (std::is_trivially_copyable_v<T>) {
  142|       |            size_t first_part = other.FirstPart();
  143|       |            Assume(first_part > 0 || m_size == 0);
  144|       |            if (first_part != 0) {
  145|       |                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|       |            }
  147|       |            if (first_part != other.m_size) {
  148|       |                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|       |            }
  150|       |            m_size = other.m_size;
  151|  13.3k|        } else {
  152|   184k|            while (m_size < other.m_size) {
  ------------------
  |  Branch (152:20): [True: 170k, False: 13.3k]
  ------------------
  153|   170k|                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|   170k|                ++m_size;
  155|   170k|            }
  156|  13.3k|        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE9push_backERKS2_:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE12emplace_backIJRKS2_EEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE9push_backEOS2_:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE12emplace_backIJS2_EEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE10push_frontERKS2_:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE13emplace_frontIJRKS2_EEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE10push_frontEOS2_:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE13emplace_frontIJS2_EEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
vecdeque.cpp:_ZeqRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEES5_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
vecdeque.cpp:_ZssRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm1EEEES5_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEC2EOS3_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE4swapERS3_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE11BufferIndexEm:
   76|  1.98M|    {
   77|  1.98M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.98M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.98M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 475k, False: 1.50M]
  ------------------
   81|   475k|            return (m_offset + pos) - m_capacity;
   82|  1.50M|        } else {
   83|  1.50M|            return m_offset + pos;
   84|  1.50M|        }
   85|  1.98M|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEixEm:
  304|  1.00M|    {
  305|  1.00M|        Assume(idx < m_size);
  ------------------
  |  |  128|  1.00M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|  1.00M|        return m_buffer[BufferIndex(idx)];
  307|  1.00M|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|       |        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|       |            m_size = size;
   97|  53.2k|        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|   496k|            while (m_size > size) {
  ------------------
  |  Branch (99:20): [True: 443k, False: 53.2k]
  ------------------
  100|   443k|                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|   443k|                --m_size;
  102|   443k|            }
  103|  53.2k|        }
  104|  53.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|       |            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|       |                size_t first_part = FirstPart();
   49|       |                if (first_part != 0) {
   50|       |                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|       |                }
   52|       |                if (first_part != m_size) {
   53|       |                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|       |                }
   55|  31.3k|            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|  31.3k|                size_t old_pos = m_offset;
   58|   200k|                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
  ------------------
  |  Branch (58:42): [True: 169k, False: 31.3k]
  ------------------
   59|   169k|                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|   169k|                    std::destroy_at(m_buffer + old_pos);
   61|   169k|                    ++old_pos;
   62|   169k|                    if (old_pos == m_capacity) old_pos = 0;
  ------------------
  |  Branch (62:25): [True: 8.31k, False: 161k]
  ------------------
   63|   169k|                }
   64|  31.3k|            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEaSEOS3_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEC2ERKS3_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
vecdeque.cpp:_Z4swapR8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEES4_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEaSERKS3_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|       |        if constexpr (std::is_trivially_copyable_v<T>) {
  142|       |            size_t first_part = other.FirstPart();
  143|       |            Assume(first_part > 0 || m_size == 0);
  144|       |            if (first_part != 0) {
  145|       |                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|       |            }
  147|       |            if (first_part != other.m_size) {
  148|       |                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|       |            }
  150|       |            m_size = other.m_size;
  151|  13.3k|        } else {
  152|   184k|            while (m_size < other.m_size) {
  ------------------
  |  Branch (152:20): [True: 170k, False: 13.3k]
  ------------------
  153|   170k|                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|   170k|                ++m_size;
  155|   170k|            }
  156|  13.3k|        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE9push_backERKS2_:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE12emplace_backIJRKS2_EEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE9push_backEOS2_:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE12emplace_backIJS2_EEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE10push_frontERKS2_:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE13emplace_frontIJRKS2_EEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE10push_frontEOS2_:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE13emplace_frontIJS2_EEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
vecdeque.cpp:_ZeqRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEES5_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
vecdeque.cpp:_ZssRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm3EEEES5_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEC2EOS3_:
  182|  1.80k|    VecDeque(VecDeque&& other) noexcept { swap(other); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE4swapERS3_:
  162|  26.8k|    {
  163|  26.8k|        std::swap(m_buffer, other.m_buffer);
  164|  26.8k|        std::swap(m_offset, other.m_offset);
  165|  26.8k|        std::swap(m_size, other.m_size);
  166|  26.8k|        std::swap(m_capacity, other.m_capacity);
  167|  26.8k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE5frontEv:
  276|  32.7k|    {
  277|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  278|  32.7k|        return m_buffer[m_offset];
  279|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE4backEv:
  290|  32.7k|    {
  291|  32.7k|        Assume(m_size);
  ------------------
  |  |  128|  32.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  292|  32.7k|        return m_buffer[BufferIndex(m_size - 1)];
  293|  32.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE11BufferIndexEm:
   76|  1.98M|    {
   77|  1.98M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.98M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.98M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 475k, False: 1.50M]
  ------------------
   81|   475k|            return (m_offset + pos) - m_capacity;
   82|  1.50M|        } else {
   83|  1.50M|            return m_offset + pos;
   84|  1.50M|        }
   85|  1.98M|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEixEm:
  304|  1.00M|    {
  305|  1.00M|        Assume(idx < m_size);
  ------------------
  |  |  128|  1.00M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  306|  1.00M|        return m_buffer[BufferIndex(idx)];
  307|  1.00M|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE6resizeEm:
  111|  26.7k|    {
  112|  26.7k|        if (size < m_size) {
  ------------------
  |  Branch (112:13): [True: 4.69k, False: 22.0k]
  ------------------
  113|       |            // Delegate to ResizeDown when shrinking.
  114|  4.69k|            ResizeDown(size);
  115|  22.0k|        } else if (size > m_size) {
  ------------------
  |  Branch (115:20): [True: 9.34k, False: 12.7k]
  ------------------
  116|       |            // When growing, first see if we need to allocate more space.
  117|  9.34k|            if (size > m_capacity) Reallocate(size);
  ------------------
  |  Branch (117:17): [True: 4.16k, False: 5.18k]
  ------------------
  118|   273k|            while (m_size < size) {
  ------------------
  |  Branch (118:20): [True: 263k, False: 9.34k]
  ------------------
  119|   263k|                std::construct_at(m_buffer + BufferIndex(m_size));
  120|   263k|                ++m_size;
  121|   263k|            }
  122|  9.34k|        }
  123|  26.7k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|       |        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|       |            m_size = size;
   97|  53.2k|        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|   496k|            while (m_size > size) {
  ------------------
  |  Branch (99:20): [True: 443k, False: 53.2k]
  ------------------
  100|   443k|                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|   443k|                --m_size;
  102|   443k|            }
  103|  53.2k|        }
  104|  53.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|       |            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|       |                size_t first_part = FirstPart();
   49|       |                if (first_part != 0) {
   50|       |                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|       |                }
   52|       |                if (first_part != m_size) {
   53|       |                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|       |                }
   55|  31.3k|            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|  31.3k|                size_t old_pos = m_offset;
   58|   200k|                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
  ------------------
  |  Branch (58:42): [True: 169k, False: 31.3k]
  ------------------
   59|   169k|                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|   169k|                    std::destroy_at(m_buffer + old_pos);
   61|   169k|                    ++old_pos;
   62|   169k|                    if (old_pos == m_capacity) old_pos = 0;
  ------------------
  |  Branch (62:25): [True: 8.31k, False: 161k]
  ------------------
   63|   169k|                }
   64|  31.3k|            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEaSEOS3_:
  174|  18.2k|    {
  175|  18.2k|        swap(other);
  176|  18.2k|        return *this;
  177|  18.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEC2ERKS3_:
  180|  9.75k|    VecDeque(const VecDeque& other) { *this = other; }
vecdeque.cpp:_Z4swapR8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEES4_:
  170|  6.79k|    friend void swap(VecDeque& a, VecDeque& b) noexcept { a.swap(b); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEaSERKS3_:
  137|  15.9k|    {
  138|  15.9k|        if (&other == this) [[unlikely]] return *this;
  ------------------
  |  Branch (138:13): [True: 2.62k, False: 13.3k]
  ------------------
  139|  13.3k|        clear();
  140|  13.3k|        Reallocate(other.m_size);
  141|       |        if constexpr (std::is_trivially_copyable_v<T>) {
  142|       |            size_t first_part = other.FirstPart();
  143|       |            Assume(first_part > 0 || m_size == 0);
  144|       |            if (first_part != 0) {
  145|       |                std::memcpy(m_buffer, other.m_buffer + other.m_offset, first_part * sizeof(T));
  146|       |            }
  147|       |            if (first_part != other.m_size) {
  148|       |                std::memcpy(m_buffer + first_part, other.m_buffer, (other.m_size - first_part) * sizeof(T));
  149|       |            }
  150|       |            m_size = other.m_size;
  151|  13.3k|        } else {
  152|   184k|            while (m_size < other.m_size) {
  ------------------
  |  Branch (152:20): [True: 170k, False: 13.3k]
  ------------------
  153|   170k|                std::construct_at(m_buffer + BufferIndex(m_size), other[m_size]);
  154|   170k|                ++m_size;
  155|   170k|            }
  156|  13.3k|        }
  157|  13.3k|        return *this;
  158|  15.9k|    }
vecdeque.cpp:_ZNK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE8capacityEv:
  314|   202k|    size_t capacity() const noexcept { return m_capacity; }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE13shrink_to_fitEv:
  213|  3.43k|    {
  214|  3.43k|        if (m_capacity > m_size) Reallocate(m_size);
  ------------------
  |  Branch (214:13): [True: 2.06k, False: 1.37k]
  ------------------
  215|  3.43k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE9push_backERKS2_:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE12emplace_backIJRKS2_EEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE9push_backEOS2_:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE12emplace_backIJS2_EEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE12emplace_backIJRmEEEvDpOT_:
  220|  4.51k|    {
  221|  4.51k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 1.91k, False: 2.60k]
  ------------------
  222|  4.51k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.51k|        ++m_size;
  224|  4.51k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE10push_frontERKS2_:
  244|  6.97k|    void push_front(const T& elem) { emplace_front(elem); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE13emplace_frontIJRKS2_EEEvDpOT_:
  235|  6.97k|    {
  236|  6.97k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.07k, False: 4.90k]
  ------------------
  237|  6.97k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  6.97k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.22k, False: 3.74k]
  ------------------
  239|  6.97k|        --m_offset;
  240|  6.97k|        ++m_size;
  241|  6.97k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE10push_frontEOS2_:
  247|  10.5k|    void push_front(T&& elem) { emplace_front(std::move(elem)); }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE13emplace_frontIJS2_EEEvDpOT_:
  235|  10.5k|    {
  236|  10.5k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.28k, False: 8.23k]
  ------------------
  237|  10.5k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  10.5k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.30k, False: 7.20k]
  ------------------
  239|  10.5k|        --m_offset;
  240|  10.5k|        ++m_size;
  241|  10.5k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE13emplace_frontIJRmEEEvDpOT_:
  235|  16.2k|    {
  236|  16.2k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (236:13): [True: 2.17k, False: 14.0k]
  ------------------
  237|  16.2k|        std::construct_at(m_buffer + BufferIndex(m_capacity - 1), std::forward<Args>(args)...);
  238|  16.2k|        if (m_offset == 0) m_offset = m_capacity;
  ------------------
  |  Branch (238:13): [True: 3.57k, False: 12.6k]
  ------------------
  239|  16.2k|        --m_offset;
  240|  16.2k|        ++m_size;
  241|  16.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
vecdeque.cpp:_ZN8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEE8pop_backEv:
  261|  1.96k|    {
  262|  1.96k|        Assume(m_size);
  ------------------
  |  |  128|  1.96k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  263|  1.96k|        std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  264|  1.96k|        --m_size;
  265|  1.96k|    }
vecdeque.cpp:_ZeqRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEES5_:
  186|  6.42k|    {
  187|  6.42k|        if (a.m_size != b.m_size) return false;
  ------------------
  |  Branch (187:13): [True: 1.48k, False: 4.94k]
  ------------------
  188|  58.0k|        for (size_t i = 0; i < a.m_size; ++i) {
  ------------------
  |  Branch (188:28): [True: 53.3k, False: 4.71k]
  ------------------
  189|  53.3k|            if (a[i] != b[i]) return false;
  ------------------
  |  Branch (189:17): [True: 226, False: 53.1k]
  ------------------
  190|  53.3k|        }
  191|  4.71k|        return true;
  192|  4.94k|    }
vecdeque.cpp:_ZssRK8VecDequeIN12_GLOBAL__N_110TrackedObjILm17EEEES5_:
  196|  12.8k|    {
  197|  12.8k|        size_t pos_a{0}, pos_b{0};
  198|   119k|        while (pos_a < a.m_size && pos_b < b.m_size) {
  ------------------
  |  Branch (198:16): [True: 110k, False: 9.57k]
  |  Branch (198:36): [True: 107k, False: 2.52k]
  ------------------
  199|   107k|            auto cmp = a[pos_a++] <=> b[pos_b++];
  200|   107k|            if (cmp != 0) return cmp;
  ------------------
  |  Branch (200:17): [True: 736, False: 107k]
  ------------------
  201|   107k|        }
  202|  12.1k|        return a.m_size <=> b.m_size;
  203|  12.8k|    }
_ZN8VecDequeIhEC2Ev:
  107|  13.1k|    VecDeque() noexcept = default;
_ZN8VecDequeIhE7reserveEm:
  207|  14.0k|    {
  208|  14.0k|        if (capacity > m_capacity) Reallocate(capacity);
  ------------------
  |  Branch (208:13): [True: 990, False: 13.0k]
  ------------------
  209|  14.0k|    }
_ZN8VecDequeIhE10ReallocateEm:
   40|  58.7k|    {
   41|  58.7k|        Assume(capacity >= m_size);
  ------------------
  |  |  128|  58.7k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   42|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   198k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 49.9k, False: 8.72k]
  |  |  |  Branch (128:51): [True: 27.3k, False: 22.6k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   43|       |        // Allocate new buffer.
   44|  58.7k|        T* new_buffer = capacity ? std::allocator<T>().allocate(capacity) : nullptr;
  ------------------
  |  Branch (44:25): [True: 31.3k, False: 27.3k]
  ------------------
   45|  58.7k|        if (capacity) {
  ------------------
  |  Branch (45:13): [True: 31.3k, False: 27.3k]
  ------------------
   46|  31.3k|            if constexpr (std::is_trivially_copyable_v<T>) {
   47|       |                // When T is trivially copyable, just copy the data over from old to new buffer.
   48|  31.3k|                size_t first_part = FirstPart();
   49|  31.3k|                if (first_part != 0) {
  ------------------
  |  Branch (49:21): [True: 9.45k, False: 21.8k]
  ------------------
   50|  9.45k|                    std::memcpy(new_buffer, m_buffer + m_offset, first_part * sizeof(T));
   51|  9.45k|                }
   52|  31.3k|                if (first_part != m_size) {
  ------------------
  |  Branch (52:21): [True: 2.04k, False: 29.3k]
  ------------------
   53|  2.04k|                    std::memcpy(new_buffer + first_part, m_buffer, (m_size - first_part) * sizeof(T));
   54|  2.04k|                }
   55|       |            } else {
   56|       |                // Otherwise move-construct in place in the new buffer, and destroy old buffer objects.
   57|       |                size_t old_pos = m_offset;
   58|       |                for (size_t new_pos = 0; new_pos < m_size; ++new_pos) {
   59|       |                    std::construct_at(new_buffer + new_pos, std::move(*(m_buffer + old_pos)));
   60|       |                    std::destroy_at(m_buffer + old_pos);
   61|       |                    ++old_pos;
   62|       |                    if (old_pos == m_capacity) old_pos = 0;
   63|       |                }
   64|       |            }
   65|  31.3k|        }
   66|       |        // Deallocate old buffer and update housekeeping.
   67|  58.7k|        std::allocator<T>().deallocate(m_buffer, m_capacity);
   68|  58.7k|        m_buffer = new_buffer;
   69|  58.7k|        m_offset = 0;
   70|  58.7k|        m_capacity = capacity;
   71|  58.7k|        Assume((m_offset == 0 && m_capacity == 0) || m_offset < m_capacity);
  ------------------
  |  |  128|   207k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  |  |  ------------------
  |  |  |  Branch (128:51): [True: 58.7k, False: 0]
  |  |  |  Branch (128:51): [True: 27.3k, False: 31.3k]
  |  |  |  Branch (128:51): [True: 31.3k, False: 0]
  |  |  ------------------
  ------------------
   72|  58.7k|    }
_ZNK8VecDequeIhE9FirstPartEv:
   37|  44.7k|    size_t FirstPart() const noexcept { return std::min(m_capacity - m_offset, m_size); }
_ZNK8VecDequeIhE5emptyEv:
  310|  67.5k|    bool empty() const noexcept { return m_size == 0; }
_ZNK8VecDequeIhE11BufferIndexEm:
   76|  1.19M|    {
   77|  1.19M|        Assume(pos < m_capacity);
  ------------------
  |  |  128|  1.19M|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   78|       |        // The expression below is used instead of the more obvious (pos + m_offset >= m_capacity),
   79|       |        // because the addition there could in theory overflow with very large deques.
   80|  1.19M|        if (pos >= m_capacity - m_offset) {
  ------------------
  |  Branch (80:13): [True: 311k, False: 886k]
  ------------------
   81|   311k|            return (m_offset + pos) - m_capacity;
   82|   886k|        } else {
   83|   886k|            return m_offset + pos;
   84|   886k|        }
   85|  1.19M|    }
_ZNK8VecDequeIhE4sizeEv:
  312|   380k|    size_t size() const noexcept { return m_size; }
_ZN8VecDequeIhE4backEv:
  283|  4.71k|    {
  284|  4.71k|        Assume(m_size);
  ------------------
  |  |  128|  4.71k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  285|  4.71k|        return m_buffer[BufferIndex(m_size - 1)];
  286|  4.71k|    }
_ZN8VecDequeIhEixEm:
  297|  8.18k|    {
  298|  8.18k|        Assume(idx < m_size);
  ------------------
  |  |  128|  8.18k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  299|  8.18k|        return m_buffer[BufferIndex(idx)];
  300|  8.18k|    }
_ZN8VecDequeIhE5frontEv:
  269|  41.6k|    {
  270|  41.6k|        Assume(m_size);
  ------------------
  |  |  128|  41.6k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  271|  41.6k|        return m_buffer[m_offset];
  272|  41.6k|    }
_ZN8VecDequeIhE9pop_frontEv:
  251|  38.2k|    {
  252|  38.2k|        Assume(m_size);
  ------------------
  |  |  128|  38.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
  253|  38.2k|        std::destroy_at(m_buffer + m_offset);
  254|  38.2k|        --m_size;
  255|  38.2k|        ++m_offset;
  256|  38.2k|        if (m_offset == m_capacity) m_offset = 0;
  ------------------
  |  Branch (256:13): [True: 2.09k, False: 36.1k]
  ------------------
  257|  38.2k|    }
_ZN8VecDequeIhE9push_backERKh:
  230|  5.93k|    void push_back(const T& elem) { emplace_back(elem); }
_ZN8VecDequeIhE12emplace_backIJRKhEEEvDpOT_:
  220|  5.93k|    {
  221|  5.93k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.84k, False: 3.08k]
  ------------------
  222|  5.93k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  5.93k|        ++m_size;
  224|  5.93k|    }
_ZN8VecDequeIhE9push_backEOh:
  227|  4.53k|    void push_back(T&& elem) { emplace_back(std::move(elem)); }
_ZN8VecDequeIhE12emplace_backIJhEEEvDpOT_:
  220|  4.53k|    {
  221|  4.53k|        if (m_size == m_capacity) Reallocate((m_size + 1) * 2);
  ------------------
  |  Branch (221:13): [True: 2.17k, False: 2.35k]
  ------------------
  222|  4.53k|        std::construct_at(m_buffer + BufferIndex(m_size), std::forward<Args>(args)...);
  223|  4.53k|        ++m_size;
  224|  4.53k|    }
_ZN8VecDequeIhED2Ev:
  130|  24.6k|    {
  131|  24.6k|        clear();
  132|  24.6k|        Reallocate(0);
  133|  24.6k|    }
_ZN8VecDequeIhE5clearEv:
  126|  48.5k|    void clear() noexcept { ResizeDown(0); }
_ZN8VecDequeIhE10ResizeDownEm:
   90|  53.2k|    {
   91|  53.2k|        Assume(size <= m_size);
  ------------------
  |  |  128|  53.2k|#define Assume(val) inline_assertion_check<false>(val, std::source_location::current(), #val)
  ------------------
   92|  53.2k|        if constexpr (std::is_trivially_destructible_v<T>) {
   93|       |            // If T is trivially destructible, we do not need to do anything but update the
   94|       |            // housekeeping record. Default constructor or zero-filling will be used when
   95|       |            // the space is reused.
   96|  53.2k|            m_size = size;
   97|       |        } else {
   98|       |            // If not, we need to invoke the destructor for every element separately.
   99|       |            while (m_size > size) {
  100|       |                std::destroy_at(m_buffer + BufferIndex(m_size - 1));
  101|       |                --m_size;
  102|       |            }
  103|       |        }
  104|  53.2k|    }

_ZN19WalletInitInterfaceD2Ev:
   25|      2|    virtual ~WalletInitInterface() = default;

