Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Using OpenSSL's SHA1 with Apple Silicon in C

I am building a git clone and working on the hash-file command. I am currently trying to compute the SHA1 hash of a known string and have this code and the following issue:

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

int hashFile(char *file_name, int ww) {
    int i, ret;
    size_t size_len;
    unsigned long file_size;
    char path[56];
    unsigned char hash[SHA_DIGEST_LENGTH];
    char *token, *type, *blob_content, *content;

    FILE *src = fopen(file_name, "r");
    if (ferror(src)) {
        perror("Unable to read file");
        return 1;
    }
    fseek(src, 0L, SEEK_END);
    file_size = ftell(src);
    rewind(src);
    size_len = snprintf(NULL, 0, "%lu", file_size);

    char *buffer = (char *)malloc((size_t)file_size + 1);
    fread(buffer, sizeof(char), file_size, src);
    buffer[file_size] = '\0';

    blob_content = (char *)malloc((7 + sizeof(unsigned long) + file_size + 1) *
                                  sizeof(char));
    snprintf(blob_content, 7 + size_len + 1, "blob %lu\\0", file_size);
    strcat(blob_content, buffer);

    SHA1((unsigned char *)blob_content, strlen(blob_content), hash);
    printf("%s\n", hash);

    free(blob_content);
    free(buffer);

    return 0;
}

void printHashHelp() {
    printf("usage: twat hash-file [options] <file_name>\n");
    printf("\n");
    printf("options:\n");
    printf("\t-w: write contents to objects store\n");
}
$ clang --std=c17 -fmodules -fprebuilt-module-path=. -I/opt/homebrew/opt/openssl/include cmd.c comp.c init.c cat.c hash.c -o twat -v
...
Undefined symbols for architecture arm64:
  "_SHA1", referenced from:
      _hashFile in hash-fc3ff3.o
ld: symbol(s) not found for architecture arm64

How should I go about linking and enabling SHA1 to work on the M2 Max? What clang command should I be using if this is incorrect?

I have been trying different methods of linking openssl/sha.h and believed to have got it but have not got the function to work currently.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

Following: How to use SHA1 hashing in C programming I attempted to use the linked library but got a compiler linking failure.

>Solution :

Append

-L/opt/homebrew/lib -lcrypto

to your command line.

Also, your malloc and snprintf looks weird. The whole +1 and +7 looks error prone

This would be better:

char header[100] = {0};  // 100 is big enough for the entire "blob 12345" thing regardless of how big the file is

SHA1_CTX ctx = {0};
SHA1_Init(&ctx);
sprintf(header, "blob %lu", file_size);
SHA1_Update(&ctx, header, strlen(header));
SHA1_Update(&ctx, buffer, file_size);
SHA1_Final(hash, &ctx);

And then if you really want to be pedantic, make sure you open the file as binary on non-Unix:

#ifdef _WIN32
    char* flags = "rb";
#else
    char* flags = "r";
#endif

FILE *src = fopen(file_name, flags);
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading