diff -r aa3baf1dd81b -r a7c48e0dca88 libidav/utils.c --- a/libidav/utils.c Fri Aug 02 21:40:05 2019 +0200 +++ b/libidav/utils.c Fri Aug 02 22:04:00 2019 +0200 @@ -41,9 +41,13 @@ #ifdef _WIN32 #include #define getpasswordchar() getch() +#define IS_PATH_SEPARATOR(c) (c == '/' || c == '\\') +#define PATH_SEPARATOR '\\' #else #include #define getpasswordchar() getchar() +#define IS_PATH_SEPARATOR(c) (c == '/') +#define PATH_SEPARATOR '/' #endif #include "webdav.h" @@ -377,10 +381,10 @@ scstr_t p1 = scstr(path1); scstr_t p2 = scstr(path2); - if(p1.ptr[p1.length-1] == '/') { + if(IS_PATH_SEPARATOR(p1.ptr[p1.length-1])) { p1.length--; } - if(p2.ptr[p2.length-1] == '/') { + if(IS_PATH_SEPARATOR(p2.ptr[p2.length-1])) { p2.length--; } @@ -393,7 +397,7 @@ } if(sstrprefix(p2, p1)) { - if(p2.ptr[p1.length] == '/') { + if(IS_PATH_SEPARATOR(p2.ptr[p1.length])) { return 1; } } @@ -401,6 +405,29 @@ return 0; } +#ifdef _WIN32 +int util_path_isabsolut(const char *path) { + if(strlen(path) < 3) { + return 0; + } + + // check if first char is A-Z or a-z + char c = path[0]; + if(!((c >= 65 && c <= 90) || (c >= 97 && c <= 122))) { + return 0; + } + + if(path[1] == ':' && path[2] == '\\') { + return 1; + } + return 0; +} +#else +int util_path_isabsolut(const char *path) { + return path[0] == '/'; +} +#endif + char* util_path_normalize(const char *path) { size_t len = strlen(path); UcxBuffer *buf = ucx_buffer_new(NULL, len+1, UCX_BUFFER_AUTOEXTEND); @@ -413,10 +440,10 @@ int seg_start = 0; for(int i=0;i<=len;i++) { char c = path[i]; - if(c == '/' || c == '\0') { + if(IS_PATH_SEPARATOR(c) || c == '\0') { const char *seg_ptr = path+seg_start; int seg_len = i - seg_start; - if(seg_ptr[0] == '/') { + if(IS_PATH_SEPARATOR(seg_ptr[0])) { seg_ptr++; seg_len--; } @@ -426,11 +453,11 @@ if(!sstrcmp(seg, SC(".."))) { for(int j=buf->pos;j>=0;j--) { char t = buf->space[j]; - if(t == '/' || j == 0) { + if(IS_PATH_SEPARATOR(t) || j == 0) { buf->pos = j; buf->size = j; buf->space[j] = 0; - add_separator = t == '/' ? 1 : 0; + add_separator = IS_PATH_SEPARATOR(t) ? 1 : 0; break; } } @@ -438,7 +465,7 @@ // ignore } else { if(add_separator) { - ucx_buffer_putc(buf, '/'); + ucx_buffer_putc(buf, PATH_SEPARATOR); } ucx_buffer_write(seg_ptr, 1, seg_len, buf); add_separator = 1; @@ -458,19 +485,19 @@ return space; } -char* util_create_relative_path(const char *abspath, const char *base) { +static char* create_relative_path(const char *abspath, const char *base) { size_t path_len = strlen(abspath); size_t base_len = strlen(base); - if(abspath[path_len-1] == '/') { + if(IS_PATH_SEPARATOR(abspath[path_len-1])) { path_len--; } - if(base[base_len-1] == '/') { + if(IS_PATH_SEPARATOR(base[base_len-1])) { base_len--; } // get base parent for(int i=base_len-1;i>=0;i--) { - if(base[i] == '/') { + if(IS_PATH_SEPARATOR(base[i])) { base_len = i+1; break; } @@ -486,7 +513,7 @@ char c = abspath[i]; if(c != base[i]) { break; - } else if(c == '/') { + } else if(IS_PATH_SEPARATOR(c)) { last_dir = i; } } @@ -497,7 +524,7 @@ // base is deeper than the link root, we have to go backwards int dircount = 0; for(int i=last_dir+1;i