From: Xavi Hernandez Date: Tue, 13 Jan 2026 12:23:28 +0000 (+0100) Subject: libcephfs_proxy: add option to specify the working directory X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=c417dd6c40700657d0ba158f87a35e8d6584d11e;p=ceph.git libcephfs_proxy: add option to specify the working directory Signed-off-by: Xavi Hernandez --- diff --git a/src/libcephfs_proxy/libcephfsd.c b/src/libcephfs_proxy/libcephfsd.c index bbb5700d21f..cb424fea65f 100644 --- a/src/libcephfs_proxy/libcephfsd.c +++ b/src/libcephfs_proxy/libcephfsd.c @@ -2232,15 +2232,48 @@ static bool check_stop(proxy_link_t *link) static int32_t server_start(proxy_manager_t *manager) { proxy_server_t server; + struct stat st; proxy_t *proxy; + const char *path; + char *wd; + int32_t err; proxy = container_of(manager, proxy_t, manager); server.manager = manager; server.settings = &proxy->settings; - return proxy_link_server(&server.link, &proxy->settings, - accept_connection, check_stop); + path = proxy->settings.work_dir; + wd = realpath(path, NULL); + if (wd == NULL) { + return proxy_log(LOG_ERR, errno, + "Failed to resolve the working directory"); + } + + if (stat(wd, &st) < 0) { + err = proxy_log(LOG_ERR, errno, + "Failed to check the working directory"); + goto done; + } + + if (!S_ISDIR(st.st_mode)) { + err = proxy_log(LOG_ERR, EINVAL, + "The provided path for the working directory " + "is not a directory"); + goto done; + } + + proxy->settings.work_dir = wd; + + err = proxy_link_server(&server.link, &proxy->settings, + accept_connection, check_stop); + + proxy->settings.work_dir = path; + +done: + free(wd); + + return err; } static void log_format(struct iovec *iov, char *buffer, size_t size, @@ -2294,10 +2327,13 @@ static void log_print(proxy_log_handler_t *handler, int32_t level, int32_t err, } static struct option main_opts[] = { - {"socket", required_argument, NULL, 's'}, + {"socket", required_argument, NULL, 's'}, + {"work-dir", required_argument, NULL, 'w'}, {} }; +static const char short_opts[] = ":s:w:"; + int32_t main(int32_t argc, char *argv[]) { struct timespec now; @@ -2313,15 +2349,18 @@ int32_t main(int32_t argc, char *argv[]) proxy_log_register(&proxy.log_handler, log_print); proxy.settings.socket_path = PROXY_SOCKET; + proxy.settings.work_dir = "."; env = getenv(PROXY_SOCKET_ENV); if (env != NULL) { proxy.settings.socket_path = env; } - while ((val = getopt_long(argc, argv, ":s:", main_opts, NULL)) >= 0) { + while ((val = getopt_long(argc, argv, short_opts, main_opts, NULL)) >= 0) { if (val == 's') { proxy.settings.socket_path = optarg; + } else if (val == 'w') { + proxy.settings.work_dir = optarg; } else if (val == ':') { proxy_log(LOG_ERR, ENODATA, "Argument missing for '%s'\n", optopt); diff --git a/src/libcephfs_proxy/proxy.h b/src/libcephfs_proxy/proxy.h index f5a409625f2..e0295e4ecf3 100644 --- a/src/libcephfs_proxy/proxy.h +++ b/src/libcephfs_proxy/proxy.h @@ -97,6 +97,7 @@ struct _list { struct _proxy_settings { const char *socket_path; + const char *work_dir; }; #endif diff --git a/src/libcephfs_proxy/proxy_mount.c b/src/libcephfs_proxy/proxy_mount.c index 33cc0e62c31..1c404f64e26 100644 --- a/src/libcephfs_proxy/proxy_mount.c +++ b/src/libcephfs_proxy/proxy_mount.c @@ -554,11 +554,11 @@ static int32_t proxy_config_source_validate(int32_t fd, struct stat *before, return 1; } -static int32_t proxy_config_destination_prepare(void) +static int32_t proxy_config_destination_prepare(proxy_settings_t *settings) { int32_t fd; - fd = openat(AT_FDCWD, ".", O_TMPFILE | O_WRONLY, 0600); + fd = open(settings->work_dir, O_TMPFILE | O_WRONLY, 0600); if (fd < 0) { return proxy_log(LOG_ERR, errno, "openat() failed"); } @@ -587,16 +587,17 @@ static int32_t proxy_config_destination_write(int32_t fd, void *data, return size; } -static int32_t proxy_config_destination_commit(int32_t fd, const char *name) +static int32_t proxy_config_destination_commit(proxy_settings_t *settings, + int32_t fd, const char *path) { - char path[32]; + char fd_path[32]; int32_t len; if (fsync(fd) < 0) { return proxy_log(LOG_ERR, errno, "fsync() failed"); } - if (linkat(fd, "", AT_FDCWD, name, AT_EMPTY_PATH) < 0) { + if (linkat(fd, "", AT_FDCWD, path, AT_EMPTY_PATH) < 0) { if (errno == EEXIST) { return 0; } @@ -606,12 +607,12 @@ static int32_t proxy_config_destination_commit(int32_t fd, const char *name) * filesystem. */ } - len = proxy_snprintf(path, sizeof(path), "/proc/self/fd/%d", fd); + len = proxy_snprintf(fd_path, sizeof(fd_path), "/proc/self/fd/%d", fd); if (len < 0) { return len; } - if (linkat(AT_FDCWD, path, AT_FDCWD, name, AT_SYMLINK_FOLLOW) < 0) { + if (linkat(AT_FDCWD, fd_path, AT_FDCWD, path, AT_SYMLINK_FOLLOW) < 0) { if (errno != EEXIST) { return proxy_log(LOG_ERR, errno, "linkat() failed"); } @@ -646,7 +647,8 @@ static int32_t proxy_config_transfer(void **ptr, void *data, int32_t idx) /* Copies and checksums a given configuration to a file and makes sure that it * has not been modified. */ -static int32_t proxy_config_prepare(const char *config, char *path, +static int32_t proxy_config_prepare(proxy_settings_t *settings, + const char *config, char *path, int32_t size) { char hash[65]; @@ -667,7 +669,7 @@ static int32_t proxy_config_prepare(const char *config, char *path, goto done_mem; } - cfg.dst = proxy_config_destination_prepare(); + cfg.dst = proxy_config_destination_prepare(settings); if (cfg.dst < 0) { err = cfg.dst; goto done_src; @@ -683,12 +685,13 @@ static int32_t proxy_config_prepare(const char *config, char *path, goto done_dst; } - err = proxy_snprintf(path, size, "ceph-%s.conf", hash); + err = proxy_snprintf(path, size, "%s/ceph-%s.conf", settings->work_dir, + hash); if (err < 0) { goto done_dst; } - err = proxy_config_destination_commit(cfg.dst, path); + err = proxy_config_destination_commit(settings, cfg.dst, path); done_dst: proxy_config_destination_close(cfg.dst); @@ -826,7 +829,7 @@ static int32_t proxy_instance_release(proxy_instance_t *instance) static int32_t proxy_instance_config(proxy_instance_t *instance, const char *config) { - char path[128], *ppath; + char path[strlen(instance->settings->work_dir) + 128], *ppath; int32_t err; if (instance->mounted) { @@ -836,7 +839,8 @@ static int32_t proxy_instance_config(proxy_instance_t *instance, ppath = NULL; if (config != NULL) { - err = proxy_config_prepare(config, path, sizeof(path)); + err = proxy_config_prepare(instance->settings, config, path, + sizeof(path)); if (err < 0) { return err; }