refactor: C++20 operators #33771

pull purpleKarrot wants to merge 2 commits into bitcoin:master from purpleKarrot:cxx20-operators changing 14 files +7 −106
  1. purpleKarrot commented at 1:49 pm on November 3, 2025: contributor

    Remove all operator!= definitions and provide operator<=> as a replacement where all relational comparison operators were defined before.

    The compiler is able to deduce missing comparison operators from operator!= and operator<=>. The compiler provided operators have the following advantages:

    1. less code
    2. guaranteed consistency

    Refactoring that changes the implementation, or replaces it with = default is left for a separate PR.

  2. refactor: Remove all `operator!=` definitions
    The compiler can deduce `operator!=` from `operator==`.
    5a0f49bd26
  3. refactor: Prefer `<=>` over multiple relational operators
    Define `operator<=>` in classes that have all of `<`, `<=`, `>`, `>=`.
    48840bfc2d
  4. DrahtBot added the label Refactoring on Nov 3, 2025
  5. DrahtBot commented at 1:49 pm on November 3, 2025: contributor

    The following sections might be updated with supplementary metadata relevant to reviewers and maintainers.

    Code Coverage & Benchmarks

    For details see: https://corecheck.dev/bitcoin/bitcoin/pulls/33771.

    Reviews

    See the guideline for information on the review process.

    Type Reviewers
    ACK stickies-v, optout21, janb84, Chand-ra, maflcko, sipa

    If your review is incorrectly listed, please copy-paste <!–meta-tag:bot-skip–> into the comment that the bot should ignore.

    Conflicts

    Reviewers, this pull request conflicts with the following ones:

    • #33772 (prevector: simplify implementation of comparison operators and match behavior of std::vector by purpleKarrot)
    • #33711 (transaction: Adding script witness to ToString for CTxIn by Ataraxia009)

    If you consider this pull request important, please also help to review the conflicting pull requests. Ideally, start with the one that should be merged first.

  6. in src/script/script.h:273 in 48840bfc2d
    269@@ -270,18 +270,10 @@ class CScriptNum
    270     }
    271 
    272     inline bool operator==(const int64_t& rhs) const    { return m_value == rhs; }
    273-    inline bool operator!=(const int64_t& rhs) const    { return m_value != rhs; }
    274-    inline bool operator<=(const int64_t& rhs) const    { return m_value <= rhs; }
    275-    inline bool operator< (const int64_t& rhs) const    { return m_value <  rhs; }
    276-    inline bool operator>=(const int64_t& rhs) const    { return m_value >= rhs; }
    277-    inline bool operator> (const int64_t& rhs) const    { return m_value >  rhs; }
    278+    inline auto operator<=>(const int64_t& rhs) const    { return m_value <=> rhs; }
    


    stickies-v commented at 4:19 pm on November 3, 2025:

    nit (here and for all other new operator<=>): perhaps better to be explicit about the std::strong_ordering return type? And perhaps making it constexpr while touching?

      0diff --git a/src/prevector.h b/src/prevector.h
      1index d4d90c7350..595be4a603 100644
      2--- a/src/prevector.h
      3+++ b/src/prevector.h
      4@@ -7,6 +7,7 @@
      5 
      6 #include <algorithm>
      7 #include <cassert>
      8+#include <compare>
      9 #include <cstddef>
     10 #include <cstdint>
     11 #include <cstdlib>
     12@@ -71,8 +72,8 @@ public:
     13         iterator& operator+=(size_type n) { ptr += n; return *this; }
     14         iterator operator-(size_type n) const { return iterator(ptr - n); }
     15         iterator& operator-=(size_type n) { ptr -= n; return *this; }
     16-        bool operator==(iterator x) const { return ptr == x.ptr; }
     17-        auto operator<=>(iterator x) const { return ptr <=> x.ptr; }
     18+        constexpr bool operator==(iterator x) const { return ptr == x.ptr; }
     19+        constexpr std::strong_ordering operator<=>(iterator x) const { return ptr <=> x.ptr; }
     20     };
     21 
     22     class const_iterator {
     23@@ -99,8 +100,8 @@ public:
     24         const_iterator& operator+=(size_type n) { ptr += n; return *this; }
     25         const_iterator operator-(size_type n) const { return const_iterator(ptr - n); }
     26         const_iterator& operator-=(size_type n) { ptr -= n; return *this; }
     27-        bool operator==(const_iterator x) const { return ptr == x.ptr; }
     28-        auto operator<=>(const_iterator x) const { return ptr <=> x.ptr; }
     29+        constexpr bool operator==(const_iterator x) const { return ptr == x.ptr; }
     30+        constexpr std::strong_ordering operator<=>(const_iterator x) const { return ptr <=> x.ptr; }
     31     };
     32 
     33 private:
     34diff --git a/src/script/script.h b/src/script/script.h
     35index b06be9c975..f1472a7dd3 100644
     36--- a/src/script/script.h
     37+++ b/src/script/script.h
     38@@ -14,6 +14,7 @@
     39 #include <util/hash_type.h>
     40 
     41 #include <cassert>
     42+#include <compare>
     43 #include <cstdint>
     44 #include <cstring>
     45 #include <limits>
     46@@ -269,11 +270,11 @@ public:
     47         m_value = set_vch(vch);
     48     }
     49 
     50-    inline bool operator==(const int64_t& rhs) const    { return m_value == rhs; }
     51-    inline auto operator<=>(const int64_t& rhs) const    { return m_value <=> rhs; }
     52+    inline constexpr bool operator==(const int64_t& rhs) const    { return m_value == rhs; }
     53+    inline constexpr std::strong_ordering operator<=>(const int64_t& rhs) const    { return m_value <=> rhs; }
     54 
     55-    inline bool operator==(const CScriptNum& rhs) const { return operator==(rhs.m_value); }
     56-    inline auto operator<=>(const CScriptNum& rhs) const { return operator<=>(rhs.m_value); }
     57+    inline constexpr bool operator==(const CScriptNum& rhs) const { return operator==(rhs.m_value); }
     58+    inline constexpr std::strong_ordering operator<=>(const CScriptNum& rhs) const { return operator<=>(rhs.m_value); }
     59 
     60     inline CScriptNum operator+(   const int64_t& rhs)    const { return CScriptNum(m_value + rhs);}
     61     inline CScriptNum operator-(   const int64_t& rhs)    const { return CScriptNum(m_value - rhs);}
     62diff --git a/src/test/scriptnum10.h b/src/test/scriptnum10.h
     63index 402606714d..fd112d6ff7 100644
     64--- a/src/test/scriptnum10.h
     65+++ b/src/test/scriptnum10.h
     66@@ -7,6 +7,7 @@
     67 #define BITCOIN_TEST_SCRIPTNUM10_H
     68 
     69 #include <cassert>
     70+#include <compare>
     71 #include <cstdint>
     72 #include <limits>
     73 #include <stdexcept>
     74@@ -60,11 +61,11 @@ public:
     75         m_value = set_vch(vch);
     76     }
     77 
     78-    inline bool operator==(const int64_t& rhs) const    { return m_value == rhs; }
     79-    inline auto operator<=>(const int64_t& rhs) const    { return m_value <=> rhs; }
     80+    inline constexpr bool operator==(const int64_t& rhs) const    { return m_value == rhs; }
     81+    inline constexpr std::strong_ordering operator<=>(const int64_t& rhs) const    { return m_value <=> rhs; }
     82 
     83-    inline bool operator==(const CScriptNum10& rhs) const { return operator==(rhs.m_value); }
     84-    inline auto operator<=>(const CScriptNum10& rhs) const { return operator<=>(rhs.m_value); }
     85+    inline constexpr bool operator==(const CScriptNum10& rhs) const { return operator==(rhs.m_value); }
     86+    inline constexpr std::strong_ordering operator<=>(const CScriptNum10& rhs) const { return operator<=>(rhs.m_value); }
     87 
     88     inline CScriptNum10 operator+(   const int64_t& rhs)    const { return CScriptNum10(m_value + rhs);}
     89     inline CScriptNum10 operator-(   const int64_t& rhs)    const { return CScriptNum10(m_value - rhs);}
     90diff --git a/src/util/bitdeque.h b/src/util/bitdeque.h
     91index 21934e02da..be3e0fd859 100644
     92--- a/src/util/bitdeque.h
     93+++ b/src/util/bitdeque.h
     94@@ -6,6 +6,7 @@
     95 #define BITCOIN_UTIL_BITDEQUE_H
     96 
     97 #include <bitset>
     98+#include <compare>
     99 #include <cstddef>
    100 #include <deque>
    101 #include <limits>
    102@@ -99,8 +100,8 @@ class bitdeque
    103         friend Iterator operator+(Iterator x, difference_type dist) { x += dist; return x; }
    104         friend Iterator operator+(difference_type dist, Iterator x) { x += dist; return x; }
    105         friend Iterator operator-(Iterator x, difference_type dist) { x -= dist; return x; }
    106-        friend auto operator<=>(const Iterator& x, const Iterator& y) { return std::tie(x.m_it, x.m_bitpos) <=> std::tie(y.m_it, y.m_bitpos); }
    107-        friend bool operator==(const Iterator& x, const Iterator& y) { return x.m_it == y.m_it && x.m_bitpos == y.m_bitpos; }
    108+        friend constexpr std::strong_ordering operator<=>(const Iterator& x, const Iterator& y) { return std::tie(x.m_it, x.m_bitpos) <=> std::tie(y.m_it, y.m_bitpos); }
    109+        friend constexpr bool operator==(const Iterator& x, const Iterator& y) { return x.m_it == y.m_it && x.m_bitpos == y.m_bitpos; }
    110         reference operator*() const { return (*m_it)[m_bitpos]; }
    111         reference operator[](difference_type pos) const { return *(*this + pos); }
    112     };
    

    purpleKarrot commented at 5:23 pm on November 3, 2025:

    Thanks @stickies-v.

    I am not convinced about std::strong_ordering. constexpr will definitely be added as a follow up, together with = default where appropriate.

  7. stickies-v approved
  8. stickies-v commented at 4:19 pm on November 3, 2025: contributor
    utACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936. Pretty straightforward cleanup taking advantage of C++20 improvements, nice.
  9. optout21 commented at 2:37 pm on November 11, 2025: none

    utACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936

    Straightforward refactoring resulting in code removal 😎 First commit removes != operator where == exits. Second commit replaces 4 comparison operators with the new <=> spaceship operator. My only concern is that competence with the new <=> operator may not be extensive across the developer community of this project, but hey, it’s time to learn!

  10. optout21 commented at 2:38 pm on November 11, 2025: none
    I wonder whether it would it be possible check for superfluous comparison operator implementations in linting?
  11. janb84 commented at 3:40 pm on December 1, 2025: contributor

    ACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936

    Reducing custom handwritten boilerplate and replacing it with modern idioms is not something we should shun to do (imho). Using the spaceship operation <=> will use the compiler to generate the other operators correctly.

    Was a bit worried that the spaceship did not yet land on apple clang, given the documentation

    But it compiles fine on MacOS 26 :

     0
     1100% tests passed, 0 tests failed out of 134
     2
     3Total Test time (real) =  82.35 sec
     4
     5The following tests did not run:
     6         89 - script_assets_tests (Skipped)
     7arjan@M1-Max bitcoin % utest
     8zsh: command not found: utest
     9arjan@M1-Max bitcoin % ./build/bin/test_bitcoin
    10Running 625 test cases...
    11
    12*** No errors detected
    

    This line makes me unsure if the support is there for older systems:

    Guix (SKD 15) also builds fine:

    Host architecture: aarch64 Commit: 48840bfc2d7b

     0 7ae74e91099585fab44a8eba15b66a1cd70e9ec615255a8418e12c113cd2b22f guix-build-48840bfc2d7b/output/aarch64-linux-gnu/SHA256SUMS.part 
     1 328f5720e716f8dc6c07155c3b0e263a0c3bb08083e1afc5b9d7819d88edcae1 guix-build-48840bfc2d7b/output/aarch64-linux-gnu/bitcoin-48840bfc2d7b-aarch64-linux-gnu-debug.tar.gz 
     2 364f8b5fed3df38c4e5e0f36081ea0ab752e1d842ee6aa8ef79630b644865dfd guix-build-48840bfc2d7b/output/aarch64-linux-gnu/bitcoin-48840bfc2d7b-aarch64-linux-gnu.tar.gz 
     3 d600f7a4cf2c0f913b493ca26afb6818873cf7cb4c4aaff8be9ba5356ae5aeb0 guix-build-48840bfc2d7b/output/arm-linux-gnueabihf/SHA256SUMS.part 
     4 18e399e645ee0d130d306e2d28c20ca256ae4c82c0eb097cd5af6d45ed23fad5 guix-build-48840bfc2d7b/output/arm-linux-gnueabihf/bitcoin-48840bfc2d7b-arm-linux-gnueabihf-debug.tar.gz 
     5 aff5f14e0ff6e8c7086adbb7ccf31515a15040e0d882659d33a4a828ac9cfd77 guix-build-48840bfc2d7b/output/arm-linux-gnueabihf/bitcoin-48840bfc2d7b-arm-linux-gnueabihf.tar.gz 
     6 1c259381c2db38ea7aa7dd1d0503a73d3af9e3d5c7fb1f0debdda8c3f0378d1c guix-build-48840bfc2d7b/output/arm64-apple-darwin/SHA256SUMS.part 
     7 ddf9c751d147b766dbc0ee4dff424f812c8c3717998eeab24ec63fc9f85c82c7 guix-build-48840bfc2d7b/output/arm64-apple-darwin/bitcoin-48840bfc2d7b-arm64-apple-darwin-codesigning.tar.gz 
     8 02f0b34dd9b87400c12a945e337912c806dffb4c4243e6f5dcacd52c3fc6ad7f guix-build-48840bfc2d7b/output/arm64-apple-darwin/bitcoin-48840bfc2d7b-arm64-apple-darwin-unsigned.tar.gz 
     9 e942a32dc63461b5e99e7745026115e45b03bd8fc76741b8ab20c56e42488820 guix-build-48840bfc2d7b/output/arm64-apple-darwin/bitcoin-48840bfc2d7b-arm64-apple-darwin-unsigned.zip 
    10 788f9ced2fbac52f2291c360e77067c56aa503a7172b6787309ac0b6d9974efe guix-build-48840bfc2d7b/output/dist-archive/bitcoin-48840bfc2d7b.tar.gz 
    11 2bf8e1dedd00f91597abc93dd08d067f47dba4e5eebab7f2ac5d11fcbaff4256 guix-build-48840bfc2d7b/output/powerpc64-linux-gnu/SHA256SUMS.part 
    12 2feefe7552a90c8b2206566e3d0c14896dc1bfa2a80794ae618132edaf5122e9 guix-build-48840bfc2d7b/output/powerpc64-linux-gnu/bitcoin-48840bfc2d7b-powerpc64-linux-gnu-debug.tar.gz 
    13 4c3bbbe588d28bf03a72f01ec06235e5477d35e8c6522c48fec685d77493a609 guix-build-48840bfc2d7b/output/powerpc64-linux-gnu/bitcoin-48840bfc2d7b-powerpc64-linux-gnu.tar.gz 
    14 15a1e20e3f6ca4860d2d8828e8764720bb4f163d7f07080d109ff356854c8266 guix-build-48840bfc2d7b/output/riscv64-linux-gnu/SHA256SUMS.part 
    15 680a35ced59259d97000d941795edda383ce6f535f876008753e0a437a7ba3a1 guix-build-48840bfc2d7b/output/riscv64-linux-gnu/bitcoin-48840bfc2d7b-riscv64-linux-gnu-debug.tar.gz 
    16 baaca17bb5e75998486dbb89d8e11326f90c71c284e35733247625e4cdef43bf guix-build-48840bfc2d7b/output/riscv64-linux-gnu/bitcoin-48840bfc2d7b-riscv64-linux-gnu.tar.gz 
    17 012f1b4f8c76758c16f72fdfc47777e3253c5ba0733d6a97190bac760c7753ee guix-build-48840bfc2d7b/output/x86_64-apple-darwin/SHA256SUMS.part 
    18 16bc8a00df772b3b5a379bdee25f894ca6f2f85944c3def500ab0387ec1581c2 guix-build-48840bfc2d7b/output/x86_64-apple-darwin/bitcoin-48840bfc2d7b-x86_64-apple-darwin-codesigning.tar.gz 
    19 7f38f933235fe2c97e1267b39769d3932ab230c4f7807b37812f405a3852cca4 guix-build-48840bfc2d7b/output/x86_64-apple-darwin/bitcoin-48840bfc2d7b-x86_64-apple-darwin-unsigned.tar.gz 
    20 3788cb3a019886c703f8718e7d5f240264f867e5702a28a1743a7f3006919e13 guix-build-48840bfc2d7b/output/x86_64-apple-darwin/bitcoin-48840bfc2d7b-x86_64-apple-darwin-unsigned.zip 
    21 f2a81cc5dece9e21410f0a19c1aefa2faddfca33093ec98c021dbd4b75fca4c8 guix-build-48840bfc2d7b/output/x86_64-linux-gnu/SHA256SUMS.part 
    22 102e27dbbde0b7c0708f7acea622bc2251191d26e77338f4fd12a2c4a1f64612 guix-build-48840bfc2d7b/output/x86_64-linux-gnu/bitcoin-48840bfc2d7b-x86_64-linux-gnu-debug.tar.gz 
    23 a6ceac36f0d0584f68cbb56d4a6f539857a475349c22c623a07e4dd2d59ee356 guix-build-48840bfc2d7b/output/x86_64-linux-gnu/bitcoin-48840bfc2d7b-x86_64-linux-gnu.tar.gz 
    24 e6507f4368396f2a1437be9ef0a757440524990d2bc98b6e5f7661f3c15597b2 guix-build-48840bfc2d7b/output/x86_64-w64-mingw32/SHA256SUMS.part 
    25 732a99e42f7a9515f6c796fb4221cc19bcbc26a1db33b2a83fa3c807b3e8cc35 guix-build-48840bfc2d7b/output/x86_64-w64-mingw32/bitcoin-48840bfc2d7b-win64-codesigning.tar.gz 
    26 828abc438986151f4959996717d469e04ac534f6bf98a0a280e807c61801882c guix-build-48840bfc2d7b/output/x86_64-w64-mingw32/bitcoin-48840bfc2d7b-win64-debug.zip 
    27 76d57ff1512d9eab0a7804aa227db1d93333f17564e612e276d5c6a0fe89ff51 guix-build-48840bfc2d7b/output/x86_64-w64-mingw32/bitcoin-48840bfc2d7b-win64-setup-unsigned.exe 
    28 0924cd8c4ba99b2be857d494be2d32ed6bd134cfe99b8b7b9c53a0abfa095956 guix-build-48840bfc2d7b/output/x86_64-w64-mingw32/bitcoin-48840bfc2d7b-win64-unsigned.zip 
    

    benchmarks: this PR:

    ns/op op/s err% total benchmark
    3.66 273,207,365.58 0.9% 0.01 PrevectorClearNontrivial
    5.47 182,981,087.16 1.9% 0.01 PrevectorClearTrivial
    221.03 4,524,203.13 1.3% 0.01 PrevectorDeserializeNontrivial
    12.88 77,654,787.98 1.0% 0.01 PrevectorDeserializeTrivial
    - - - - :boom: PrevectorDestructorNontrivial (iterations overflow. Maybe your code got optimized away?)
    - - - - :boom: PrevectorDestructorTrivial (iterations overflow. Maybe your code got optimized away?)
    1,148.86 870,426.34 1.5% 0.01 PrevectorFillVectorDirectNontrivial
    297.98 3,355,948.40 1.2% 0.01 PrevectorFillVectorDirectTrivial
    4,150.18 240,953.25 0.3% 0.01 PrevectorFillVectorIndirectNontrivial
    4,003.70 249,768.73 4.7% 0.01 PrevectorFillVectorIndirectTrivial
    1.89 528,716,700.36 0.6% 0.01 PrevectorResizeNontrivial
    2.85 350,494,388.31 0.4% 0.01 PrevectorResizeTrivial
    ns/job job/s err% total benchmark
    225.66 4,431,399.41 4.6% 0.09 CCheckQueueSpeedPrevectorJob

    Master:

    ns/op op/s err% total benchmark
    3.63 275,735,101.26 0.1% 0.01 PrevectorClearNontrivial
    5.32 187,794,641.77 0.1% 0.01 PrevectorClearTrivial
    219.86 4,548,382.05 0.9% 0.01 PrevectorDeserializeNontrivial
    11.71 85,371,714.77 0.8% 0.01 PrevectorDeserializeTrivial
    - - - - :boom: PrevectorDestructorNontrivial (iterations overflow. Maybe your code got optimized away?)
    - - - - :boom: PrevectorDestructorTrivial (iterations overflow. Maybe your code got optimized away?)
    1,372.81 728,434.76 3.6% 0.01 PrevectorFillVectorDirectNontrivial
    315.76 3,166,924.15 2.1% 0.01 PrevectorFillVectorDirectTrivial
    4,324.56 231,237.32 1.2% 0.01 PrevectorFillVectorIndirectNontrivial
    3,856.83 259,280.23 1.1% 0.01 PrevectorFillVectorIndirectTrivial
    1.85 539,265,429.27 0.3% 0.01 PrevectorResizeNontrivial
    2.72 367,563,122.86 0.6% 0.01 PrevectorResizeTrivial
    ns/job job/s err% total benchmark
    258.39 3,870,177.88 4.8% 0.10 CCheckQueueSpeedPrevectorJob
  12. fanquake requested review from maflcko on Dec 5, 2025
  13. Chand-ra commented at 8:37 am on December 8, 2025: none

    tACK 48840bf. Built the PR and ran unit tests; everything passes.

    Verified that all instances of operator!= have been removed and operator<=> replaces combined implementations of <, <=, >, and >=. (Note: PR #33772 and not this one gets rid of operator< in src/prevector.h.)

  14. maflcko commented at 3:54 pm on December 8, 2025: member

    review ACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936 🌖

    Signature:

    0untrusted comment: signature from minisign secret key on empty file; verify via: minisign -Vm "${path_to_any_empty_file}" -P RWTRmVTMeKV5noAMqVlsMugDDCyyTSbA3Re5AkUrhvLVln0tSaFWglOw -x "${path_to_this_whole_four_line_signature_blob}"
    1RUTRmVTMeKV5npGrKx1nqXCw5zeVHdtdYURB/KlyA/LMFgpNCs+SkW9a8N95d+U4AP1RJMi+krxU1A3Yux4bpwZNLvVBKy0wLgM=
    2trusted comment: review ACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936 🌖
    3RJCzzHS7aZcc9j1dS+BlIns6fkD9vUnjg/5rVEcIpZ07JGtNbdDramcmgcbbznLHZYBJgSUdVocxGNYeupAnCw==
    
  15. sipa commented at 4:36 pm on December 8, 2025: member

    ACK 48840bfc2d7beeac0ddf56a3c26b243156ec8936

    ultra-nit: I think the commit message “The compiler can deduce” is misleading. Of course it can, but the point isn’t that it can, it’s that the language spec says it must.

  16. fanquake merged this on Dec 8, 2025
  17. fanquake closed this on Dec 8, 2025

  18. maflcko commented at 12:37 pm on December 9, 2025: member

    I think there are some missed cases. It could make sense to include them in a follow-up?

     0diff --git a/src/kernel/bitcoinkernel_wrapper.h b/src/kernel/bitcoinkernel_wrapper.h
     1index 3fb90da7a9..055ea83808 100644
     2--- a/src/kernel/bitcoinkernel_wrapper.h
     3+++ b/src/kernel/bitcoinkernel_wrapper.h
     4@@ -465,14 +465,9 @@ private:
     5     TxidApi() = default;
     6 
     7 public:
     8-    bool operator==(const TxidApi& other) const
     9+    friend bool operator==(const Derived& lhs, const Derived& rhs)
    10     {
    11-        return btck_txid_equals(impl(), other.impl()) != 0;
    12-    }
    13-
    14-    bool operator!=(const TxidApi& other) const
    15-    {
    16-        return btck_txid_equals(impl(), other.impl()) == 0;
    17+        return btck_txid_equals(lhs.get(), rhs.get()) != 0;
    18     }
    19 
    20     std::array<std::byte, 32> ToBytes() const
    21@@ -665,14 +660,9 @@ private:
    22     }
    23 
    24 public:
    25-    bool operator==(const Derived& other) const
    26-    {
    27-        return btck_block_hash_equals(impl(), other.get()) != 0;
    28-    }
    29-
    30-    bool operator!=(const Derived& other) const
    31+    friend bool operator==(const Derived& lhs, const Derived& rhs)
    32     {
    33-        return btck_block_hash_equals(impl(), other.get()) == 0;
    34+        return btck_block_hash_equals(lhs.get(), rhs.get()) != 0;
    35     }
    36 
    37     std::array<std::byte, 32> ToBytes() const
    

github-metadata-mirror

This is a metadata mirror of the GitHub repository bitcoin/bitcoin. This site is not affiliated with GitHub. Content is generated from a GitHub metadata backup.
generated: 2025-12-13 18:12 UTC

This site is hosted by @0xB10C
More mirrored repositories can be found on mirror.b10c.me