X-Git-Url: https://git.jtryba.com/browse/friidump.git/blobdiff_plain/6e43cd3fd4f7324a177331a01d653b4c19c4bca7..7564cb0e17b2d09c012ac9f2a6e62b4363fd563f:/src/redump_dat.c diff --git a/src/redump_dat.c b/src/redump_dat.c index 6231679..028aa13 100644 --- a/src/redump_dat.c +++ b/src/redump_dat.c @@ -5,6 +5,93 @@ #include #include +static int redump_path_exists(const char *path) { + FILE *f; + if (!path || !path[0]) + return 0; + f = fopen(path, "rb"); + if (!f) + return 0; + fclose(f); + return 1; +} + +static int redump_join_path( + const char *dir, + const char *child_dir, + const char *basename, + char *out_path, + size_t out_path_size +) { + int written; + + if (!dir || !dir[0] || !basename || !basename[0] || + !out_path || out_path_size == 0) + return 0; + + if (child_dir && child_dir[0]) + written = snprintf(out_path, out_path_size, "%s/%s/%s", + dir, child_dir, basename); + else + written = snprintf(out_path, out_path_size, "%s/%s", + dir, basename); + + if (written < 0 || (size_t)written >= out_path_size) { + out_path[0] = '\0'; + return 0; + } + + return 1; +} + +int redump_resolve_dat_path( + const char *explicit_dir, + const char *executable_dir, + const char *basename, + char *out_path, + size_t out_path_size +) { + char candidate[1024]; + + if (!basename || !basename[0] || !out_path || out_path_size == 0) + return 0; + + out_path[0] = '\0'; + + if (explicit_dir && explicit_dir[0]) { + if (!redump_join_path(explicit_dir, NULL, basename, + out_path, out_path_size)) + return 0; + return redump_path_exists(out_path); + } + + if (executable_dir && executable_dir[0] && + redump_join_path(executable_dir, "redump_dat", basename, + candidate, sizeof(candidate))) { + if (redump_path_exists(candidate)) { + snprintf(out_path, out_path_size, "%s", candidate); + return 1; + } + + /* Retain the executable-relative path as the preferred diagnostic + * candidate if neither automatic location exists. */ + snprintf(out_path, out_path_size, "%s", candidate); + } + + if (redump_join_path(".", "redump_dat", basename, + candidate, sizeof(candidate))) { + if (redump_path_exists(candidate)) { + snprintf(out_path, out_path_size, "%s", candidate); + return 1; + } + + if (!out_path[0]) + snprintf(out_path, out_path_size, "%s", candidate); + } + + return 0; +} + static int redump_ascii_equal(const char *a, const char *b) { unsigned char ca, cb; if (!a || !b)