aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordergoegge <n.goeggi@gmail.com>2024-02-06 17:07:48 +0000
committerglozow <gloriajzhao@gmail.com>2024-03-05 10:24:16 +0000
commit50c0b61a9d562240d5fe4bd79324b0c0e79caa5c (patch)
tree88a0c2f54bbdb927c626164a6e8a6a246915570c
parentaff368fa817b065d99729186d304fff02f6e527b (diff)
[validation] Merkle root malleation should be caught by IsBlockMutated
Github-Pull: #29412 Rebased-From: 2d8495e0800f5332748cd50eaad801ff77671bba
-rw-r--r--src/test/validation_tests.cpp5
-rw-r--r--src/validation.cpp13
2 files changed, 17 insertions, 1 deletions
diff --git a/src/test/validation_tests.cpp b/src/test/validation_tests.cpp
index 14440571eb..cb7d1a312f 100644
--- a/src/test/validation_tests.cpp
+++ b/src/test/validation_tests.cpp
@@ -4,12 +4,17 @@
#include <chainparams.h>
#include <consensus/amount.h>
+#include <consensus/merkle.h>
+#include <core_io.h>
+#include <hash.h>
#include <net.h>
#include <signet.h>
#include <uint256.h>
#include <util/chaintype.h>
#include <validation.h>
+#include <string>
+
#include <test/util/setup_common.h>
#include <boost/test/unit_test.hpp>
diff --git a/src/validation.cpp b/src/validation.cpp
index 1ad4ebcdaa..a2128b231e 100644
--- a/src/validation.cpp
+++ b/src/validation.cpp
@@ -3815,7 +3815,18 @@ bool IsBlockMutated(const CBlock& block, bool check_witness_root)
}
if (block.vtx.empty() || !block.vtx[0]->IsCoinBase()) {
- return false;
+ // Consider the block mutated if any transaction is 64 bytes in size (see 3.1
+ // in "Weaknesses in Bitcoin’s Merkle Root Construction":
+ // https://lists.linuxfoundation.org/pipermail/bitcoin-dev/attachments/20190225/a27d8837/attachment-0001.pdf).
+ //
+ // Note: This is not a consensus change as this only applies to blocks that
+ // don't have a coinbase transaction and would therefore already be invalid.
+ return std::any_of(block.vtx.begin(), block.vtx.end(),
+ [](auto& tx) { return ::GetSerializeSize(tx, PROTOCOL_VERSION | SERIALIZE_TRANSACTION_NO_WITNESS) == 64; });
+ } else {
+ // Theoretically it is still possible for a block with a 64 byte
+ // coinbase transaction to be mutated but we neglect that possibility
+ // here as it requires at least 224 bits of work.
}
if (!CheckWitnessMalleation(block, check_witness_root, state)) {