讨论帖:比特币中的SHA256算法的实现与标准的SHA256算法实现是否相同?

近日阅读了比特币源码中与哈希相关的部分,对于其中一些细节还是有不清晰的地方。

于是我写了一个小的测试demo:sha256_test代码下载

分别测试了三个版本对于SHA-256算法的实现:

  • Bitcoin Version:来自比特币核心源码中对于SHA-256的实现
  • crypto Version: 来自于Github上开源算法库crypto-algorithms中的标准SHA-256实现
  • Tool Version: 来自于在线测试工具的SHA-256计算

对比发现,开源算法库crypto-algorithms在线SHA-256测试工具对于同一数据的哈希结果相同,但 Bitcoin Version 的哈希结果与其余两个测试版本不一致。因此,我想了解:

比特币中的SHA256算法的实现与标准的SHA256算法实现是否相同?

如果相同,那一定是我对比特币源码的使用出现了问题,可否指出我在测试时调用错误的地方?

如果不相同,可否指出哪些实现细节有差异,比如或许大小端的差异?字符串转换存在差异?

具体地,我将Bitcoin Core源码中与SHA256相关的部分剥离出来,放置于sha256_test目录下,构成Bitcoin Version的测试代码

我将开源算法库crypto-algorithms中与SHA256相关的部分,放置于standard_implement_test目录下,构成crypto Version的测试代码

在线测试工具对于字符串”hello”的计算结果如下:

Conversion Completed
Your hash has been successfully generated.
hex: 2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824
HEX: 2CF24DBA5FB0A30E26E83B2AC5B9E29E1B161E5C1FA7425E73043362938B9824

算法库crypto-algorithms对于字符串”hello”的计算结果如下:

$ ./test
the string to test SHA-256: hello

result of SHA-256
2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824

Bitcoin Version对于字符串”hello”的计算结果如下:
其中,我使用了两种方法从哈希结果中解析出16进制字符串,但均与希望的结果不一致。

$ ./test hello
The string to test SHA-256:
hello

Bitcoin SHA-256 result by GetHex():
fa20f248146c7b29c2d6d2b52ed56fd6465503a39919ca848d763bd32d72f95c

Bitcoin SHA-256 result by parse data[Width]:
5cf9722dd33b768d84ca1999a3035546d66fd52eb5d2d6c2297b6c1448f220fa

Bitcoin Version包含了以下文件:

$ ls
common.h    sha256.h                 tinyformat.h  utilstrencodings.cpp
makefile    standard_implementation  uint256.cpp   utilstrencodings.h
sha256.cpp  test.cpp                 uint256.h

test.cpp的代码如下:

#include<iostream>

#include "sha256.h"
#include "uint256.h"

//using namespace std;
int main(int argc, char* argv[])
{
    if(argc!=2)
    {
        std::cout<<"please type a string to test sha-256"<<std::endl;
        return 1;
    }

    char* str = argv[1];

    std::cout << "The string to test SHA-256:" << std::endl;
    int strLen = strlen(str);
    for(char* p = str; p<str+strLen; p++)
    {
        std::cout<<*p;
    }
    std::cout<<std::endl;

    uint256 sha256_result;

    // use code in Bitcoin Core to solve SHA-256
    CSHA256 sha;
    sha.Write((unsigned char*)str, strLen);
    sha.Finalize((unsigned char*)&sha256_result);

    // show hash result by GetHex()
    std::cout << std::endl << "Bitcoin SHA-256 result by GetHex():" << std::endl;
    std::cout << sha256_result.GetHex() << std::endl;

    // show hash result by parsing member variable data[Width]
    std::cout << std::endl << "Bitcoin SHA-256 result by parse data[Width]:" << std::endl;
    unsigned int size = sha256_result.size();
    unsigned char* pointer = sha256_result.begin();
    unsigned char temp;
    for(unsigned char* pdata = pointer; pdata < pointer + size; pdata++)
    {
        temp = *pdata;
        unsigned char hex1 = temp >> 4;
        unsigned char hex2 = temp & 0x0f;

        if(hex1<10)
            std::printf("%c",hex1+48);
        else
            std::printf("%c",hex1+87);

        if(hex2<10)
            std::printf("%c",hex2+48);
        else
            std::printf("%c",hex2+87);
    }
    std::cout << std::endl;
}

如果哪位大神有见解,多多交流,还望赐教~

后续如果对于这个问题有了答案,我会回来更新的。

发布了87 篇原创文章 · 获赞 325 · 访问量 52万+

猜你喜欢

转载自blog.csdn.net/u011583927/article/details/81905565