Skip to content

Instantly share code, notes, and snippets.

@ephemient
Last active July 7, 2020 13:44
Show Gist options
  • Save ephemient/73340a6c6e83a9c94bb3 to your computer and use it in GitHub Desktop.
Save ephemient/73340a6c6e83a9c94bb3 to your computer and use it in GitHub Desktop.
crc32
#/* \
make -C "$(dirname "$0")" -f "$0" "$@"; exit $?
crc32: LDLIBS += -lz
crc32: crc32.o
$(CC) $(LDFLAGS) $(TARGET_ARCH) $^ $(LOADLIBES) $(LDLIBS) -o $@
crc32.o: crc32.c
$(CC) $(CFLAGS) $(CPPFLAGS) $(TARGET_ARCH) -c -o $@ $^
help:
$(info )
$(info http://www.linuxquestions.org/questions/linux-newbie-8/how-do-i-generate-a-crc32-checksum-163908/#post4670222)
$(info http://xrefactor.com/blog/polyglot-in-c-makefile-and-shell-script)
$(info )
.PHONY: help
#*/
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <string.h>
#include <sysexits.h>
#include <unistd.h>
#include <zlib.h>
static int checksum_file(int fd, const char *name) {
char buffer[1 << 20];
int rc;
uLong crc = crc32(0L, Z_NULL, 0);
while ((rc = read(fd, buffer, sizeof(buffer))) > 0 ||
errno == EAGAIN || errno == EWOULDBLOCK || errno == EINTR)
if (rc > 0)
crc = crc32(crc, buffer, rc);
printf("%08x\t%s\n", crc, name);
return rc;
}
int main(int argc, const char *const *argv) {
int rc = 0;
if (argc <= 1)
rc = checksum_file(0, "-");
else {
int i;
for (i = 1; !rc && i < argc; i++) {
int fd = open(argv[i], O_RDONLY);
if (fd < 0)
goto err;
rc = checksum_file(fd, argv[i]);
close(fd);
if (rc)
break;
}
}
if (!rc)
return EX_OK;
err:
fprintf(stderr, "%s\n", strerror(errno));
return EX_IOERR;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment