+-+-+ +-+ +-+-+-+-+
|G|O| |4| |H|I|V|E|
+-+-+ +-+ +-+-+-+-+

 --- A GOPHER-LIKE INTERFACE FOR HIVE BLOCKCHAIN ---

Bitcoin01-01: 비트코인 코어 소스코드로 살펴보는 머클 트리

BY: @dlgusdn616 | CREATED: June 7, 2018, 3:45 a.m. | VOTES: 8 | PAYOUT: $2.67 | [ VOTE ]

머클트리

등장 배경:

사용되는 기술:

작동 방식에 대한 간략한 설명:

[IMAGE: https://cdn.steemitimages.com/DQmQrntFrZM7Kh6n2bN5kKxBt6ooRuJEQ8nevAAH7nSzwgw/image.png]

비트코인코어 소스코드 리뷰 및 설명

main.h에 정의되어 있는 CBlock 클래스

class CBlock in main.h
    // header: 흔히 말하는 블록 헤더의 정체다. 풀노드가 아닌 경량 클라이언트(light client)들은 블록 헤더만 저장하게 된다.
    int nVersion;
    uint256 hashPrevBlock;
    uint256 hashMerkleRoot; // BuildMerkleTree()로 생성되는 머클루트
    unsigned int nTime;
    unsigned int nBits;
    unsigned int nNonce;

    // network and disk
    vector vtx; // 트랜잭션들을 저장할 때는 CTransaction 클래스의 벡터로 저장
    // A block contains multiple transactions, held in vector vtx.

    // memory only
    mutable vector\ vMerkleTree;

머클 트리의 생성(1)

CBlock::BuildMerkleTree( )
    uint256 BuildMerkleTree() const
    {
        vMerkleTree.clear();
        // 각 트랜잭션들의 해시값을 따로 저장하여 vMerkleTree 생성
        foreach(const CTransaction& tx, vtx)
            vMerkleTree.push_back(tx.GetHash());
        int j = 0;
        for (int nSize = vtx.size(); nSize > 1; nSize = (nSize + 1) / 2)
        {
            for (int i = 0; i < nSize; i += 2)
            {
                // 만약 트랜잭션이 짝수개가 아니라면, 마지막 트랜잭션의 해시는 자기 자신과 해시하게 된다.
                int i2 = min(i+1, nSize-1); 
                // 트랜잭션의 해시를 2개씩 묶어서 다시 머클트리에 삽입한다.
                vMerkleTree.push_back(Hash(BEGIN(vMerkleTree[j+i]),  END(vMerkleTree[j+i]),
                                           BEGIN(vMerkleTree[j+i2]), END(vMerkleTree[j+i2])));
            }
            j += nSize; // j는 각 트리레벨에 맞춰 삽입해야할 첫번째 위치를 가리킨다.
        }
        return (vMerkleTree.empty() ? 0 : vMerkleTree.back());
    }

머클트리의 생성(2)

머클트리의 증명(1)

// nIndex로 위변조 여부를 검사할 특정 트랜잭션을 선택하고 머클 트리내의 트랜잭션 해시값과 연관된 
// 트랜잭션의 해시들만 따로 추출하여 MerkleBranch를 생성한다.
    vector\ GetMerkleBranch(int nIndex) const
    {   // nIndex에 해당하는 트랜잭션 증명에 사용되는 노드들을 vMerkleBranch에 담는 작업을 진행
        if (vMerkleTree.empty())
            BuildMerkleTree();
        vector\ vMerkleBranch;
        int j = 0;
        for (int nSize = vtx.size(); nSize > 1; nSize = (nSize + 1) / 2)
        {
            int i = min(nIndex^1, nSize-1); // nIndex^1의 값은 0 또는 1(반복)
            vMerkleBranch.push_back(vMerkleTree[j+i]);
            nIndex >>= 1;
            j += nSize;
        }
        return vMerkleBranch;
    }

머클트리의 증명(2)

    static uint256 CheckMerkleBranch(uint256 hash, const vector\& vMerkleBranch, int nIndex)
    {
        if (nIndex == -1)
            return 0;
        foreach(const uint256& otherside, vMerkleBranch)
        {  // 해시되는 순서를 지켜주기 위해 아래의 두 경우를 구분하여 처리
            if (nIndex & 1) // 트랜잭션의 인덱스가 홀수일 경우
                hash = Hash(BEGIN(otherside), END(otherside), BEGIN(hash), END(hash));
            else            // 트랜잭션의 인덱스가 짝수일 경우
                hash = Hash(BEGIN(hash), END(hash), BEGIN(otherside), END(otherside));
            nIndex >>= 1;   // 해시되는 순서를 맞춰준다.
        }
        return hash; // it should be merkleRoot
    }

머클트리의 증명(3)

마치며

TAGS: [ #bitcoin ] [ #merkletree ] [ #merkleroot ] [ #bitcoincore ]

Replies

@allnatural | June 7, 2018, 3:45 a.m. | Votes: 1 | [ VOTE ]

Get your post resteemed to 72,000 followers. Go here https://steemit.com/@a-a-a

@endiyou | June 10, 2018, 1:46 a.m. | Votes: 1 | [ VOTE ]

좋은 글 감사합니다.

@dlgusdn616 | June 10, 2018, 10:19 a.m. | Votes: 0 | [ VOTE ]

도움이 되었다니 다행입니다 :)

@steemitboard | June 10, 2018, 2:33 p.m. | Votes: 0 | [ VOTE ]

Congratulations @dlgusdn616! You have completed some achievement on Steemit and have been rewarded with new badge(s) :

[IMAGE: https://steemitimages.com/70x70/http://steemitboard.com/notifications/firstvote.png] You made your First Vote

Click on the badge to view your Board of Honor.
If you no longer want to receive notifications, reply to this comment with the word STOP

> Do you like SteemitBoard's project? Then Vote for its witness and get one more award!

[ BACK TO TRENDING ] [ BACK TO MENU ]
CMD>