Bitcoin Merkle Root Calculation

首先放一张Merkle Tree的概念示意图:

直接看例子:

以Block 100008为例:

https://btc.com/btc/block/000000000002dfb177c4acd494b3dd73b9abece24df11c62bb614a8c6c5665e2

可以看到只有两个交易。一个是Coinbase给了矿工,另一个是一次转账。非常标准的区块。

这里已经给出了两个交易的哈希。我们也可以深入看看交易的具体内容:

Coinbase交易:

点击体积旁边的蓝色小字rawtx,可以看到这笔交易的数据流是如何原始的记录在区块体(Block Body)当中的。

扫描二维码关注公众号,回复: 13213529 查看本文章

01000000010000000000000000000000000000000000000000000000000000000000000000ffffffff07044c86041b0147ffffffff0100f2052a01000000434104ad3b4c6ee28cb0c438c87b4efe1c36e1e54c10efc690f24c2c02446def863c50e9bf482647727b415aa81b45d0f7aa42c2cb445e4d08f18b49c027b58b6b4041ac00000000

 常规转账交易:点击体积旁边的蓝色小字rawtx,可以看到这笔交易的数据流是如何原始的记录在区块体(Block Body)当中的。

0100000001bd06367d15f5699ab2231160de4c74a4a8cfae4a97c1fc5a77a02aead8e391cb000000008b483045022100a1f2df66d173e668849694bd2c0dc77162278f34902483d55fb16631e39e37f10220157636faa19568e04f82dd477e9e6a10fefe99492a70ec23b338c633a6f28f5d014104a34f5f40605dd7d2b11a0ef3c9ab32be64318c2aa34b3a924f16ee8a9a0eabd8b7183bd8e1acb0569f3a6b4cfc912c575d0d83bc2ba7035fc59991205432479cffffffff0140420f00000000001976a9147d878427c2cffbbb117200ca85689269f73e7fcb88ac00000000

拿到转账数据之后,我们要构建Merkle Tree,首先计算转账本身的Hash

import hashlib
import struct
import time


def hash256(s):
  return hashlib.new('sha256', s).digest()


def dhash256(s):
  return hash256(hash256(s))


if __name__ == '__main__':
	tx_0 = "01000000010000000000000000000000000000000000000000000000000000000000000000ffffffff07044c86041b0147ffffffff0100f2052a01000000434104ad3b4c6ee28cb0c438c87b4efe1c36e1e54c10efc690f24c2c02446def863c50e9bf482647727b415aa81b45d0f7aa42c2cb445e4d08f18b49c027b58b6b4041ac00000000"
	tx_1 = "0100000001bd06367d15f5699ab2231160de4c74a4a8cfae4a97c1fc5a77a02aead8e391cb000000008b483045022100a1f2df66d173e668849694bd2c0dc77162278f34902483d55fb16631e39e37f10220157636faa19568e04f82dd477e9e6a10fefe99492a70ec23b338c633a6f28f5d014104a34f5f40605dd7d2b11a0ef3c9ab32be64318c2aa34b3a924f16ee8a9a0eabd8b7183bd8e1acb0569f3a6b4cfc912c575d0d83bc2ba7035fc59991205432479cffffffff0140420f00000000001976a9147d878427c2cffbbb117200ca85689269f73e7fcb88ac00000000"
	h_0, h_1 = dhash256(bytes.fromhex(tx_0))[::-1], dhash256(bytes.fromhex(tx_1))[::-1]
	print("tx_0:\n\tRaw Length = %d\n\tTx Hash = %s" % (len(tx_0), ''.join( [ "%02x" % x for x in h_0 ] ).strip()))
	print("tx_1:\n\tRaw Length = %d\n\tTx Hash = %s" % (len(tx_1), ''.join( [ "%02x" % x for x in h_1 ] ).strip()))

	tree = dhash256(h_0[::-1] + h_1[::-1])[::-1]
	print("merkle_tree:\n\tRoot = %s" % ''.join( [ "%02x" % x for x in tree ] ).strip())

 扩展

计算block高度 123456的merkle tree。二叉树,从最底部的叶子节点开始之后,每两个子树的root合并,计算其hash进行合并,生成新的树。

import hashlib
 
def hash256(s):
  return hashlib.new('sha256', s).digest()
 
def dhash256(s):
  return hash256(hash256(s))
 
tx1="5b75086dafeede555fc8f9a810d8b10df57c46f9f176ccc3dd8d2fa20edd685b".decode('hex')[::-1]
tx2="e3d0425ab346dd5b76f44c222a4bb5d16640a4247050ef82462ab17e229c83b4".decode('hex')[::-1]
tx3="137d247eca8b99dee58e1e9232014183a5c5a9e338001a0109df32794cdcc92e".decode('hex')[::-1]
tx4="5fd167f7b8c417e59106ef5acfe181b09d71b8353a61a55a2f01aa266af5412d".decode('hex')[::-1]
tx5="60925f1948b71f429d514ead7ae7391e0edf965bf5a60331398dae24c6964774".decode('hex')[::-1]
tx6="d4d5fc1529487527e9873256934dfb1e4cdcb39f4c0509577ca19bfad6c5d28f".decode('hex')[::-1]
tx7="7b29d65e5018c56a33652085dbb13f2df39a1a9942bfe1f7e78e97919a6bdea2".decode('hex')[::-1]
tx8="0b89e120efd0a4674c127a76ff5f7590ca304e6a064fbc51adffbd7ce3a3deef".decode('hex')[::-1]
tx9="603f2044da9656084174cfb5812feaf510f862d3addcf70cacce3dc55dab446e".decode('hex')[::-1]
tx10="9a4ed892b43a4df916a7a1213b78e83cd83f5695f635d535c94b2b65ffb144d3".decode('hex')[::-1]
tx11="dda726e3dad9504dce5098dfab5064ecd4a7650bfe854bb2606da3152b60e427".decode('hex')[::-1]
tx12="e46ea8b4d68719b65ead930f07f1f3804cb3701014f8e6d76c4bdbc390893b94".decode('hex')[::-1]
tx13="864a102aeedf53dd9b2baab4eeb898c5083fde6141113e0606b664c41fe15e1f".decode('hex')[::-1]
 
mrkl_tree1 = dhash256(tx1+tx2)
mrkl_tree2 = dhash256(tx3+tx4)
mrkl_tree3 = dhash256(tx5+tx6)
mrkl_tree4 = dhash256(tx7+tx8)
mrkl_tree5 = dhash256(tx9+tx10)
mrkl_tree6 = dhash256(tx11+tx12)
mrkl_tree7 = dhash256(tx13+ tx13) #奇数要重复相加
 
mrkl_tree1_1 = dhash256(mrkl_tree1 + mrkl_tree2)
mrkl_tree2_2 = dhash256(mrkl_tree3 + mrkl_tree4)
mrkl_tree3_3 = dhash256(mrkl_tree5 + mrkl_tree6)
mrkl_tree4_4 = dhash256(mrkl_tree7 + mrkl_tree7)  #奇数个
 
 
mrkl_tree1_1_1 = dhash256(mrkl_tree1_1 + mrkl_tree2_2 )
mrkl_tree2_2_2 = dhash256(mrkl_tree3_3 + mrkl_tree4_4 )
 
result = dhash256(mrkl_tree1_1_1 + mrkl_tree2_2_2 )
 
print("0e60651a9934e8f0decd1c5fde39309e48fca0cd1c84a21ddfde95033762d86c", "ok")
print result[::-1].encode('hex')

 进一步扩展

通用代码

#coding: utf-8

import hashlib

def merkle(hashList):
    if len(hashList) == 1:
        return hashList[0]

    newHashList = []

    # Process pairs. For odd length, the last is skipped

    for i in range(0, len(hashList) - 1, 2):
        newHashList.append(dhash256(hashList[i], hashList[i + 1]))

    if len(hashList) % 2 == 1:  # odd, hash last item twice
        newHashList.append(dhash256(hashList[-1], hashList[-1]))
    return merkle(newHashList)


def dhash256(a, b): # a/b 大小端转换后的数据
    # due to big-endian / little-endian nonsense
    concat = a + b
    temp = hashlib.sha256(concat).digest()
    h = hashlib.sha256(temp).digest()
    return h


#高度 123456
#https://btc.com/0000000000002917ed80650c6174aac8dfc46f5fe36480aaef682ff6cd83c3ca
txHashes = [
    '5b75086dafeede555fc8f9a810d8b10df57c46f9f176ccc3dd8d2fa20edd685b'.decode('hex')[::-1],
    'e3d0425ab346dd5b76f44c222a4bb5d16640a4247050ef82462ab17e229c83b4'.decode('hex')[::-1],
    '137d247eca8b99dee58e1e9232014183a5c5a9e338001a0109df32794cdcc92e'.decode('hex')[::-1],
    '5fd167f7b8c417e59106ef5acfe181b09d71b8353a61a55a2f01aa266af5412d'.decode('hex')[::-1],
    '60925f1948b71f429d514ead7ae7391e0edf965bf5a60331398dae24c6964774'.decode('hex')[::-1],
    'd4d5fc1529487527e9873256934dfb1e4cdcb39f4c0509577ca19bfad6c5d28f'.decode('hex')[::-1],
    '7b29d65e5018c56a33652085dbb13f2df39a1a9942bfe1f7e78e97919a6bdea2'.decode('hex')[::-1],
    '0b89e120efd0a4674c127a76ff5f7590ca304e6a064fbc51adffbd7ce3a3deef'.decode('hex')[::-1],
    '603f2044da9656084174cfb5812feaf510f862d3addcf70cacce3dc55dab446e'.decode('hex')[::-1],
    '9a4ed892b43a4df916a7a1213b78e83cd83f5695f635d535c94b2b65ffb144d3'.decode('hex')[::-1],
    'dda726e3dad9504dce5098dfab5064ecd4a7650bfe854bb2606da3152b60e427'.decode('hex')[::-1],
    'e46ea8b4d68719b65ead930f07f1f3804cb3701014f8e6d76c4bdbc390893b94'.decode('hex')[::-1],
    '864a102aeedf53dd9b2baab4eeb898c5083fde6141113e0606b664c41fe15e1f'.decode('hex')[::-1],
    ]

result = merkle(txHashes)
print(result[::-1].encode('hex'))

参考:

https://www.jianshu.com/p/4e08d0d037a6

merkle-root-bitcoin-step-by-step
https://gist.github.com/shirriff/c9fb5d98e6da79d9a772
http://pythonfiddle.com/merkle-root-bitcoin/
http://www.cnblogs.com/fengzhiwu/p/5524324.html
https://en.wikipedia.org/wiki/Merkle_tree
http://bittorrent.org/beps/bep_0030.html

猜你喜欢

转载自blog.csdn.net/uiop_uiop_uiop/article/details/119580326
今日推荐