SHA - 程序输出与sha512sum命令不同

时间:2018-03-17 14:13:32

标签: c hash openssl sha512

总之,我第一次使用 openssl / sha.h 进行编程,编译时一切正常。这是我的代码:

#include <stdlib.h>
#include <stdio.h>
#include <openssl/sha.h>


int main()
{
    int j;

    FILE *hash_file = fopen("hash.txt", "wb");

    for(j = 0; j < 256; j++)
    {
        unsigned char md[SHA512_DIGEST_LENGTH];
        char* fileName = malloc(sizeof(int));
        sprintf(fileName, "%X%s", j, ".txt");

        int i;
        FILE *file = fopen(fileName, "rb");
        SHA512_CTX mdcontext;

        int bytes;
        unsigned char data[2048];

        if(file == NULL)
        {
            printf("%s can not be opened\n", fileName);
            return;
        }

        SHA512_Init(&mdcontext);

        while((bytes = fread(data, 1, 2048, file) != 0))
            SHA512_Update(&mdcontext, data, bytes);

        SHA512_Final(md, &mdcontext);

        for(i = 0; i < SHA512_DIGEST_LENGTH; i++)
        {
            printf("%x", md[i]);
            fprintf(hash_file, "%x", md[i]);
        }
        // fprintf(hash_file, "\n");
        printf("\n");
        free(fileName);
        fclose(file);
    }

    fclose(hash_file);
    return 0;
}

我有这个输出:

711c22448e721e5491d8245b49425aa861f1fc4a15287f735e23799b65cffec5b5abdfddd91cd643aeb3b530d48f5e258e7e230a94ed525c1387bb4e1b  

但是当我在Linux中使用 sha512sum 命令散列相同的文件时,我得到了这个输出:

6e3ea4bec3cd738f06f011c2f4ee4f6cd6d12205cafe41c083d52f94d9de4ab8b9e702664a367b633be14024a96e88a140a2e7fee4dc2c6e2f0bd436e281e35b  make.sh  

问题是什么?

1 个答案:

答案 0 :(得分:3)

哦,boi!

一个小小的parantheses可以让你拉出你的头发。

问题在于此声明while((bytes = fread(data, 1, 2048, file) != 0))。您会看到,在此语句中,将首先评估!=条件。因此,当fread读取(并返回)时,假设n个字符数,它会检查n!=0是否为true。如果评估为bytes,则将1设置为true1已投放到SHA512_Update(&mdcontext, data, bytes);)。

现在,函数SHA512_Update(&mdcontext, data, 1);变为SHA512_Update(&mdcontext, data, n);,而它应该是n(其中while((bytes = fread(data, 1, 2048, file) != 0))是成功读取的字符数。)

解决方案

while((bytes = fread(data, 1, 2048, file)) != 0)更改为char

更新[保存SHA512数组中的哈希值]:

char的输出为128个字符。因此,我们需要一个SHA512_DIGEST_LENGTH数组,其大小是char(64)的两倍。然后,我们可以使用sprintf将其存储在char hash[SHA512_DIGEST_LENGTH*2]; for(i = 0; i < SHA512_DIGEST_LENGTH; i++) sprintf(&hash[i*2], "%02x", md[i]); 数组中。

i*2

为什么hash[i]?因为输出的宽度为2个字节。因此,结果将存储在hash[i+1]for(i = 0; i < SHA512_DIGEST_LENGTH*2; i++) printf("%c", hash[i]);

现在,打印它:

%02x

<强> PS : 阅读precedence

请不要忘记在帖子中注意评论中的建议,尤其是关于使用史蒂夫class Foo: def __init__(self, filename): with open(filename, "r") as fp: self.data = fp.readlines() 的建议。