diff -r 9385330bdd38 -r 5fe4453fc025 dav/sync.c --- a/dav/sync.c Tue Apr 09 21:43:36 2024 +0200 +++ b/dav/sync.c Wed Apr 10 22:07:17 2024 +0200 @@ -698,6 +698,18 @@ cxListDestroy(stack); } +static CxHashKey resource_path_key(DavResource *res) { + CxHashKey key = { NULL, 0, 0 }; + if(res && res->path) { + cxstring res_path = cx_str(res->path); + if(res_path.length > 0 && res_path.ptr[res_path.length-1] == '/') { + res_path.length--; + } + key = cx_hash_key(res_path.ptr, res_path.length); + } + return key; +} + int cmd_pull(CmdArgs *a, DavBool incoming) { if(a->argc != 1) { fprintf(stderr, "Too %s arguments\n", a->argc < 1 ? "few" : "many"); @@ -910,7 +922,7 @@ // remove every server resource from dbres // all remaining elements are the resources that are removed // on the server - cxMapRemove(dbres, cx_hash_key_str(res->path)); + cxMapRemove(dbres, resource_path_key(res)); if(!dav_get_property_ns(res, DAV_NS, "split") && res->children) { cxListInsert(stack, 0, res->children); @@ -1056,7 +1068,7 @@ break; } - LocalResource *local = cxMapGet(db->resources, cx_hash_key_str(res->path)); + LocalResource *local = cxMapGet(db->resources, resource_path_key(res)); if(local) { log_printf("update: %s\n", res->path); char *res_path = resource_local_path(res); @@ -1156,7 +1168,6 @@ return ret; } - RemoteChangeType resource_get_remote_change( CmdArgs *a, DavResource *res, @@ -1181,7 +1192,7 @@ RemoteChangeType type = cmd_getoption(a, "conflict") ? REMOTE_CHANGE_MODIFIED : REMOTE_CHANGE_CONFLICT_LOCAL_MODIFIED; - LocalResource *local = cxMapGet(db->resources, cx_hash_key_str(res->path)); + LocalResource *local = cxMapGet(db->resources, resource_path_key(res)); char *local_path = create_local_path(dir, res->path); char *link = SYNC_SYMLINK(dir) ? @@ -1806,9 +1817,15 @@ DavResource *res, SyncDatabase *db) { - char *res_path = resource_local_path(res); + cxstring res_path = cx_str(res->path); + if(res_path.length > 0 && res_path.ptr[res_path.length-1] == '/') { + res_path.length--; + } + + // TODO: use resource_local_path return value (necessary for creating links on windows) + //char *res_path = resource_local_path(res); char *local_path = create_local_path(dir, res->path); - free(res_path); + //free(res_path); log_printf("get: %s\n", res->path); // create directory @@ -1830,10 +1847,10 @@ } // if it doesn't exist in the db, create an entry for the dir - LocalResource *local = cxMapGet(db->resources, cx_hash_key_str(res->path)); + LocalResource *local = cxMapGet(db->resources, cx_hash_key(res_path.ptr, res_path.length)); if(!local) { local = calloc(1, sizeof(LocalResource)); - local->path = strdup(res->path); + local->path = cx_strdup(res_path).ptr; cxMapPut(db->resources, cx_hash_key_str(local->path), local); } local->isdirectory = 1; @@ -3445,16 +3462,20 @@ } char* resource_local_path(DavResource *res) { + cxstring path = cx_str(res->path); + if(path.length > 0 && path.ptr[path.length-1] == '/') { + path.length--; + } #ifdef SYS_LINK_EXT // on Windows, add .lnk extension to links if(dav_get_property_ns(res, DAV_PROPS_NS, "link")) { - return cx_asprintf("%s%s", res->path, SYS_LINK_EXT).ptr; + return cx_asprintf("%.*s%s", (int)path.length, path.ptr, SYS_LINK_EXT).ptr; } else { // not a link - return strdup(res->path); + return cx_strdup(path).ptr; } #else - return strdup(res->path); + return cx_strdup(path).ptr; #endif }