Added arbitary number of files to check

multi
Avril 4 years ago
parent ddb80535ca
commit 408f5ab7a3
Signed by: flanchan
GPG Key ID: 284488987C31F630

1
.gitignore vendored

@ -1,2 +1,3 @@
obj/
fcmp-*
test/

@ -8,7 +8,7 @@ OPT_FLAGS+= -fgraphite
RELEASE_CFLAGS?= -O3 -march=native -flto $(OPT_FLAGS)
RELEASE_LDFLAGS?= -O3 -flto
DEBUG_CFLAGS?= -O0 -g
DEBUG_CFLAGS?= -DDEBUG -O0 -g
DEBUG_LDFLAGS?= -O0
CFLAGS+= -Wall -pedantic --std=gnu11 $(addprefix -I,$(INCLUDE))

@ -6,10 +6,17 @@
static const char* _prog_name = "fcmp";
__attribute__((noreturn)) void usage()
#ifdef DEBUG
#define __name(d) #d
#define dprintf(fmt, ...) printf("[dbg @" __FILE__ "->%s:%d] " fmt "\n", __func__, __LINE__ __VA_OPT__(,) __VA_ARGS__)
#else
#define dprintf(fmt, ...)
#endif
__attribute__((noreturn)) static void usage()
{
fprintf(stderr, "fcmp: compare files for identity\n");
fprintf(stderr, "usage: %s <file1> <file2>\n", _prog_name);
fprintf(stderr, "usage: %s <files...>\n", _prog_name);
exit(-1);
}
@ -19,37 +26,90 @@ __attribute__((always_inline)) static inline const void* die_if_null(const void*
else return ptr;
}
static int unmap_all(mmap_t ptrs[], size_t len)
{
register int rval=1;
dprintf("Unmapping %lu entries", len);
for (register size_t i=0;i<len;i++)
{
if(!unmap_and_close(ptrs[i])) {
fprintf(stderr, "Failed to unmap and close fd %d", ptrs[i].fd);
rval = -1;
}
}
return rval;
}
static int compare_then_close(const mmap_t * restrict map1, mmap_t* restrict map2)
{
register int rval=0;
if (map1->len != map2->len) rval = 2;
else if (memcmp(map1->ptr, map2->ptr, map1->len) != 0) rval = 1;
if(!unmap_and_close(*map2)) {
fprintf(stderr, "Failed to unmap and close");
rval=-1;
}
return rval;
}
int main(int argc, char** argv)
{
_prog_name = argv[0];
const int nrest = argc-2;
if (nrest==0) usage();
dprintf("There are %d extra files to chk", nrest);
const char* f1 = die_if_null(argv[1]);
const char* f2 = die_if_null(argv[2]);
const char* frest[nrest];
for (register int i=0;i<nrest;i++) {
frest[i] = die_if_null(argv[2+i]);
dprintf("frest[%d] = \"%s\"", i, frest[i]);
}
mmap_t map1;
mmap_t mrest[nrest];
mmap_t map1, map2;
if (!open_and_map(f1, &map1)) {
fprintf(stderr, "Failed to open or map %s\n", f1);
return -1;
}
if (!open_and_map(f2, &map2)) {
fprintf(stderr, "Failed to open or map %s\n", f2);
unmap_and_close(map1);
return -1;
}
for(register int i=0;i<nrest;i++) {
const char* f2 = frest[i];
dprintf("Attempting to map %d (%s)", i, f2);
if (!open_and_map(f2, &mrest[i])) {
fprintf(stderr, "Failed to open or map arg %d, `%s`\n", i+2, f2);
unmap_and_close(map1);
unmap_all(mrest, i);
return -1;
}
}
dprintf("All map okay");
register int rval=0;
if (map1.len != map2.len) rval = 2;
else if (memcmp(map1.ptr, map2.ptr, map1.len) != 0) rval = 1;
if(!unmap_and_close(map1)) {
fprintf(stderr, "Failed to unmap and close %s", f1);
rval=-1;
for(register int i=0;i<nrest;i++) {
dprintf("Checking %d \"%s\"", i, frest[i]);
switch ((rval=compare_then_close(&map1, mrest+i))) {
case 0: break;
default:
// Close the rest
dprintf("Unmapping mrest from %d (len %d) while max of nrest is %d", (i+1), nrest-(i+1), nrest);
if(i<nrest-1) unmap_all(mrest+ (i+1), nrest- (i+1));
goto end;
}
dprintf("Ident %d OK", i);
}
if(!unmap_and_close(map2)) {
fprintf(stderr, "Failed to unmap and close %s", f2);
end:
if(!unmap_and_close(map1)) {
fprintf(stderr, "Failed to unmap and close %s", f1);
rval=-1;
}
dprintf("Final rval is %d", rval);
return rval;
}

Loading…
Cancel
Save