获取二进制文件 C 的哈希值
Getting hash of a binary file C
我想获取我拥有的二进制文件的哈希值。我尝试了以下操作,但后来意识到 SHA1()
正在返回字符串的哈希值(文件名)。但我想 运行 它在文件本身上。关于如何做到这一点的任何指示都会很棒。
char *fileName = "/bin/ls"
unsigned char hash[SHA_DIGEST_LENGTH];
SHA1((unsigned char *)fileName, strlen(fileName),hash);
我不知道你的 SHA1() 函数是如何工作的(它来自 libssl 吗?),但我假设
SHA1((unsigned char *)fileName, strlen(fileName),hash);
你正在散列文件名,所以 /bin/ls
字符串。您需要将文件内容逐字节读取到缓冲区中并对其进行哈希处理。
您只需将文件上下文的参数提供给 SHA1()。
变量 fileName 包含字符串“/bin/ls”和该字符串的 SHA1() 函数 returns 散列。这是如何读取文件并获取哈希的简单示例
/* Used variables */
FILE *fp;
char string[2048];
unsigned char hash[SHA_DIGEST_LENGTH];
int t;
/* Open file */
fp=fopen("test","r");
if (fp == NULL)
{
printf("Can not open file\n");
exit(1);
}
/* Read file */
fread (string,1,sizeof(string),fp);
/* Get hash of file */
SHA1((unsigned char *)string, strlen(string),hash);
我希望字符串 (2048) 的缓冲区大小对于文件上下文来说足够了。
您需要逐块读取文件,并逐块计算摘要。
读取块最多例如2048 字节 fread
。开头使用 SHA1_Init
,每个块使用 SHA1_Update
,最后使用 SHA1_Final
。
如果您一次性读取整个文件,您可以使用普通 SHA1
函数 gulp,但不推荐这样做。
另一种方法是对文件进行内存映射(参见 mmap()
或任何 Windows 等价物)并使用普通 SHA1
。这种方法非常有效,但不如另一种方法可移植。
感谢大家的意见我解决了这个问题。我在这里发布代码,所以其他人可能会觉得它有用。
void getFileHash(char *fileName){
unsigned char result[2*SHA_DIGEST_LENGTH];
unsigned char hash[SHA_DIGEST_LENGTH];
int i;
FILE *f = fopen(fileName,"rb");
SHA_CTX mdContent;
int bytes;
unsigned char data[1024];
if(f == NULL){
printf("%s couldn't open file\n",fileName);
exit(1);
}
SHA1_Init(&mdContent);
while((bytes = fread(data, 1, 1024, f)) != 0){
SHA1_Update(&mdContent, data, bytes);
}
SHA1_Final(hash,&mdContent);
for(i=0;i<SHA_DIGEST_LENGTH;i++){
printf("%02x",hash[i]);
}
printf("\n");
/** if you want to see the plain text of the hash */
for(i=0; i < SHA_DIGEST_LENGTH;i++){
sprintf((char *)&(result[i*2]), "%02x",hash[i]);
}
printf("%s\n",result);
fclose(f);
}
我想获取我拥有的二进制文件的哈希值。我尝试了以下操作,但后来意识到 SHA1()
正在返回字符串的哈希值(文件名)。但我想 运行 它在文件本身上。关于如何做到这一点的任何指示都会很棒。
char *fileName = "/bin/ls"
unsigned char hash[SHA_DIGEST_LENGTH];
SHA1((unsigned char *)fileName, strlen(fileName),hash);
我不知道你的 SHA1() 函数是如何工作的(它来自 libssl 吗?),但我假设
SHA1((unsigned char *)fileName, strlen(fileName),hash);
你正在散列文件名,所以 /bin/ls
字符串。您需要将文件内容逐字节读取到缓冲区中并对其进行哈希处理。
您只需将文件上下文的参数提供给 SHA1()。 变量 fileName 包含字符串“/bin/ls”和该字符串的 SHA1() 函数 returns 散列。这是如何读取文件并获取哈希的简单示例
/* Used variables */
FILE *fp;
char string[2048];
unsigned char hash[SHA_DIGEST_LENGTH];
int t;
/* Open file */
fp=fopen("test","r");
if (fp == NULL)
{
printf("Can not open file\n");
exit(1);
}
/* Read file */
fread (string,1,sizeof(string),fp);
/* Get hash of file */
SHA1((unsigned char *)string, strlen(string),hash);
我希望字符串 (2048) 的缓冲区大小对于文件上下文来说足够了。
您需要逐块读取文件,并逐块计算摘要。
读取块最多例如2048 字节 fread
。开头使用 SHA1_Init
,每个块使用 SHA1_Update
,最后使用 SHA1_Final
。
如果您一次性读取整个文件,您可以使用普通 SHA1
函数 gulp,但不推荐这样做。
另一种方法是对文件进行内存映射(参见 mmap()
或任何 Windows 等价物)并使用普通 SHA1
。这种方法非常有效,但不如另一种方法可移植。
感谢大家的意见我解决了这个问题。我在这里发布代码,所以其他人可能会觉得它有用。
void getFileHash(char *fileName){
unsigned char result[2*SHA_DIGEST_LENGTH];
unsigned char hash[SHA_DIGEST_LENGTH];
int i;
FILE *f = fopen(fileName,"rb");
SHA_CTX mdContent;
int bytes;
unsigned char data[1024];
if(f == NULL){
printf("%s couldn't open file\n",fileName);
exit(1);
}
SHA1_Init(&mdContent);
while((bytes = fread(data, 1, 1024, f)) != 0){
SHA1_Update(&mdContent, data, bytes);
}
SHA1_Final(hash,&mdContent);
for(i=0;i<SHA_DIGEST_LENGTH;i++){
printf("%02x",hash[i]);
}
printf("\n");
/** if you want to see the plain text of the hash */
for(i=0; i < SHA_DIGEST_LENGTH;i++){
sprintf((char *)&(result[i*2]), "%02x",hash[i]);
}
printf("%s\n",result);
fclose(f);
}