Sat, 18 Mar 2023 15:52:35 +0100
add libxattr
/* * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. * * Copyright 2023 Olaf Wintermann. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. */ #include "xattrbackend.h" #include "../util/util.h" #include "../util/libxattr.h" static WebdavBackend webdav_xattr_backend = { webdav_xattr_propfind_init, webdav_xattr_propfind_do, webdav_xattr_propfind_finish, webdav_xattr_proppatch_do, webdav_xattr_proppatch_finish, NULL, // opt_mkcol NULL, // opt_mkcol_finish NULL, // opt_delete NULL, // opt_delete_finish WS_WEBDAV_PROPFIND_USE_VFS | WS_WEBDAV_PROPPATCH_USE_VFS, // settings NULL, // instance NULL // next }; int webdav_init_xattr_backend(void) { if(webdav_register_backend("xattr", webdav_xattr_init, webdav_xattr_create)) { return 1; } return 0; } void* webdav_xattr_init(ServerConfiguration *cfg, pool_handle_t *pool, WSConfigNode *config) { WebdavXAttrRepository *repo = pool_malloc(pool, sizeof(WebdavXAttrRepository)); if(!repo) { return NULL; } // TODO: config repo->xattr_name = "webdav_properties"; return repo; } WebdavBackend* webdav_xattr_create(Session *sn, Request *rq, pblock *pb, void *initData) { WebdavBackend *dav = pool_malloc(sn->pool, sizeof(WebdavBackend)); if(!dav) { return NULL; } WebdavXAttrBackend *instance = pool_malloc(sn->pool, sizeof(WebdavXAttrBackend)); if(!instance) { return NULL; } instance->repo = initData; *dav = webdav_xattr_backend; dav->instance = instance; return dav; } /* -------------------- webdav backend imlementation ----------------------*/ int webdav_xattr_propfind_init( WebdavPropfindRequest *rq, const char *path, const char *href, WebdavPList **outplist) { // make sure the sys vfs is used, because currently only // native sysfs xattr is supported if(rq->rq->vfs) { log_ereport(LOG_FAILURE, "webdav-propfind: xattr backend unsupported with non-native VFS"); return 1; } XAttrPropfind *xprop = pool_malloc(rq->sn->pool, sizeof(XAttrPropfind)); if(!xprop) { return 1; } rq->userdata = xprop; xprop->base_href = href; xprop->base_path = path; return 0; } int webdav_xattr_propfind_do( WebdavPropfindRequest *request, WebdavResponse *response, VFS_DIR parent, WebdavResource *resource, struct stat *s) { Session *sn = request->sn; Request *rq = request->rq; WebdavXAttrBackend *xdav = request->dav->instance; WebdavXAttrRepository *repo = xdav->repo; XAttrPropfind *xprop = request->userdata; const char *path; char *path_dp = NULL; if(!parent) { // use base path path = xprop->base_path; } else { size_t base_href_len = strlen(xprop->base_href); size_t base_path_len = strlen(xprop->base_path); char *res_path = resource->href + base_href_len; size_t res_path_len = strlen(res_path); path_dp = pool_malloc(sn->pool, base_path_len + res_path_len + 2); memcpy(path_dp, xprop->base_path, base_path_len); int s = 0; if(path_dp[base_path_len-1] != '/' && res_path[0] != '/') { path_dp[base_path_len] = '/'; s = 1; } memcpy(path_dp + base_path_len + s, res_path, res_path_len); path_dp[base_path_len + s + res_path_len] = 0; path = path_dp; } ssize_t xattr_data_len = 0; char *xattr_data = xattr_get_alloc( sn->pool, (libxattr_malloc_func)pool_malloc, (libxattr_free_func)pool_free, path, repo->xattr_name, &xattr_data_len); return 0; } int webdav_xattr_propfind_finish(WebdavPropfindRequest *rq) { return 0; } int webdav_xattr_proppatch_do( WebdavProppatchRequest *request, WebdavResource *response, VFSFile *file, WebdavPList **setInOut, WebdavPList **removeInOut) { return 0; } int webdav_xattr_proppatch_finish( WebdavProppatchRequest *request, WebdavResource *response, VFSFile *file, WSBool commit) { return 0; }