diff options
author | Michael Pavone <pavone@retrodev.com> | 2016-05-01 21:39:43 -0700 |
---|---|---|
committer | Michael Pavone <pavone@retrodev.com> | 2016-05-01 21:39:43 -0700 |
commit | 5278b492751f31df81c297c60630b3106776b29e (patch) | |
tree | 15586129807f0fa613c43aaa6c63c71efaf8a6eb | |
parent | fc14e18db5375b0b8e081781c4c103c53da82add (diff) |
Removed assumptions that path separators are Unix style outside of Unix-only verions of functions
-rw-r--r-- | blastem.c | 6 | ||||
-rw-r--r-- | menu.c | 10 | ||||
-rw-r--r-- | util.c | 36 | ||||
-rw-r--r-- | util.h | 10 |
4 files changed, 49 insertions, 13 deletions
@@ -330,7 +330,7 @@ m68k_context * sync_components(m68k_context * context, uint32_t address) } else { char slotname[] = "slot_0.gst"; slotname[5] = '0' + slot; - char const *parts[] = {gen->save_dir, "/", slotname}; + char const *parts[] = {gen->save_dir, PATH_SEP, slotname}; save_path = alloc_concat_m(3, parts); } save_gst(gen, save_path, address); @@ -1027,7 +1027,7 @@ void set_region(rom_info *info, uint8_t region) void setup_saves(char *fname, rom_info *info, genesis_context *context) { char * barename = basename_no_extension(fname); - char const * parts[3] = {get_save_dir(), "/", barename}; + char const * parts[3] = {get_save_dir(), PATH_SEP, barename}; char *save_dir = alloc_concat_m(3, parts); if (!ensure_dir_exists(save_dir)) { warning("Failed to create save directory %s\n", save_dir); @@ -1170,7 +1170,7 @@ int main(int argc, char ** argv) if (!romfname) { romfname = "menu.bin"; } - if (romfname[0] == '/') { + if (is_absolute_path(romfname)) { if (!(rom_size = load_rom(romfname))) { fatal_error("Failed to open UI ROM %s for reading", romfname); } @@ -195,14 +195,14 @@ void * menu_write_w(uint32_t address, void * context, uint16_t value) size_t len = strlen(menu->curpath); while (len > 1) { --len; - if (menu->curpath[len] == '/') { + if (is_path_sep(menu->curpath[len])) { menu->curpath[len] = 0; break; } } } else { char *tmp = menu->curpath; - char const *pieces[] = {menu->curpath, "/", buf}; + char const *pieces[] = {menu->curpath, PATH_SEP, buf}; menu->curpath = alloc_concat_m(3, pieces); free(tmp); } @@ -211,7 +211,7 @@ void * menu_write_w(uint32_t address, void * context, uint16_t value) case 2: { char buf[4096]; copy_string_from_guest(m68k, dst, buf, sizeof(buf)); - char const *pieces[] = {menu->curpath, "/", buf}; + char const *pieces[] = {menu->curpath, PATH_SEP, buf}; gen->next_rom = alloc_concat_m(3, pieces); m68k->should_return = 1; break; @@ -236,7 +236,7 @@ void * menu_write_w(uint32_t address, void * context, uint16_t value) if (gen->next_context && gen->next_context->save_dir) { char *end = buffer + SAVE_INFO_BUFFER_SIZE; char slotfile[] = "slot_0.gst"; - char const * parts[3] = {gen->next_context->save_dir, "/", slotfile}; + char const * parts[3] = {gen->next_context->save_dir, PATH_SEP, slotfile}; struct tm ltime; char *fname; time_t modtime; @@ -297,7 +297,7 @@ void * menu_write_w(uint32_t address, void * context, uint16_t value) numslotname[5] = '0' + dst; slotname = numslotname; } - char const *parts[] = {gen->next_context->save_dir, "/", slotname}; + char const *parts[] = {gen->next_context->save_dir, PATH_SEP, slotname}; char *gstpath = alloc_concat_m(3, parts); uint32_t pc = load_gst(gen->next_context, gstpath); free(gstpath); @@ -94,6 +94,26 @@ char * split_keyval(char * text) return text+1; } +char is_path_sep(char c) +{ +#ifdef _WIN32 + if (c == '\\') { + return 1; + } +#endif + return c == '/'; +} + +char is_absolute_path(char *path) +{ +#ifdef _WIN32 + if (path[1] == ':' && is_path_sep(path[2]) && isalpha(path[0])) { + return 1; + } +#endif + return is_path_sep(path[0]); +} + char * basename_no_extension(char *path) { char *lastdot = NULL; @@ -103,7 +123,7 @@ char * basename_no_extension(char *path) { if (*cur == '.') { lastdot = cur; - } else if (*cur == '/') { + } else if (is_path_sep(*cur)) { lastslash = cur + 1; } } @@ -314,7 +334,13 @@ int ensure_dir_exists(char *path) return 0; } char *parent = strdup(path); - char *sep = strrchr(parent, '/'); + //Windows technically supports both native and Unix-style path separators + //so search for both + char *sep = strrchr(parent, '\\'); + char *osep = strrchr(parent, '/'); + if (osep && (!sep || osep < sep)) { + sep = osep; + } if (!sep || sep == parent) { //relative path, but for some reason we failed return 0; @@ -372,7 +398,7 @@ char * get_exe_dir() int linksize = strlen(linktext); for(cur = linktext + linksize - 1; cur != linktext; cur--) { - if (*cur == '/') { + if (is_path_sep(*cur)) { *cur = 0; break; } @@ -387,7 +413,7 @@ fallback: int pathsize = strlen(exe_str); for(cur = exe_str + pathsize - 1; cur != exe_str; cur--) { - if (*cur == '/') { + if (is_path_sep(*cur)) { exe_dir = malloc(cur-exe_str+1); memcpy(exe_dir, exe_str, cur-exe_str); exe_dir[cur-exe_str] = 0; @@ -533,7 +559,7 @@ char *read_bundled_file(char *name, long *sizeret) } return NULL; } - char const *pieces[] = {exe_dir, "/", name}; + char const *pieces[] = {exe_dir, PATH_SEP, name}; char *path = alloc_concat_m(3, pieces); FILE *f = fopen(path, "rb"); free(path); @@ -9,6 +9,12 @@ typedef struct { uint8_t is_dir; } dir_entry; +#ifdef _WIN32 +#define PATH_SEP "\\" +#else +#define PATH_SEP "/" +#endif + //Utility functions //Allocates a new string containing the concatenation of first and second @@ -21,6 +27,10 @@ long file_size(FILE * f); char * strip_ws(char * text); //Inserts a null after the first word, returns a pointer to the second word char * split_keyval(char * text); +//Determines whether a character is a valid path separator for the current platform +char is_path_sep(char c); +//Determines whether a path is considered an absolute path on the current platform +char is_absolute_path(char *path); //Returns the basename of a path with th extension (if any) stripped char * basename_no_extension(char *path); //Gets the smallest power of two that is >= a certain value, won't work for values > 0x80000000 |