Mon, 10 Nov 2025 21:52:51 +0100
update ucx
| 1 | 1 | /* |
| 2 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. | |
| 3 | * | |
| 4 | * Copyright 2018 Olaf Wintermann. All rights reserved. | |
| 5 | * | |
| 6 | * Redistribution and use in source and binary forms, with or without | |
| 7 | * modification, are permitted provided that the following conditions are met: | |
| 8 | * | |
| 9 | * 1. Redistributions of source code must retain the above copyright | |
| 10 | * notice, this list of conditions and the following disclaimer. | |
| 11 | * | |
| 12 | * 2. Redistributions in binary form must reproduce the above copyright | |
| 13 | * notice, this list of conditions and the following disclaimer in the | |
| 14 | * documentation and/or other materials provided with the distribution. | |
| 15 | * | |
| 16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | |
| 17 | * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
| 18 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
| 19 | * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE | |
| 20 | * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | |
| 21 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF | |
| 22 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS | |
| 23 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN | |
| 24 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | |
| 25 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | |
| 26 | * POSSIBILITY OF SUCH DAMAGE. | |
| 27 | */ | |
| 28 | ||
| 29 | #include <stdio.h> | |
| 30 | #include <stdlib.h> | |
| 31 | #include <string.h> | |
| 32 | #include <libxml/tree.h> | |
| 33 | ||
| 34 | #include "utils.h" | |
| 35 | #include "webdav.h" | |
| 36 | #include "session.h" | |
| 37 | #include "methods.h" | |
| 38 | #include <cx/buffer.h> | |
| 39 | #include <cx/linked_list.h> | |
| 40 | #include <cx/hash_map.h> | |
| 41 | #include <cx/compare.h> | |
| 42 | #include "davqlparser.h" | |
| 43 | #include "davqlexec.h" | |
| 44 | ||
| 45 | ||
| 46 | DavContext* dav_context_new(void) { | |
| 47 | // initialize | |
| 48 | DavContext *context = calloc(1, sizeof(DavContext)); | |
| 49 | if(!context) { | |
| 50 | return NULL; | |
| 51 | } | |
|
53
da05df77652e
add menu items to open resource properties
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
49
diff
changeset
|
52 | context->sessions = cxLinkedListCreate(cxDefaultAllocator, cx_cmp_ptr, CX_STORE_POINTERS); |
|
49
2f71f4ee247a
update toolkit, ucx, libidav
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
18
diff
changeset
|
53 | cxDefineDestructor(context->sessions, dav_session_destructor); |
| 1 | 54 | context->http_proxy = calloc(1, sizeof(DavProxy)); |
| 55 | if(!context->http_proxy) { | |
| 56 | dav_context_destroy(context); | |
| 57 | return NULL; | |
| 58 | } | |
| 59 | context->https_proxy = calloc(1, sizeof(DavProxy)); | |
| 60 | if(!context->https_proxy) { | |
| 61 | dav_context_destroy(context); | |
| 62 | return NULL; | |
| 63 | } | |
| 64 | context->namespaces = cxHashMapCreate(cxDefaultAllocator, CX_STORE_POINTERS, 16); | |
| 65 | if(!context->namespaces) { | |
| 66 | dav_context_destroy(context); | |
| 67 | return NULL; | |
| 68 | } | |
| 69 | context->namespaceinfo = cxHashMapCreate(cxDefaultAllocator, CX_STORE_POINTERS, 16); | |
| 70 | if(!context->namespaceinfo) { | |
| 71 | dav_context_destroy(context); | |
| 72 | } | |
| 73 | context->keys = cxHashMapCreate(cxDefaultAllocator, CX_STORE_POINTERS, 16); | |
| 74 | if(!context->keys) { | |
| 75 | dav_context_destroy(context); | |
| 76 | return NULL; | |
| 77 | } | |
| 78 | ||
| 79 | // add DAV: namespace | |
| 80 | if(dav_add_namespace(context, "D", "DAV:")) { | |
| 81 | dav_context_destroy(context); | |
| 82 | return NULL; | |
| 83 | } | |
| 84 | ||
| 85 | ||
| 86 | // add idav namespace | |
| 87 | if(dav_add_namespace(context, "idav", DAV_NS)) { | |
| 88 | dav_context_destroy(context); | |
| 89 | return NULL; | |
| 90 | } | |
| 91 | ||
| 92 | // add idavprops namespace | |
| 93 | if(dav_add_namespace(context, "idavprops", DAV_PROPS_NS)) { | |
| 94 | dav_context_destroy(context); | |
| 95 | return NULL; | |
| 96 | } | |
| 97 | ||
| 98 | return context; | |
| 99 | } | |
| 100 | ||
| 101 | void dav_context_destroy(DavContext *ctx) { | |
| 102 | // destroy all sessions assoziated with this context | |
| 103 | // ctx->sessions destructor must be dav_session_destructor | |
|
101
7b3a3130be44
update ucx, toolkit
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
53
diff
changeset
|
104 | cxListFree(ctx->sessions); |
| 1 | 105 | |
| 106 | if(ctx->http_proxy) { | |
| 107 | free(ctx->http_proxy); | |
| 108 | } | |
| 109 | if(ctx->https_proxy) { | |
| 110 | free(ctx->https_proxy); | |
| 111 | } | |
| 112 | ||
| 113 | if(ctx->namespaces) { | |
|
102
64ded9f6a6c6
update libs (ucx, toolkit, libidav)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
101
diff
changeset
|
114 | CxMapIterator i = cxMapIteratorValues(ctx->namespaces); |
| 1 | 115 | cx_foreach(DavNamespace*, ns, i) { |
| 116 | if(!ns) continue; | |
| 117 | if(ns->prefix) { | |
| 118 | free(ns->prefix); | |
| 119 | } | |
| 120 | if(ns->name) { | |
| 121 | free(ns->name); | |
| 122 | } | |
| 123 | free(ns); | |
| 124 | } | |
|
101
7b3a3130be44
update ucx, toolkit
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
53
diff
changeset
|
125 | cxMapFree(ctx->namespaces); |
| 1 | 126 | } |
| 127 | if(ctx->namespaceinfo) { | |
| 128 | // TODO: implement | |
| 129 | } | |
| 130 | if(ctx->keys) { | |
|
102
64ded9f6a6c6
update libs (ucx, toolkit, libidav)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
101
diff
changeset
|
131 | CxMapIterator i = cxMapIteratorValues(ctx->keys); |
| 1 | 132 | cx_foreach(DavKey*, key, i) { |
| 133 | if(!key) continue; | |
| 134 | if(key->name) { | |
| 135 | free(key->name); | |
| 136 | } | |
| 137 | if(key->data) { | |
| 138 | free(key->data); | |
| 139 | } | |
| 140 | free(key); | |
| 141 | } | |
|
101
7b3a3130be44
update ucx, toolkit
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
53
diff
changeset
|
142 | cxMapFree(ctx->keys); |
| 1 | 143 | } |
| 144 | ||
| 145 | free(ctx); | |
| 146 | } | |
| 147 | ||
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
148 | #ifndef _WIN32 |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
149 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
150 | void dav_context_set_mtsafe(DavContext *ctx, DavBool enable) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
151 | if (enable) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
152 | pthread_mutex_init(&ctx->mutex, NULL); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
153 | } else { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
154 | pthread_mutex_destroy(&ctx->mutex); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
155 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
156 | ctx->mtsafe = enable; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
157 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
158 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
159 | void dav_context_lock(DavContext *ctx) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
160 | if (ctx->mtsafe) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
161 | pthread_mutex_lock(&ctx->mutex); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
162 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
163 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
164 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
165 | void dav_context_unlock(DavContext *ctx) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
166 | if (ctx->mtsafe) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
167 | pthread_mutex_unlock(&ctx->mutex); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
168 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
169 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
170 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
171 | #else |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
172 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
173 | void dav_context_set_mtsafe(DavContext *ctx, DavBool enable) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
174 | if (enable) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
175 | ctx->mutex = CreateMutex(NULL, FALSE, NULL); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
176 | } else { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
177 | CloseHandle(ctx->mutex); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
178 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
179 | ctx->mtsafe = enable; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
180 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
181 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
182 | void dav_context_lock(DavContext *ctx) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
183 | if (ctx->mtsafe) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
184 | WaitForSingleObject(ctx->mutex, INFINITE); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
185 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
186 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
187 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
188 | void dav_context_unlock(DavContext *ctx) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
189 | if (ctx->mtsafe) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
190 | ReleaseMutex(ctx->mutex); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
191 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
192 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
193 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
194 | #endif |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
195 | |
| 1 | 196 | void dav_context_add_key(DavContext *context, DavKey *key) { |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
197 | dav_context_lock(context); |
| 1 | 198 | cxMapPut(context->keys, cx_hash_key_str(key->name), key); |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
199 | dav_context_unlock(context); |
| 1 | 200 | } |
| 201 | ||
| 202 | DavKey* dav_context_get_key(DavContext *context, const char *name) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
203 | DavKey *key = NULL; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
204 | dav_context_lock(context); |
| 1 | 205 | if(name) { |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
206 | key = cxMapGet(context->keys, cx_hash_key_str(name)); |
| 1 | 207 | } |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
208 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
209 | return key; |
| 1 | 210 | } |
| 211 | ||
| 212 | int dav_add_namespace(DavContext *context, const char *prefix, const char *name) { | |
| 213 | DavNamespace *namespace = malloc(sizeof(DavNamespace)); | |
| 214 | if(!namespace) { | |
| 215 | return 1; | |
| 216 | } | |
| 217 | ||
| 218 | char *p = strdup(prefix); | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
219 | if (!p) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
220 | free(namespace); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
221 | return 1; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
222 | } |
| 1 | 223 | char *n = strdup(name); |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
224 | if (!n) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
225 | free(namespace); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
226 | free(p); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
227 | return 1; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
228 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
229 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
230 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
231 | |
| 1 | 232 | int err = 0; |
| 233 | if(p && n) { | |
| 234 | namespace->prefix = p; | |
| 235 | namespace->name = n; | |
| 236 | err = cxMapPut(context->namespaces, cx_hash_key_str(prefix), namespace); | |
| 237 | } | |
| 238 | ||
| 239 | if(err) { | |
| 240 | free(namespace); | |
| 241 | if(p) free(p); | |
| 242 | if(n) free(n); | |
| 243 | } | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
244 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
245 | dav_context_unlock(context); |
| 1 | 246 | |
| 247 | return err; | |
| 248 | } | |
| 249 | ||
| 250 | DavNamespace* dav_get_namespace(DavContext *context, const char *prefix) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
251 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
252 | DavNamespace *ns = cxMapGet(context->namespaces, cx_hash_key_str(prefix)); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
253 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
254 | return ns; |
| 1 | 255 | } |
| 256 | ||
| 257 | DavNamespace* dav_get_namespace_s(DavContext *context, cxstring prefix) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
258 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
259 | DavNamespace *ns = cxMapGet(context->namespaces, cx_hash_key(prefix.ptr, prefix.length)); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
260 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
261 | return ns; |
| 1 | 262 | } |
| 263 | ||
| 264 | int dav_enable_namespace_encryption(DavContext *context, const char *ns, DavBool encrypt) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
265 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
266 | |
| 1 | 267 | CxHashKey hkey = cx_hash_key_str(ns); |
| 268 | DavNSInfo *info = cxMapGet(context->namespaceinfo, hkey); | |
| 269 | if(!info) { | |
| 270 | info = calloc(1, sizeof(DavNSInfo)); | |
| 271 | info->encrypt = encrypt; | |
| 272 | cxMapPut(context->namespaceinfo, hkey, info); | |
| 273 | } else { | |
| 274 | info->encrypt = encrypt; | |
| 275 | } | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
276 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
277 | dav_context_unlock(context); |
| 1 | 278 | return 0; |
| 279 | } | |
| 280 | ||
| 281 | int dav_namespace_is_encrypted(DavContext *context, const char *ns) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
282 | int ret = 0; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
283 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
284 | |
| 1 | 285 | DavNSInfo *info = cxMapGet(context->namespaceinfo, cx_hash_key_str(ns)); |
| 286 | if(info) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
287 | ret = info->encrypt; |
| 1 | 288 | } |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
289 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
290 | return ret; |
| 1 | 291 | } |
| 292 | ||
| 293 | void dav_get_property_namespace_str( | |
| 294 | DavContext *ctx, | |
| 295 | char *prefixed_name, | |
| 296 | char **ns, | |
| 297 | char **name) | |
| 298 | { | |
| 299 | // TODO: rewrite using dav_get_property_ns | |
| 300 | ||
| 301 | char *pname = strchr(prefixed_name, ':'); | |
| 302 | char *pns = "DAV:"; | |
| 303 | if(pname) { | |
|
49
2f71f4ee247a
update toolkit, ucx, libidav
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
18
diff
changeset
|
304 | DavNamespace *davns = dav_get_namespace_s( |
| 1 | 305 | ctx, |
| 306 | cx_strn(prefixed_name, pname-prefixed_name)); | |
|
49
2f71f4ee247a
update toolkit, ucx, libidav
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
18
diff
changeset
|
307 | if(davns) { |
|
2f71f4ee247a
update toolkit, ucx, libidav
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
18
diff
changeset
|
308 | pns = davns->name; |
| 1 | 309 | pname++; |
| 310 | } else { | |
| 311 | pns = NULL; | |
| 312 | pname = NULL; | |
| 313 | } | |
| 314 | } else { | |
| 315 | pname = prefixed_name; | |
| 316 | } | |
| 317 | *ns = pns; | |
| 318 | *name = pname; | |
| 319 | } | |
| 320 | ||
| 321 | DavNamespace* dav_get_property_namespace( | |
| 322 | DavContext *ctx, | |
| 323 | char *prefixed_name, | |
| 324 | char **name) | |
| 325 | { | |
| 326 | char *pname = strchr(prefixed_name, ':'); | |
| 327 | if(pname) { | |
| 328 | DavNamespace *ns = dav_get_namespace_s( | |
| 329 | ctx, | |
| 330 | cx_strn(prefixed_name, pname-prefixed_name)); | |
| 331 | if(ns) { | |
| 332 | *name = pname +1; | |
| 333 | return ns; | |
| 334 | } else { | |
| 335 | *name = NULL; | |
| 336 | return NULL; | |
| 337 | } | |
| 338 | } else { | |
| 339 | *name = prefixed_name; | |
| 340 | return dav_get_namespace_s(ctx, cx_str("D")); | |
| 341 | } | |
| 342 | } | |
| 343 | ||
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
344 | int dav_context_add_session(DavContext *context, DavSession *sn) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
345 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
346 | int ret = cxListAdd(context->sessions, sn); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
347 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
348 | return ret; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
349 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
350 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
351 | int dav_context_remove_session(DavContext *context, DavSession *sn) { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
352 | int ret = 0; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
353 | dav_context_lock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
354 | CxList *sessions = context->sessions; |
| 113 | 355 | size_t i = cxListFind(sessions, sn); |
| 356 | if(cxListIndexValid(sessions, i)) { | |
|
18
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
357 | cxListRemove(sessions, i); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
358 | } else { |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
359 | ret = 1; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
360 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
361 | dav_context_unlock(context); |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
362 | return ret; |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
363 | } |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
364 | |
|
af411868ab9b
implement dnd upload (without progressbar)
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
1
diff
changeset
|
365 | |
| 1 | 366 | // TODO: add sstr_t version of dav_get_property_ns |
| 367 | ||
| 368 | void dav_set_effective_href(DavSession *sn, DavResource *resource) { | |
| 369 | char *eff_url; | |
| 370 | curl_easy_getinfo(sn->handle, CURLINFO_EFFECTIVE_URL, &eff_url); | |
| 371 | if(eff_url) { | |
| 372 | const char *href = util_url_path(eff_url); | |
| 373 | if(strcmp(href, resource->href)) { | |
| 374 | dav_session_free(sn, resource->href); | |
| 375 | resource->href = dav_session_strdup(sn, href); | |
| 376 | } | |
| 377 | } | |
| 378 | } | |
| 379 | ||
| 380 | DavResource* dav_get(DavSession *sn, char *path, const char *properties) { | |
| 381 | CURL *handle = sn->handle; | |
| 382 | DavResource *resource = dav_resource_new(sn, path); | |
| 383 | util_set_url(sn, dav_resource_get_href(resource)); | |
| 384 | ||
| 385 | CxList *proplist = NULL; | |
| 386 | if(properties) { | |
| 387 | proplist = parse_properties_string(sn->context, cx_str(properties)); | |
| 388 | } | |
| 389 | CxBuffer *rqbuf = create_propfind_request(sn, proplist, "propfind", 0); | |
| 390 | CxBuffer *rpbuf = cxBufferCreate(NULL, 4096, cxDefaultAllocator, CX_BUFFER_FREE_CONTENTS|CX_BUFFER_AUTO_EXTEND); | |
| 391 | ||
| 392 | //fwrite(rqbuf->space, 1, rqbuf->size, stdout); | |
| 393 | //printf("\n"); | |
| 394 | ||
| 395 | CURLcode ret = do_propfind_request(sn, rqbuf, rpbuf); | |
| 396 | long status = 0; | |
| 397 | curl_easy_getinfo (handle, CURLINFO_RESPONSE_CODE, &status); | |
| 398 | if(ret == CURLE_OK && status == 207) { | |
| 399 | dav_set_effective_href(sn, resource); | |
| 400 | ||
| 401 | //printf("response\n%s\n", rpbuf->space); | |
| 402 | // TODO: use PropfindParser | |
| 403 | resource = parse_propfind_response(sn, resource, rpbuf); | |
| 404 | resource->exists = 1; | |
| 405 | sn->error = DAV_OK; | |
| 406 | } else { | |
| 407 | dav_session_set_error(sn, ret, status); | |
| 408 | dav_resource_free(resource); | |
| 409 | resource = NULL; | |
| 410 | } | |
| 411 | ||
| 412 | cxBufferFree(rqbuf); | |
| 413 | cxBufferFree(rpbuf); | |
| 414 | ||
| 415 | if(proplist) { | |
| 416 | CxIterator i = cxListIterator(proplist); | |
| 417 | cx_foreach(DavProperty*, p, i) { | |
| 418 | free(p->name); | |
| 419 | } | |
|
101
7b3a3130be44
update ucx, toolkit
Olaf Wintermann <olaf.wintermann@gmail.com>
parents:
53
diff
changeset
|
420 | cxListFree(proplist); |
| 1 | 421 | } |
| 422 | ||
| 423 | return resource; | |
| 424 | } | |
| 425 | ||
| 426 | ||
| 427 | int dav_propfind(DavSession *sn, DavResource *root, CxBuffer *rqbuf) { | |
| 428 | // clean resource properties | |
| 429 | DavResourceData *data = root->data; | |
| 430 | cxMapClear(data->properties); // TODO: free existing content | |
| 431 | ||
| 432 | CURL *handle = sn->handle; | |
| 433 | util_set_url(sn, dav_resource_get_href(root)); | |
| 434 | ||
| 435 | CxBuffer *rpbuf = cxBufferCreate(NULL, 4096, cxDefaultAllocator, CX_BUFFER_FREE_CONTENTS|CX_BUFFER_AUTO_EXTEND); | |
| 436 | DavResource *resource = root; | |
| 437 | CURLcode ret = do_propfind_request(sn, rqbuf, rpbuf); | |
| 438 | long status = 0; | |
| 439 | long error = 0; | |
| 440 | curl_easy_getinfo (handle, CURLINFO_RESPONSE_CODE, &status); | |
| 441 | if(ret == CURLE_OK && status == 207) { | |
| 442 | //printf("response\n%s\n", rpbuf->space); | |
| 443 | dav_set_effective_href(sn, resource); | |
| 444 | // TODO: use PropfindParser | |
| 445 | resource = parse_propfind_response(sn, resource, rpbuf); | |
| 446 | sn->error = DAV_OK; | |
| 447 | root->exists = 1; | |
| 448 | } else { | |
| 449 | dav_session_set_error(sn, ret, status); | |
| 450 | error = 1; | |
| 451 | } | |
| 452 | cxBufferFree(rpbuf); | |
| 453 | return error; | |
| 454 | } | |
| 455 | ||
| 456 | CxList* parse_properties_string(DavContext *context, cxstring str) { | |
| 457 | CxList *proplist = cxLinkedListCreateSimple(sizeof(DavProperty)); | |
| 458 | ||
| 459 | CxStrtokCtx tok = cx_strtok(str, cx_str(","), INT_MAX); | |
| 460 | cxstring s; | |
| 461 | while(cx_strtok_next(&tok, &s)) { | |
| 462 | cxstring nsname = cx_strchr(s, ':'); | |
| 463 | if(nsname.length > 0) { | |
| 464 | cxstring nspre = cx_strsubsl(s, 0, nsname.ptr - s.ptr); | |
| 465 | nsname.ptr++; | |
| 466 | nsname.length--; | |
| 467 | ||
| 468 | DavProperty dp; | |
| 469 | cxstring pre = cx_strtrim(nspre); | |
| 470 | dp.ns = dav_get_namespace_s(context, pre); | |
| 471 | dp.name = cx_strdup(nsname).ptr; | |
| 472 | dp.value = NULL; | |
| 473 | if(dp.ns && dp.name) { | |
| 474 | cxListAdd(proplist, &dp); | |
| 475 | } else { | |
| 476 | free(dp.name); | |
| 477 | } | |
| 478 | } | |
| 479 | } | |
| 480 | ||
| 481 | return proplist; | |
| 482 | } | |
| 483 | ||
| 484 | DavResource* dav_query(DavSession *sn, char *query, ...) { | |
| 485 | DavQLStatement *stmt = dav_parse_statement(cx_str(query)); | |
| 486 | if(!stmt) { | |
| 487 | sn->error = DAV_ERROR; | |
| 488 | return NULL; | |
| 489 | } | |
| 490 | if(stmt->errorcode != 0) { | |
| 491 | sn->error = DAV_QL_ERROR; | |
| 492 | dav_free_statement(stmt); | |
| 493 | return NULL; | |
| 494 | } | |
| 495 | ||
| 496 | va_list ap; | |
| 497 | va_start(ap, query); | |
| 498 | DavResult result = dav_statement_execv(sn, stmt, ap); | |
| 499 | va_end(ap); | |
| 500 | ||
| 501 | dav_free_statement(stmt); | |
| 502 | ||
| 503 | if(result.status == -1) { | |
| 504 | if(result.result) { | |
| 505 | dav_resource_free(result.result); | |
| 506 | result.result = NULL; | |
| 507 | } | |
| 508 | } | |
| 509 | ||
| 510 | return result.result; | |
| 511 | } | |
| 512 | ||
| 513 | ||
| 514 | ||
| 515 | ||
| 516 | void dav_verbose_log( | |
| 517 | DavSession *sn, | |
| 518 | const char *method, | |
| 519 | const char *url, | |
| 520 | const char *request_body, | |
| 521 | size_t request_bodylen, | |
| 522 | int status, | |
| 523 | const char *response_body, | |
| 524 | size_t response_bodylen) | |
| 525 | { | |
| 526 | fprintf(stderr, "# method: %s url: %s status: %d\n", method, url, status); | |
| 527 | fprintf(stderr, "# request len: %d\n%.*s\n", (int)request_bodylen, (int)request_bodylen, request_body); | |
| 528 | fprintf(stderr, "# response len: %d\n%.*s\n", (int)response_bodylen, (int)response_bodylen, response_body); | |
| 529 | } |