Luke
Luke

Reputation: 301

convert sha 256 hash to number in c

I have a 16MB file. I want to take 16-byte chuck of the data each time, using SHA256 to hash it, and then use the result to point to the next location of the 16-byte chunk to be hashed.

For example,

#include <openssl/aes.h>
#include <openssl/sha.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>


#define BLOCKSIZE 1048576
#define SUBBLOCKSIZE 16

int main(void) {

  SHA256_CTX ctx;
  int SHA256_Init(SHA256_CTX *ctx);
  u_int8_t results[32];

  FILE *infile;
  char buf[SUBBLOCKSIZE];
  int bufsize = SUBBLOCKSIZE;

  infile = fopen("sample.dat", "r");
  int i = 0;
  int n;

  while (fread(buf, SUBBLOCKSIZE, 1, infile) != NULL) {
    SHA256_Init(&ctx);
    n = strlen(buf);
    SHA256_Update(&ctx, (u_int8_t *)buf, n);
    SHA256_Final(results, &ctx);

    //fseek here.....

    i++;
  }

  return 0;
}

In my code, 'results' is the hash result of SHA256. I want to convert it to a 256-bit number and mod it by 1024(or some other arbitrary integer number). Then I use the result as an input in fseek to locate to the next file pointer.

I'd like to know how can I convert 'results' to a 256-bit number?

Upvotes: 2

Views: 3904

Answers (1)

Maarten Bodewes
Maarten Bodewes

Reputation: 94018

The direct answer would be to use a library that handles big integers. For C the OpenSSL BN_ functions perform operations on Big Numbers, to name just an obvious one.

The not-so direct answer is to simply use 64 bits/8 bytes (leftmost) bits of the 256 bits/32 bytes of the resulting array and put it into a 64 bit "long" number (int64_t is probably best). Then you can simply retrieve the modulo x of that value using the % operator.

Beware that the result is not well distributed over the limit x that are not powers of two. In that case you may need to discard any number r that is equal or larger than x * n where n is the maximum value where x * n still fits into 64 bits. If you don't discard those values then you have a (tiny) higher chance that the result will be a lower value.

Of course if your result is exactly a power p of 2 then you might as well take the p (leftmost) bits and interpret those bits as an unsigned integer of a size the same or higher.

Upvotes: 2

Related Questions