【问题标题】:Hashing program not returning identical values for the same file哈希程序没有为同一个文件返回相同的值
【发布时间】:2019-09-03 07:16:28
【问题描述】:

我创建的这个散列函数(扫描新文件并计算它们的散列)看似函数,但是一旦删除一个文件,例如 test.c,然后用完全相同的文件替换它,它会返回 2 个不同的哈希值。我的意思是,当程序运行时,第一次计算可能会返回 1234 的哈希值,例如,一旦删除并将相同的文件放在文件夹中,它就会返回 2345。

似乎没有顺序,因为 1234 可能是连续 5 次的结果。我想知道这段代码中是否有任何非常明显的原因?

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <string.h>
#include <errno.h>
#include <sys/inotify.h>
#include <openssl/sha.h>

int main (int argc, char *argv[])
{
        int fd;
        unsigned char c[SHA512_DIGEST_LENGTH];
        int i;
        SHA512_CTX mdContext;
        int bytes;
        unsigned char data[1024];
        const int event_size = sizeof(struct inotify_event);
        const int buf_len = 1024 * (event_size + FILENAME_MAX);
        char *directory = "/home/joe/Documents/";
        char *hashDirectory = "/home/joe/Documents/_Hash/";
        char hashInBuf[100];
        char hashOutBuf[100];
        fd = inotify_init();

        if (fd < 0) {
          perror("inotify_init");
        }
        while (1) {
          char buff[buf_len];
          int no_of_events, count = 0;

          //SEARCH FOR NEW FILES WITHIN DIRECTORY
          no_of_events = read (fd, buff, buf_len);
          while (count < no_of_events) {
            struct inotify_event *event = (struct inotify_event *)&buff[count];
            if (event->len) {
              if ((event->mask & IN_CREATE))
              if(!(event->mask & IN_ISDIR)) {
                printf("\n%s has been created\n", event->name);

                //CONJOIN DIRECTORY AND FILENAME / EXTENSION
                snprintf(hashInBuf, sizeof(hashInBuf), "%s/%s", directory, event->name);
                snprintf(hashOutBuf, sizeof(hashOutBuf), "%s/%s.txt", hashDirectory, event->name);

                FILE *ftest=fopen(hashInBuf, "rb");
                FILE *ftest2=fopen(hashOutBuf, "wt");

                //HASH FUNCTION
                SHA512_Init (&mdContext);
                while ((bytes = fread (data, 1, 1024, ftest)) != 0)
                SHA512_Update (&mdContext, data, bytes);
                SHA512_Final (c,&mdContext);
                for(i = 0; i < SHA512_DIGEST_LENGTH; i++){
                  fprintf(ftest2, "%02x", c[i]);
                  printf("%02x", c[i]);
                }
                fclose (ftest);
                fclose (ftest2);
                fflush (stdout);
              }
            }
            count += event_size + event->len;
          }
        }
        return 0;
}

提前谢谢你!

【问题讨论】:

  • 您可以尝试对这两个文件使用md5sum &lt;filename&gt; 吗?如果这也不同,那么文件实际上并不相同。
  • @SanderDeDycker 我正在尝试检查同一个文件,因此使用您要求的方法只会产生一个哈希值。我正在删除扫描文件夹中的那个,然后将相同的文件放回所述文件夹中(以验证它是否有效,不幸的是,它没有描述)。奇怪的是该函数只有 2 个结果(即哈希将是 A. 或 B. 随机)。
  • 哈希值之一是偶然cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e
  • @Ctx 是的!天哪,我一直在寻找解决这个问题的方法,哈哈。

标签: c loops hash openssl


【解决方案1】:

在这一行

if ((event->mask & IN_CREATE))

您等待文件被创建的事件。然后,您的散列函数立即开始运行! 这可能会导致文件完全写入的情况,因此您只对文件的部分进行了哈希处理。

您应该使用事件IN_CLOSE_WRITE 来确保文件已经被完全写入。

另一种选择是在此目录中创建文件,而是在临时目录中创建它们,然后将它们移动到目标目录中。那么对应的事件是IN_MOVED_TO

【讨论】:

  • 啊,太棒了!非常感谢,我会努力实现的。
  • @JosephSmith yw ;)
  • 很抱歉再次打扰,但我应该将IN_CLOSE_WRITE 放在哪里?我对编码不是很熟悉(或擅长..)......!
  • 而不是 IN_CREATE
猜你喜欢
  • 2013-02-08
  • 2018-03-23
  • 1970-01-01
  • 2012-08-13
  • 1970-01-01
  • 2019-10-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多