diff options
author | Lennart Poettering <lennart@poettering.net> | 2013-11-30 03:53:42 +0100 |
---|---|---|
committer | Lennart Poettering <lennart@poettering.net> | 2013-11-30 03:53:42 +0100 |
commit | e3dd987cfc395848256fc6eae637ed0eaf5f1635 (patch) | |
tree | 5e265370b750c3f552f55f8a3417df8658a263b6 /src/libsystemd-bus | |
parent | 32f464809e8e487739fde53a2feb0afba70c8db7 (diff) |
core: allocate a kdbus bus for each systemd instance, if we can
Diffstat (limited to 'src/libsystemd-bus')
-rw-r--r-- | src/libsystemd-bus/bus-kernel.c | 177 | ||||
-rw-r--r-- | src/libsystemd-bus/kdbus.h | 5 | ||||
-rw-r--r-- | src/libsystemd-bus/sd-bus.c | 40 |
3 files changed, 109 insertions, 113 deletions
diff --git a/src/libsystemd-bus/bus-kernel.c b/src/libsystemd-bus/bus-kernel.c index 69143434b3..1cab2544ec 100644 --- a/src/libsystemd-bus/bus-kernel.c +++ b/src/libsystemd-bus/bus-kernel.c @@ -605,39 +605,6 @@ static int bus_kernel_translate_message(sd_bus *bus, struct kdbus_msg *k) { return translate[found->type - _KDBUS_ITEM_KERNEL_BASE](bus, k, found); } -int kdbus_translate_attach_flags(uint64_t mask, uint64_t *kdbus_mask) { - - uint64_t m = 0; - - SET_FLAG(m, KDBUS_ATTACH_CREDS, - !!(mask & (SD_BUS_CREDS_UID|SD_BUS_CREDS_GID|SD_BUS_CREDS_PID|SD_BUS_CREDS_PID_STARTTIME|SD_BUS_CREDS_TID))); - - SET_FLAG(m, KDBUS_ATTACH_COMM, - !!(mask & (SD_BUS_CREDS_COMM|SD_BUS_CREDS_TID_COMM))); - - SET_FLAG(m, KDBUS_ATTACH_EXE, - !!(mask & SD_BUS_CREDS_EXE)); - - SET_FLAG(m, KDBUS_ATTACH_CMDLINE, - !!(mask & SD_BUS_CREDS_CMDLINE)); - - SET_FLAG(m, KDBUS_ATTACH_CGROUP, - !!(mask & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_OWNER_UID))); - - SET_FLAG(m, KDBUS_ATTACH_CAPS, - !!(mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS))); - - SET_FLAG(m, KDBUS_ATTACH_SECLABEL, - !!(mask & SD_BUS_CREDS_SELINUX_CONTEXT)); - - SET_FLAG(m, KDBUS_ATTACH_AUDIT, - !!(mask & (SD_BUS_CREDS_AUDIT_SESSION_ID|SD_BUS_CREDS_AUDIT_LOGIN_UID))); - - *kdbus_mask = m; - - return 0; -} - static int bus_kernel_make_message(sd_bus *bus, struct kdbus_msg *k) { sd_bus_message *m = NULL; struct kdbus_item *d; @@ -923,52 +890,6 @@ int bus_kernel_read_message(sd_bus *bus) { return r < 0 ? r : 1; } -int bus_kernel_create(const char *name, char **s) { - struct kdbus_cmd_bus_make *make; - struct kdbus_item *n; - size_t l; - int fd; - char *p; - - assert(name); - assert(s); - - fd = open("/dev/kdbus/control", O_RDWR|O_NOCTTY|O_CLOEXEC); - if (fd < 0) - return -errno; - - l = strlen(name); - make = alloca0(offsetof(struct kdbus_cmd_bus_make, items) + - KDBUS_PART_HEADER_SIZE + sizeof(uint64_t) + - KDBUS_PART_HEADER_SIZE + DECIMAL_STR_MAX(uid_t) + 1 + l + 1); - - n = make->items; - n->type = KDBUS_MAKE_NAME; - sprintf(n->str, "%lu-%s", (unsigned long) getuid(), name); - n->size = KDBUS_PART_HEADER_SIZE + strlen(n->str) + 1; - - make->size = offsetof(struct kdbus_cmd_bus_make, items) + n->size; - make->flags = KDBUS_MAKE_POLICY_OPEN; - make->bus_flags = 0; - make->bloom_size = BLOOM_SIZE; - assert_cc(BLOOM_SIZE % 8 == 0); - - p = strjoin("/dev/kdbus/", n->str, "/bus", NULL); - if (!p) - return -ENOMEM; - - if (ioctl(fd, KDBUS_CMD_BUS_MAKE, make) < 0) { - close_nointr_nofail(fd); - free(p); - return -errno; - } - - if (s) - *s = p; - - return fd; -} - int bus_kernel_pop_memfd(sd_bus *bus, void **address, size_t *size) { struct memfd_cache *c; int fd; @@ -1061,20 +982,100 @@ void bus_kernel_flush_memfd(sd_bus *b) { close_and_munmap(b->memfd_cache[i].fd, b->memfd_cache[i].address, b->memfd_cache[i].size); } -int kdbus_translate_request_name_flags(uint64_t sd_bus_flags, uint64_t *kdbus_flags) { +int kdbus_translate_request_name_flags(uint64_t flags, uint64_t *kdbus_flags) { + uint64_t f = 0; - assert_return(kdbus_flags != NULL, -EINVAL); + assert(kdbus_flags); - *kdbus_flags = 0; + if (flags & SD_BUS_NAME_ALLOW_REPLACEMENT) + f |= KDBUS_NAME_ALLOW_REPLACEMENT; - if (sd_bus_flags & SD_BUS_NAME_ALLOW_REPLACEMENT) - *kdbus_flags |= KDBUS_NAME_ALLOW_REPLACEMENT; + if (flags & SD_BUS_NAME_REPLACE_EXISTING) + f |= KDBUS_NAME_REPLACE_EXISTING; - if (sd_bus_flags & SD_BUS_NAME_REPLACE_EXISTING) - *kdbus_flags |= KDBUS_NAME_REPLACE_EXISTING; + if (!(flags & SD_BUS_NAME_DO_NOT_QUEUE)) + f |= KDBUS_NAME_QUEUE; - if (!(sd_bus_flags & SD_BUS_NAME_DO_NOT_QUEUE)) - *kdbus_flags |= KDBUS_NAME_QUEUE; + *kdbus_flags = f; + return 0; +} + +int kdbus_translate_attach_flags(uint64_t mask, uint64_t *kdbus_mask) { + uint64_t m = 0; + + assert(kdbus_mask); + + if (mask & (SD_BUS_CREDS_UID|SD_BUS_CREDS_GID|SD_BUS_CREDS_PID|SD_BUS_CREDS_PID_STARTTIME|SD_BUS_CREDS_TID)) + m |= KDBUS_ATTACH_CREDS; + + if (mask & (SD_BUS_CREDS_COMM|SD_BUS_CREDS_TID_COMM)) + m |= KDBUS_ATTACH_COMM; + + if (mask & SD_BUS_CREDS_EXE) + m |= KDBUS_ATTACH_EXE; + + if (mask & SD_BUS_CREDS_CMDLINE) + m |= KDBUS_ATTACH_CMDLINE; + + if (mask & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_OWNER_UID)) + m |= KDBUS_ATTACH_CGROUP; + + if (mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS)) + m |= KDBUS_ATTACH_CAPS; + + if (mask & SD_BUS_CREDS_SELINUX_CONTEXT) + m |= KDBUS_ATTACH_SECLABEL; + if (mask & (SD_BUS_CREDS_AUDIT_SESSION_ID|SD_BUS_CREDS_AUDIT_LOGIN_UID)) + m |= KDBUS_ATTACH_AUDIT; + + *kdbus_mask = m; return 0; } + +int bus_kernel_create(const char *name, char **s) { + struct kdbus_cmd_bus_make *make; + struct kdbus_item *n; + int fd; + + assert(name); + assert(s); + + fd = open("/dev/kdbus/control", O_RDWR|O_NOCTTY|O_CLOEXEC); + if (fd < 0) + return -errno; + + make = alloca0(ALIGN8(offsetof(struct kdbus_cmd_bus_make, items) + + offsetof(struct kdbus_item, str) + + DECIMAL_STR_MAX(uid_t) + 1 + strlen(name) + 1)); + + n = make->items; + sprintf(n->str, "%lu-%s", (unsigned long) getuid(), name); + n->size = offsetof(struct kdbus_item, str) + strlen(n->str) + 1; + n->type = KDBUS_MAKE_NAME; + + make->size = ALIGN8(offsetof(struct kdbus_cmd_bus_make, items) + n->size); + make->flags = KDBUS_MAKE_POLICY_OPEN; + make->bus_flags = 0; + make->bloom_size = BLOOM_SIZE; + assert_cc(BLOOM_SIZE % 8 == 0); + + if (ioctl(fd, KDBUS_CMD_BUS_MAKE, make) < 0) { + close_nointr_nofail(fd); + return -errno; + } + + if (s) { + char *p; + + p = strjoin("/dev/kdbus/", n->str, "/bus", NULL); + if (!p) { + close_nointr_nofail(fd); + return -ENOMEM; + } + + *s = p; + } + + return fd; +} diff --git a/src/libsystemd-bus/kdbus.h b/src/libsystemd-bus/kdbus.h index c9377ea277..bfd299bd26 100644 --- a/src/libsystemd-bus/kdbus.h +++ b/src/libsystemd-bus/kdbus.h @@ -297,11 +297,6 @@ enum { enum { _KDBUS_MAKE_NULL, KDBUS_MAKE_NAME, - KDBUS_MAKE_CRED, /* allow translator services which connect - * to the bus on behalf of somebody else, - * allow specifying the credentials of the - * client to connect on behalf on. Needs - * privileges */ }; struct kdbus_cmd_bus_make { diff --git a/src/libsystemd-bus/sd-bus.c b/src/libsystemd-bus/sd-bus.c index 8ffc9a9eff..0d5deb6c6d 100644 --- a/src/libsystemd-bus/sd-bus.c +++ b/src/libsystemd-bus/sd-bus.c @@ -986,15 +986,13 @@ _public_ int sd_bus_open_system(sd_bus **ret) { return r; e = secure_getenv("DBUS_SYSTEM_BUS_ADDRESS"); - if (e) { + if (e) r = sd_bus_set_address(b, e); - if (r < 0) - goto fail; - } else { - b->sockaddr.un.sun_family = AF_UNIX; - strncpy(b->sockaddr.un.sun_path, "/run/dbus/system_bus_socket", sizeof(b->sockaddr.un.sun_path)); - b->sockaddr_size = offsetof(struct sockaddr_un, sun_path) + sizeof("/run/dbus/system_bus_socket") - 1; - } + else + r = sd_bus_set_address(b, "kernel:path=/dev/kdbus/0-system/bus;unix:path=/run/dbus/system_bus_socket"); + + if (r < 0) + goto fail; b->bus_client = true; @@ -1013,7 +1011,6 @@ fail: _public_ int sd_bus_open_user(sd_bus **ret) { const char *e; sd_bus *b; - size_t l; int r; assert_return(ret, -EINVAL); @@ -1029,20 +1026,23 @@ _public_ int sd_bus_open_user(sd_bus **ret) { goto fail; } else { e = secure_getenv("XDG_RUNTIME_DIR"); - if (!e) { - r = -ENOENT; - goto fail; - } + if (e) { + _cleanup_free_ char *ee = NULL; + + ee = bus_address_escape(e); + if (!ee) { + r = -ENOENT; + goto fail; + } - l = strlen(e); - if (l + 4 > sizeof(b->sockaddr.un.sun_path)) { - r = -E2BIG; + asprintf(&b->address, "kernel:path=/dev/kdbus/%lu-user/bus;unix:path=%s/bus", (unsigned long) getuid(), ee); + } else + asprintf(&b->address, "kernel:path=/dev/kdbus/%lu-user/bus", (unsigned long) getuid()); + + if (!b->address) { + r = -ENOMEM; goto fail; } - - b->sockaddr.un.sun_family = AF_UNIX; - memcpy(mempcpy(b->sockaddr.un.sun_path, e, l), "/bus", 4); - b->sockaddr_size = offsetof(struct sockaddr_un, sun_path) + l + 4; } b->bus_client = true; |