SD_VARLINK_CONNECT_EXEC(3)
β¨ sd_varlink_connect_address β bestie, let's make a Varlink connection π
okay so this is the sd_varlink_connect_address(3) manual page, and it's basically a whole friend group of functions that all do the same vibe: they make a new client-side Varlink connection object and hook it up to a Varlink service. the only thing that's different between them is how you tell them which service you wanna talk to. iconic, honestly. π«Ά
πΈ NAME πΈ
sd_varlink_connect_address, sd_varlink_connect_exec, sd_varlink_connect_url, sd_varlink_connect_fd, sd_varlink_connect_fd_pair β create a Varlink connection object and connect it to a service. literally the whole point. no cap. β¨
π SYNOPSIS π
#include <systemd/sd-varlink.h>
struct ucred; /* defined in <sys/socket.h> */
int sd_varlink_connect_address(sd_varlink **ret, const char *address);
int sd_varlink_connect_exec(sd_varlink **ret, const char *command,
char **argv);
int sd_varlink_connect_url(sd_varlink **ret, const char *url);
int sd_varlink_connect_fd(sd_varlink **ret, int fd);
int sd_varlink_connect_fd_pair(sd_varlink **ret, int input_fd,
int output_fd,
const struct ucred *override_ucred);
π DESCRIPTION π
so these five functions all allocate you a shiny new client-side Varlink connection object and connect it to a Varlink service. the only difference is how you specify which service you're talking to. when it works, you get a reference to the fresh new connection object back in ret. that reference is yours, bestie β you own it, and you gotta release it eventually with sd_varlink_unref(3), sd_varlink_close_unref(3), or sd_varlink_flush_close_unref(3). don't just ghost it. π
all five of them return immediately. none of them block waiting for the connection to be fully established. for socket-based connections, the actual connect() might still be in progress when the function hands back control (more on that below) β but the connection object handles the completion transparently, so don't stress. π§
the connection object you get back is not attached to any event loop. there are three ways to drive it, and you get to pick your main character moment:
- attach it to an
sd-event(3)loop withsd_varlink_attach_event(3); - run its I/O manually via
sd_varlink_process(3)andsd_varlink_wait(3); - or just vibe and issue blocking method calls.
and like, it is perfectly fine to follow any of these connection functions directly with a synchronous, blocking call like sd_varlink_call(3) β that call internally drives the connection (yes, including completing a still-pending connect()) and returns once the reply has been received. in that case you need zero explicit event loop integration and zero manual processing. slay. π₯
the five besties, one by one
sd_varlink_connect_address() β connects to an AF_UNIX stream socket whose address is given as a string in address. the address must begin either with "/" (for a socket in the file system) or with "@" (for a socket in the abstract namespace, where the rest of the string is the abstract name). it has to be at least two characters long. no other forms are accepted β and yes, relative paths get refused, sorry. abstract namespace names that embed NUL bytes can't be expressed through this interface. but here's the cute part: if a file system socket path is too long to fit into a sockaddr_un structure, the connection is established transparently via an O_PATH indirection, so overlong paths still work. π
sd_varlink_connect_exec() β forks off a child process and speaks the Varlink protocol with it over a connected AF_UNIX SOCK_STREAM socket pair. command is the program to execute, and it's looked up in $PATH in the usual way (i.e. via execvp(3)). argv is the argument vector (a NULL-terminated string array) passed to the child as its argv[]; if it's NULL or empty, an argument vector consisting of just command is synthesized. the connected socket is handed to the child as file descriptor 3 using the sd_listen_fds(3) protocol, meaning the child gets invoked with $LISTEN_FDS set to "1", $LISTEN_FDNAMES set to "varlink", and the appropriate $LISTEN_PID (plus, where available, $LISTEN_PIDFDID). the command and argv strings get copied into the connection object, so the caller may free or modify them once the function returns. π
sd_varlink_connect_url() β the higher-level glow-up. it parses a service address string with a leading scheme and dispatches to the appropriate transport. despite the name, these strings are not Internet URLs in the sense of the relevant RFCs (the name is just... a name, okay?). here are the schemes it understands natively:
"unix:"PATHβ connects to anAF_UNIXsocket, equivalent to passing PATH tosd_varlink_connect_address(). PATH must either be an absolute, normalized file system path, or begin with"@"for an abstract namespace socket (for which no path normalization checks are applied)."exec:"PATHβ forks off the executable at PATH, equivalent to passing it tosd_varlink_connect_exec()with no extra arguments. PATH must be an absolute, normalized path."ssh:"HOST":"PATH,"ssh-unix:"HOST":"PATHβ connects to anAF_UNIXsocket at the absolute, normalized path PATH on the remote SSH host HOST. this relies on OpenSSH 9.4 or newer on the server side. abstract namespace sockets are not supported for this transport."ssh:"and"ssh-unix:"are synonyms, iykyk."ssh-exec:"HOST":"COMMANDβ invokes COMMAND (a command line, split on whitespace with shell-style quoting and unescaping) on the remote SSH host HOST and speaks the Varlink protocol over its standard input and output.
if the scheme is none of the above but is otherwise a syntactically valid URL scheme, sd_varlink_connect_url() goes looking for a bridge helper binary of that name in the directory configured via $SYSTEMD_VARLINK_BRIDGES_DIR (see below π). if it finds it and it's executable, it's invoked like an "exec:" transport, with the complete, unmodified URL passed as its sole command line argument. this is how you plug in extra transports out of tree. cute, right? π
for the natively supported schemes, URL parameterization using ";", "?" or "#" is rejected (these are reserved for possible future use). a "vsock:" scheme is not currently supported. periodt.
sd_varlink_connect_fd() β takes an already existing, already connected file descriptor fd and turns it into a Varlink connection. the descriptor is used for both reading and writing. it may refer to a connected stream socket, but also to a pipe or any other bidirectional file descriptor. flexible queen. π
sd_varlink_connect_fd_pair() β like sd_varlink_connect_fd(), but it accepts a separate input_fd (used for reading from the peer) and output_fd (used for writing to the peer). super useful when the two directions are backed by different descriptors β like a pair of pipes, or the standard output and standard input of a co-process. the two descriptors may also be identical, which is exactly what sd_varlink_connect_fd() does internally. if override_ucred is non-NULL, the peer credentials reported for the connection (as returned e.g. by sd_varlink_get_peer_uid(3)) are taken from the supplied ucred structure instead of being queried from the socket via SO_PEERCRED. this is primarily useful when the descriptors are not sockets (and hence carry no kernel-supplied peer credentials), or when the credentials need to be overridden for other reasons. if override_ucred is NULL, peer credentials are determined from the socket as usual. π¦
ownership tea β
sd_varlink_connect_fd() and sd_varlink_connect_fd_pair() take over ownership of the descriptors passed to them: the descriptors get closed automatically when the connection object is freed, and the caller must not close them itself. on failure, ownership remains with the caller. so like... hands off, bestie. π
child process vibes πΆ
the connection objects created by sd_varlink_connect_exec(), and by the "exec:", "ssh:"/"ssh-unix:", "ssh-exec:" and bridge-helper paths of sd_varlink_connect_url(), are bound to the lifetime of the spawned child process. when such a connection object is freed, the associated child process is sent SIGTERM and reaped. the child is also configured to receive SIGTERM if the calling process dies. no zombie situations here, we don't do that. π
π RETURN VALUE π
on success, these functions return a non-negative integer and store a pointer to the new connection object in ret. on failure, they return a negative errno-style error code and leave ret unchanged. β¨
π₯Ί Errors π₯Ί
the errors you might get back mean the following, so let's decode them:
-EINVALβ a required argument isNULL, or the supplied address, command, or URL is malformed. this includes addresses that don't begin with"/"or"@", abstract namespace names that don't fit into asockaddr_unstructure, and β forsd_varlink_connect_url()β file system paths that are not absolute or not normalized.-EBADFβ forsd_varlink_connect_fd()andsd_varlink_connect_fd_pair(): a supplied file descriptor is negative.-EPROTONOSUPPORTβ forsd_varlink_connect_url(): the URL contains no":"separator, uses an unsupported scheme for which no bridge helper binary is available, or makes use of the reserved";","?"or"#"URL parameterization characters with a natively supported scheme.-ENOMEMβ memory allocation failed. π
plus, these functions may propagate any error returned by the underlying system calls they use, such as socket(2), connect(2), fork(2), pipe(2) and the various execution helpers.
β NOTES β
the functions described here are available as a shared library, which you can compile against and link to with the libsystemd pkg-config(1) file. π
the code described here uses getenv(3), which is declared to be not multi-thread-safe. this means code calling the functions described here must not call setenv(3) from a parallel thread. it's recommended to only call setenv() from an early phase of the program, when no other threads have been started yet. don't be messy about it. π
πΈ ENVIRONMENT πΈ
$SYSTEMD_SSHβ used by the"ssh:"/"ssh-unix:"and"ssh-exec:"transports ofsd_varlink_connect_url()to override thesshbinary to invoke. may be a plain file name (looked up in$PATH) or an absolute path.
Added in version 257.
$SYSTEMD_VARLINK_BRIDGES_DIRβ overrides the directory in whichsd_varlink_connect_url()looks up bridge helper binaries for non-native URL schemes. defaults to/usr/lib/systemd/varlink-bridges/.
Added in version 257.
π FILES π
/usr/lib/systemd/varlink-bridges/β the default directory searched for bridge helper binaries whensd_varlink_connect_url()encounters a URL with a scheme that isn't natively supported. seesd-varlink(3)for details.
π HISTORY π
sd_varlink_connect_address(), sd_varlink_connect_exec(), sd_varlink_connect_url(), sd_varlink_connect_fd() and sd_varlink_connect_fd_pair() were added in version 257. so they're not ancient, they're just β¨establishedβ¨.
π SEE ALSO π
systemd(1), sd-varlink(3), sd_varlink_attach_event(3), sd_varlink_call(3), sd_varlink_send(3), sd_varlink_is_connected(3), sd_listen_fds(3), varlinkctl(1)
okay that's the whole page, bestie, you ate it up fr fr. this was systemd 262.1 energy, and we're signing off β stay connected, keep your refs released, and remember: the descriptors belong to the connection object now. π«Άβ¨π
π¦ where this page comes from
- arch rolling: systemd-libs 262.1-1 Β· LGPL-2.1-or-later AND CC0-1.0 AND GPL-2.0-or-later WITH Linux-syscall-note
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms