From 6d4778f14f19a1787dce13641b4c6d84d9b715a6 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Wed, 20 Nov 2024 12:57:33 +0100 Subject: [PATCH 1/2] sd-varlink: add flag for sd_varlink_server for creating connections with fd passing enabled Let's add a simple flag that enables fd passing for all connections of a server. It's much easier to use this than to install a connect handler which manually enables this for each connection. --- src/libsystemd/sd-varlink/sd-varlink.c | 11 ++++++++++- src/systemd/sd-varlink.h | 12 +++++++----- 2 files changed, 17 insertions(+), 6 deletions(-) diff --git a/src/libsystemd/sd-varlink/sd-varlink.c b/src/libsystemd/sd-varlink/sd-varlink.c index 46dd3a62df..9e8f2a66f8 100644 --- a/src/libsystemd/sd-varlink/sd-varlink.c +++ b/src/libsystemd/sd-varlink/sd-varlink.c @@ -3259,7 +3259,13 @@ _public_ int sd_varlink_server_new(sd_varlink_server **ret, sd_varlink_server_fl int r; assert_return(ret, -EINVAL); - assert_return((flags & ~(SD_VARLINK_SERVER_ROOT_ONLY|SD_VARLINK_SERVER_MYSELF_ONLY|SD_VARLINK_SERVER_ACCOUNT_UID|SD_VARLINK_SERVER_INHERIT_USERDATA|SD_VARLINK_SERVER_INPUT_SENSITIVE)) == 0, -EINVAL); + assert_return((flags & ~(SD_VARLINK_SERVER_ROOT_ONLY| + SD_VARLINK_SERVER_MYSELF_ONLY| + SD_VARLINK_SERVER_ACCOUNT_UID| + SD_VARLINK_SERVER_INHERIT_USERDATA| + SD_VARLINK_SERVER_INPUT_SENSITIVE| + SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT| + SD_VARLINK_SERVER_ALLOW_FD_PASSING_OUTPUT)) == 0, -EINVAL); s = new(sd_varlink_server, 1); if (!s) @@ -3469,6 +3475,9 @@ _public_ int sd_varlink_server_add_connection_pair( if (asprintf(&desc, "%s-%i-%i", varlink_server_description(server), input_fd, output_fd) >= 0) v->description = TAKE_PTR(desc); + (void) sd_varlink_set_allow_fd_passing_input(v, FLAGS_SET(server->flags, SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT)); + (void) sd_varlink_set_allow_fd_passing_output(v, FLAGS_SET(server->flags, SD_VARLINK_SERVER_ALLOW_FD_PASSING_OUTPUT)); + /* Link up the server and the connection, and take reference in both directions. Note that the * reference on the connection is left dangling. It will be dropped when the connection is closed, * which happens in varlink_close(), including in the event loop quit callback. */ diff --git a/src/systemd/sd-varlink.h b/src/systemd/sd-varlink.h index 6329c4ee6a..03509163d3 100644 --- a/src/systemd/sd-varlink.h +++ b/src/systemd/sd-varlink.h @@ -65,11 +65,13 @@ __extension__ typedef enum _SD_ENUM_TYPE_S64(sd_varlink_method_flags_t) { } sd_varlink_method_flags_t; __extension__ typedef enum _SD_ENUM_TYPE_S64(sd_varlink_server_flags_t) { - SD_VARLINK_SERVER_ROOT_ONLY = 1 << 0, /* Only accessible by root */ - SD_VARLINK_SERVER_MYSELF_ONLY = 1 << 1, /* Only accessible by our own UID */ - SD_VARLINK_SERVER_ACCOUNT_UID = 1 << 2, /* Do per user accounting */ - SD_VARLINK_SERVER_INHERIT_USERDATA = 1 << 3, /* Initialize Varlink connection userdata from sd_varlink_server userdata */ - SD_VARLINK_SERVER_INPUT_SENSITIVE = 1 << 4, /* Automatically mark all connection input as sensitive */ + SD_VARLINK_SERVER_ROOT_ONLY = 1 << 0, /* Only accessible by root */ + SD_VARLINK_SERVER_MYSELF_ONLY = 1 << 1, /* Only accessible by our own UID */ + SD_VARLINK_SERVER_ACCOUNT_UID = 1 << 2, /* Do per user accounting */ + SD_VARLINK_SERVER_INHERIT_USERDATA = 1 << 3, /* Initialize Varlink connection userdata from sd_varlink_server userdata */ + SD_VARLINK_SERVER_INPUT_SENSITIVE = 1 << 4, /* Automatically mark all connection input as sensitive */ + SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT = 1 << 5, /* Allow receiving fds over all connections */ + SD_VARLINK_SERVER_ALLOW_FD_PASSING_OUTPUT = 1 << 6, /* Allow sending fds over all connections */ _SD_ENUM_FORCE_S64(SD_VARLINK_SERVER) } sd_varlink_server_flags_t; From 6f8487309669e2d169cafeb1537ddedb0f14b190 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Mon, 6 Jan 2025 09:33:50 +0100 Subject: [PATCH 2/2] mountfsd,networkd,nsresourced: port over to new fd passing varlink server flags --- src/mountfsd/mountwork.c | 13 ++++--------- src/network/networkd-manager-varlink.c | 22 +++++----------------- src/nsresourced/nsresourcework.c | 14 +++++--------- 3 files changed, 14 insertions(+), 35 deletions(-) diff --git a/src/mountfsd/mountwork.c b/src/mountfsd/mountwork.c index af46287fcf..6add73894b 100644 --- a/src/mountfsd/mountwork.c +++ b/src/mountfsd/mountwork.c @@ -553,14 +553,6 @@ static int process_connection(sd_varlink_server *server, int _fd) { TAKE_FD(fd); vl = sd_varlink_ref(vl); - r = sd_varlink_set_allow_fd_passing_input(vl, true); - if (r < 0) - return log_error_errno(r, "Failed to enable fd passing for read: %m"); - - r = sd_varlink_set_allow_fd_passing_output(vl, true); - if (r < 0) - return log_error_errno(r, "Failed to enable fd passing for write: %m"); - r = sd_event_loop(event); if (r < 0) return log_error_errno(r, "Failed to run event loop: %m"); @@ -596,7 +588,10 @@ static int run(int argc, char *argv[]) { if (r < 0) return log_error_errno(r, "Failed to turn off non-blocking mode for listening socket: %m"); - r = varlink_server_new(&server, SD_VARLINK_SERVER_INHERIT_USERDATA, NULL); + r = varlink_server_new(&server, + SD_VARLINK_SERVER_INHERIT_USERDATA| + SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT|SD_VARLINK_SERVER_ALLOW_FD_PASSING_OUTPUT, + NULL); if (r < 0) return log_error_errno(r, "Failed to allocate server: %m"); diff --git a/src/network/networkd-manager-varlink.c b/src/network/networkd-manager-varlink.c index 546dae0739..b2a196c5fc 100644 --- a/src/network/networkd-manager-varlink.c +++ b/src/network/networkd-manager-varlink.c @@ -250,18 +250,6 @@ static int vl_method_set_persistent_storage(sd_varlink *vlink, sd_json_variant * return sd_varlink_reply(vlink, NULL); } -static int on_connect(sd_varlink_server *s, sd_varlink *vlink, void *userdata) { - int r; - - assert(vlink); - - r = sd_varlink_set_allow_fd_passing_input(vlink, true); - if (r < 0) - return log_warning_errno(r, "Failed to allow receiving file descriptor through varlink: %m"); - - return 0; -} - int manager_connect_varlink(Manager *m) { _cleanup_(sd_varlink_server_unrefp) sd_varlink_server *s = NULL; int r; @@ -271,7 +259,11 @@ int manager_connect_varlink(Manager *m) { if (m->varlink_server) return 0; - r = varlink_server_new(&s, SD_VARLINK_SERVER_ACCOUNT_UID|SD_VARLINK_SERVER_INHERIT_USERDATA, m); + r = varlink_server_new( + &s, + SD_VARLINK_SERVER_ACCOUNT_UID|SD_VARLINK_SERVER_INHERIT_USERDATA| + SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT, + m); if (r < 0) return log_error_errno(r, "Failed to allocate varlink server object: %m"); @@ -298,10 +290,6 @@ int manager_connect_varlink(Manager *m) { if (r < 0) return log_error_errno(r, "Failed to attach varlink connection to event loop: %m"); - r = sd_varlink_server_bind_connect(s, on_connect); - if (r < 0) - return log_error_errno(r, "Failed to set on-connect callback for varlink: %m"); - m->varlink_server = TAKE_PTR(s); return 0; } diff --git a/src/nsresourced/nsresourcework.c b/src/nsresourced/nsresourcework.c index 21fc2d9088..b8db07fcd3 100644 --- a/src/nsresourced/nsresourcework.c +++ b/src/nsresourced/nsresourcework.c @@ -1637,14 +1637,6 @@ static int process_connection(sd_varlink_server *server, int _fd) { TAKE_FD(fd); vl = sd_varlink_ref(vl); - r = sd_varlink_set_allow_fd_passing_input(vl, true); - if (r < 0) - return log_error_errno(r, "Failed to enable fd passing for read: %m"); - - r = sd_varlink_set_allow_fd_passing_output(vl, true); - if (r < 0) - return log_error_errno(r, "Failed to enable fd passing for write: %m"); - for (;;) { r = sd_varlink_process(vl); if (r == -ENOTCONN) { @@ -1690,7 +1682,11 @@ static int run(int argc, char *argv[]) { if (r < 0) return log_error_errno(r, "Failed to turn off non-blocking mode for listening socket: %m"); - r = varlink_server_new(&server, SD_VARLINK_SERVER_INHERIT_USERDATA, NULL); + r = varlink_server_new( + &server, + SD_VARLINK_SERVER_INHERIT_USERDATA| + SD_VARLINK_SERVER_ALLOW_FD_PASSING_INPUT|SD_VARLINK_SERVER_ALLOW_FD_PASSING_OUTPUT, + NULL); if (r < 0) return log_error_errno(r, "Failed to allocate varlink server: %m");