1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2013 Lennart Poettering
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
22 #ifdef HAVE_VALGRIND_MEMCHECK_H
23 #include <valgrind/memcheck.h>
29 #include <sys/prctl.h>
31 /* When we include libgen.h because we need dirname() we immediately
32 * undefine basename() since libgen.h defines it as a macro to the POSIX
33 * version which is really broken. We prefer GNU basename(). */
39 #include "memfd-util.h"
40 #include "capability.h"
42 #include "formats-util.h"
44 #include "bus-internal.h"
45 #include "bus-message.h"
46 #include "bus-kernel.h"
47 #include "bus-bloom.h"
49 #include "bus-label.h"
51 #define UNIQUE_NAME_MAX (3+DECIMAL_STR_MAX(uint64_t))
53 int bus_kernel_parse_unique_name(const char *s, uint64_t *id) {
59 if (!startswith(s, ":1."))
62 r = safe_atou64(s + 3, id);
69 static void append_payload_vec(struct kdbus_item **d, const void *p, size_t sz) {
75 /* Note that p can be NULL, which encodes a region full of
76 * zeroes, which is useful to optimize certain padding
79 (*d)->size = offsetof(struct kdbus_item, vec) + sizeof(struct kdbus_vec);
80 (*d)->type = KDBUS_ITEM_PAYLOAD_VEC;
81 (*d)->vec.address = PTR_TO_UINT64(p);
84 *d = (struct kdbus_item *) ((uint8_t*) *d + (*d)->size);
87 static void append_payload_memfd(struct kdbus_item **d, int memfd, size_t start, size_t sz) {
93 (*d)->size = offsetof(struct kdbus_item, memfd) + sizeof(struct kdbus_memfd);
94 (*d)->type = KDBUS_ITEM_PAYLOAD_MEMFD;
95 (*d)->memfd.fd = memfd;
96 (*d)->memfd.start = start;
97 (*d)->memfd.size = sz;
99 *d = (struct kdbus_item *) ((uint8_t*) *d + (*d)->size);
102 static void append_destination(struct kdbus_item **d, const char *s, size_t length) {
108 (*d)->size = offsetof(struct kdbus_item, str) + length + 1;
109 (*d)->type = KDBUS_ITEM_DST_NAME;
110 memcpy((*d)->str, s, length + 1);
112 *d = (struct kdbus_item *) ((uint8_t*) *d + (*d)->size);
115 static struct kdbus_bloom_filter *append_bloom(struct kdbus_item **d, size_t length) {
116 struct kdbus_item *i;
122 i->size = offsetof(struct kdbus_item, bloom_filter) +
123 offsetof(struct kdbus_bloom_filter, data) +
125 i->type = KDBUS_ITEM_BLOOM_FILTER;
127 *d = (struct kdbus_item *) ((uint8_t*) i + i->size);
129 return &i->bloom_filter;
132 static void append_fds(struct kdbus_item **d, const int fds[], unsigned n_fds) {
138 (*d)->size = offsetof(struct kdbus_item, fds) + sizeof(int) * n_fds;
139 (*d)->type = KDBUS_ITEM_FDS;
140 memcpy((*d)->fds, fds, sizeof(int) * n_fds);
142 *d = (struct kdbus_item *) ((uint8_t*) *d + (*d)->size);
145 static void add_bloom_arg(void *data, size_t size, unsigned n_hash, unsigned i, const char *t) {
146 char buf[sizeof("arg")-1 + 2 + sizeof("-slash-prefix")];
154 e = stpcpy(buf, "arg");
156 *(e++) = '0' + (char) i;
158 *(e++) = '0' + (char) (i / 10);
159 *(e++) = '0' + (char) (i % 10);
163 bloom_add_pair(data, size, n_hash, buf, t);
165 strcpy(e, "-dot-prefix");
166 bloom_add_prefixes(data, size, n_hash, buf, t, '.');
167 strcpy(e, "-slash-prefix");
168 bloom_add_prefixes(data, size, n_hash, buf, t, '/');
171 static int bus_message_setup_bloom(sd_bus_message *m, struct kdbus_bloom_filter *bloom) {
180 memzero(data, m->bus->bloom_size);
181 bloom->generation = 0;
183 bloom_add_pair(data, m->bus->bloom_size, m->bus->bloom_n_hash, "message-type", bus_message_type_to_string(m->header->type));
186 bloom_add_pair(data, m->bus->bloom_size, m->bus->bloom_n_hash, "interface", m->interface);
188 bloom_add_pair(data, m->bus->bloom_size, m->bus->bloom_n_hash, "member", m->member);
190 bloom_add_pair(data, m->bus->bloom_size, m->bus->bloom_n_hash, "path", m->path);
191 bloom_add_pair(data, m->bus->bloom_size, m->bus->bloom_n_hash, "path-slash-prefix", m->path);
192 bloom_add_prefixes(data, m->bus->bloom_size, m->bus->bloom_n_hash, "path-slash-prefix", m->path, '/');
195 r = sd_bus_message_rewind(m, true);
199 for (i = 0; i < 64; i++) {
200 const char *t, *contents;
203 r = sd_bus_message_peek_type(m, &type, &contents);
207 if (IN_SET(type, SD_BUS_TYPE_STRING, SD_BUS_TYPE_OBJECT_PATH, SD_BUS_TYPE_SIGNATURE)) {
209 /* The bloom filter includes simple strings of any kind */
210 r = sd_bus_message_read_basic(m, type, &t);
214 add_bloom_arg(data, m->bus->bloom_size, m->bus->bloom_n_hash, i, t);
215 } if (type == SD_BUS_TYPE_ARRAY && STR_IN_SET(contents, "s", "o", "g")) {
217 /* As well as array of simple strings of any kinds */
218 r = sd_bus_message_enter_container(m, type, contents);
222 while ((r = sd_bus_message_read_basic(m, contents[0], &t)) > 0)
223 add_bloom_arg(data, m->bus->bloom_size, m->bus->bloom_n_hash, i, t);
227 r = sd_bus_message_exit_container(m);
232 /* Stop adding to bloom filter as soon as we
233 * run into the first argument we cannot add
241 static int bus_message_setup_kmsg(sd_bus *b, sd_bus_message *m) {
242 struct bus_body_part *part;
243 struct kdbus_item *d;
244 const char *destination;
255 /* We put this together only once, if this message is reused
256 * we reuse the earlier-built version */
260 destination = m->destination ?: m->destination_ptr;
263 r = bus_kernel_parse_unique_name(destination, &unique);
271 sz = offsetof(struct kdbus_msg, items);
273 /* Add in fixed header, fields header and payload */
274 sz += (1 + m->n_body_parts) * ALIGN8(offsetof(struct kdbus_item, vec) +
275 MAX(sizeof(struct kdbus_vec),
276 sizeof(struct kdbus_memfd)));
278 /* Add space for bloom filter */
279 sz += ALIGN8(offsetof(struct kdbus_item, bloom_filter) +
280 offsetof(struct kdbus_bloom_filter, data) +
283 /* Add in well-known destination header */
285 dl = strlen(destination);
286 sz += ALIGN8(offsetof(struct kdbus_item, str) + dl + 1);
289 /* Add space for unix fds */
291 sz += ALIGN8(offsetof(struct kdbus_item, fds) + sizeof(int)*m->n_fds);
293 m->kdbus = memalign(8, sz);
299 m->free_kdbus = true;
300 memzero(m->kdbus, sz);
303 ((m->header->flags & BUS_MESSAGE_NO_REPLY_EXPECTED) ? 0 : KDBUS_MSG_EXPECT_REPLY) |
304 ((m->header->flags & BUS_MESSAGE_NO_AUTO_START) ? KDBUS_MSG_NO_AUTO_START : 0) |
305 ((m->header->type == SD_BUS_MESSAGE_SIGNAL) ? KDBUS_MSG_SIGNAL : 0);
308 /* verify_destination_id will usually be 0, which makes the kernel driver only look
309 * at the provided well-known name. Otherwise, the kernel will make sure the provided
310 * destination id matches the owner of the provided weel-known-name, and fail if they
311 * differ. Currently, this is only needed for bus-proxyd. */
312 m->kdbus->dst_id = m->verify_destination_id;
314 m->kdbus->dst_id = destination ? unique : KDBUS_DST_ID_BROADCAST;
316 m->kdbus->payload_type = KDBUS_PAYLOAD_DBUS;
317 m->kdbus->cookie = m->header->dbus2.cookie;
318 m->kdbus->priority = m->priority;
320 if (m->header->flags & BUS_MESSAGE_NO_REPLY_EXPECTED)
321 m->kdbus->cookie_reply = m->reply_cookie;
325 assert_se(clock_gettime(CLOCK_MONOTONIC_COARSE, &now) == 0);
326 m->kdbus->timeout_ns = now.tv_sec * NSEC_PER_SEC + now.tv_nsec +
327 m->timeout * NSEC_PER_USEC;
333 append_destination(&d, destination, dl);
335 append_payload_vec(&d, m->header, BUS_MESSAGE_BODY_BEGIN(m));
337 MESSAGE_FOREACH_PART(part, i, m) {
339 /* If this is padding then simply send a
340 * vector with a NULL data pointer which the
341 * kernel will just pass through. This is the
342 * most efficient way to encode zeroes */
344 append_payload_vec(&d, NULL, part->size);
348 if (part->memfd >= 0 && part->sealed && destination) {
349 /* Try to send a memfd, if the part is
350 * sealed and this is not a broadcast. Since we can only */
352 append_payload_memfd(&d, part->memfd, part->memfd_offset, part->size);
356 /* Otherwise, let's send a vector to the actual data.
357 * For that, we need to map it first. */
358 r = bus_body_part_map(part);
362 append_payload_vec(&d, part->data, part->size);
365 if (m->header->type == SD_BUS_MESSAGE_SIGNAL) {
366 struct kdbus_bloom_filter *bloom;
368 bloom = append_bloom(&d, m->bus->bloom_size);
369 r = bus_message_setup_bloom(m, bloom);
375 append_fds(&d, m->fds, m->n_fds);
377 m->kdbus->size = (uint8_t*) d - (uint8_t*) m->kdbus;
378 assert(m->kdbus->size <= sz);
387 static void unset_memfds(struct sd_bus_message *m) {
388 struct bus_body_part *part;
393 /* Make sure the memfds are not freed twice */
394 MESSAGE_FOREACH_PART(part, i, m)
395 if (part->memfd >= 0)
399 static void message_set_timestamp(sd_bus *bus, sd_bus_message *m, const struct kdbus_timestamp *ts) {
406 if (!(bus->attach_flags & KDBUS_ATTACH_TIMESTAMP))
409 m->realtime = ts->realtime_ns / NSEC_PER_USEC;
410 m->monotonic = ts->monotonic_ns / NSEC_PER_USEC;
411 m->seqnum = ts->seqnum;
414 static int bus_kernel_make_message(sd_bus *bus, struct kdbus_msg *k) {
415 sd_bus_message *m = NULL;
416 struct kdbus_item *d;
418 _cleanup_free_ int *fds = NULL;
419 struct bus_header *header = NULL;
421 size_t header_size = 0, footer_size = 0;
422 size_t n_bytes = 0, idx = 0;
423 const char *destination = NULL, *seclabel = NULL;
424 bool last_was_memfd = false;
429 assert(k->payload_type == KDBUS_PAYLOAD_DBUS);
431 KDBUS_ITEM_FOREACH(d, k, items) {
434 l = d->size - offsetof(struct kdbus_item, data);
438 case KDBUS_ITEM_PAYLOAD_OFF:
440 header = (struct bus_header*)((uint8_t*) k + d->vec.offset);
441 header_size = d->vec.size;
444 footer = (uint8_t*) k + d->vec.offset;
445 footer_size = d->vec.size;
447 n_bytes += d->vec.size;
448 last_was_memfd = false;
451 case KDBUS_ITEM_PAYLOAD_MEMFD:
452 if (!header) /* memfd cannot be first part */
455 n_bytes += d->memfd.size;
456 last_was_memfd = true;
459 case KDBUS_ITEM_FDS: {
464 f = realloc(fds, sizeof(int) * (n_fds + j));
469 memcpy(fds + n_fds, d->fds, sizeof(int) * j);
474 case KDBUS_ITEM_SECLABEL:
480 if (last_was_memfd) /* memfd cannot be last part */
486 if (header_size < sizeof(struct bus_header))
489 /* on kdbus we only speak native endian gvariant, never dbus1
490 * marshalling or reverse endian */
491 if (header->version != 2 ||
492 header->endian != BUS_NATIVE_ENDIAN)
495 r = bus_message_from_header(
505 /* The well-known names list is different from the other
506 credentials. If we asked for it, but nothing is there, this
507 means that the list of well-known names is simply empty, not
508 that we lack any data */
510 m->creds.mask |= (SD_BUS_CREDS_UNIQUE_NAME|SD_BUS_CREDS_WELL_KNOWN_NAMES) & bus->creds_mask;
512 KDBUS_ITEM_FOREACH(d, k, items) {
515 l = d->size - offsetof(struct kdbus_item, data);
519 case KDBUS_ITEM_PAYLOAD_OFF: {
522 begin_body = BUS_MESSAGE_BODY_BEGIN(m);
524 if (idx + d->vec.size > begin_body) {
525 struct bus_body_part *part;
527 /* Contains body material */
529 part = message_append_part(m);
535 /* A -1 offset is NUL padding. */
536 part->is_zero = d->vec.offset == ~0ULL;
538 if (idx >= begin_body) {
540 part->data = (uint8_t* )k + d->vec.offset;
541 part->size = d->vec.size;
544 part->data = (uint8_t*) k + d->vec.offset + (begin_body - idx);
545 part->size = d->vec.size - (begin_body - idx);
555 case KDBUS_ITEM_PAYLOAD_MEMFD: {
556 struct bus_body_part *part;
558 if (idx < BUS_MESSAGE_BODY_BEGIN(m)) {
563 part = message_append_part(m);
569 part->memfd = d->memfd.fd;
570 part->memfd_offset = d->memfd.start;
571 part->size = d->memfd.size;
574 idx += d->memfd.size;
578 case KDBUS_ITEM_PIDS:
580 /* The PID/TID might be missing, when the data
581 * is faked by a bus proxy and it lacks that
582 * information about the real client (since
583 * SO_PEERCRED is used for that). Also kernel
584 * namespacing might make some of this data
585 * unavailable when untranslatable. */
587 if (d->pids.pid > 0) {
588 m->creds.pid = (pid_t) d->pids.pid;
589 m->creds.mask |= SD_BUS_CREDS_PID & bus->creds_mask;
592 if (d->pids.tid > 0) {
593 m->creds.tid = (pid_t) d->pids.tid;
594 m->creds.mask |= SD_BUS_CREDS_TID & bus->creds_mask;
597 if (d->pids.ppid > 0) {
598 m->creds.ppid = (pid_t) d->pids.ppid;
599 m->creds.mask |= SD_BUS_CREDS_PPID & bus->creds_mask;
600 } else if (d->pids.pid == 1) {
602 m->creds.mask |= SD_BUS_CREDS_PPID & bus->creds_mask;
607 case KDBUS_ITEM_CREDS:
609 /* EUID/SUID/FSUID/EGID/SGID/FSGID might be
610 * missing too (see above). */
612 if ((uid_t) d->creds.uid != UID_INVALID) {
613 m->creds.uid = (uid_t) d->creds.uid;
614 m->creds.mask |= SD_BUS_CREDS_UID & bus->creds_mask;
617 if ((uid_t) d->creds.euid != UID_INVALID) {
618 m->creds.euid = (uid_t) d->creds.euid;
619 m->creds.mask |= SD_BUS_CREDS_EUID & bus->creds_mask;
622 if ((uid_t) d->creds.suid != UID_INVALID) {
623 m->creds.suid = (uid_t) d->creds.suid;
624 m->creds.mask |= SD_BUS_CREDS_SUID & bus->creds_mask;
627 if ((uid_t) d->creds.fsuid != UID_INVALID) {
628 m->creds.fsuid = (uid_t) d->creds.fsuid;
629 m->creds.mask |= SD_BUS_CREDS_FSUID & bus->creds_mask;
632 if ((gid_t) d->creds.gid != GID_INVALID) {
633 m->creds.gid = (gid_t) d->creds.gid;
634 m->creds.mask |= SD_BUS_CREDS_GID & bus->creds_mask;
637 if ((gid_t) d->creds.egid != GID_INVALID) {
638 m->creds.egid = (gid_t) d->creds.egid;
639 m->creds.mask |= SD_BUS_CREDS_EGID & bus->creds_mask;
642 if ((gid_t) d->creds.sgid != GID_INVALID) {
643 m->creds.sgid = (gid_t) d->creds.sgid;
644 m->creds.mask |= SD_BUS_CREDS_SGID & bus->creds_mask;
647 if ((gid_t) d->creds.fsgid != GID_INVALID) {
648 m->creds.fsgid = (gid_t) d->creds.fsgid;
649 m->creds.mask |= SD_BUS_CREDS_FSGID & bus->creds_mask;
654 case KDBUS_ITEM_TIMESTAMP:
655 message_set_timestamp(bus, m, &d->timestamp);
658 case KDBUS_ITEM_PID_COMM:
659 m->creds.comm = d->str;
660 m->creds.mask |= SD_BUS_CREDS_COMM & bus->creds_mask;
663 case KDBUS_ITEM_TID_COMM:
664 m->creds.tid_comm = d->str;
665 m->creds.mask |= SD_BUS_CREDS_TID_COMM & bus->creds_mask;
669 m->creds.exe = d->str;
670 m->creds.mask |= SD_BUS_CREDS_EXE & bus->creds_mask;
673 case KDBUS_ITEM_CMDLINE:
674 m->creds.cmdline = d->str;
675 m->creds.cmdline_size = l;
676 m->creds.mask |= SD_BUS_CREDS_CMDLINE & bus->creds_mask;
679 case KDBUS_ITEM_CGROUP:
680 m->creds.cgroup = d->str;
681 m->creds.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) & bus->creds_mask;
683 r = bus_get_root_path(bus);
687 m->creds.cgroup_root = bus->cgroup_root;
690 case KDBUS_ITEM_AUDIT:
691 m->creds.audit_session_id = (uint32_t) d->audit.sessionid;
692 m->creds.mask |= SD_BUS_CREDS_AUDIT_SESSION_ID & bus->creds_mask;
694 m->creds.audit_login_uid = (uid_t) d->audit.loginuid;
695 m->creds.mask |= SD_BUS_CREDS_AUDIT_LOGIN_UID & bus->creds_mask;
698 case KDBUS_ITEM_CAPS:
699 if (d->caps.last_cap != cap_last_cap() ||
700 d->size - offsetof(struct kdbus_item, caps.caps) < DIV_ROUND_UP(d->caps.last_cap, 32U) * 4 * 4) {
705 m->creds.capability = d->caps.caps;
706 m->creds.mask |= (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS) & bus->creds_mask;
709 case KDBUS_ITEM_DST_NAME:
710 if (!service_name_is_valid(d->str)) {
715 destination = d->str;
718 case KDBUS_ITEM_OWNED_NAME:
719 if (!service_name_is_valid(d->name.name)) {
724 if (bus->creds_mask & SD_BUS_CREDS_WELL_KNOWN_NAMES) {
728 /* We just extend the array here, but
729 * do not allocate the strings inside
730 * of it, instead we just point to our
731 * buffer directly. */
732 n = strv_length(m->creds.well_known_names);
733 wkn = realloc(m->creds.well_known_names, (n + 2) * sizeof(char*));
739 wkn[n] = d->name.name;
741 m->creds.well_known_names = wkn;
743 m->creds.mask |= SD_BUS_CREDS_WELL_KNOWN_NAMES;
747 case KDBUS_ITEM_CONN_DESCRIPTION:
748 m->creds.description = d->str;
749 m->creds.mask |= SD_BUS_CREDS_DESCRIPTION & bus->creds_mask;
752 case KDBUS_ITEM_AUXGROUPS:
754 if (bus->creds_mask & SD_BUS_CREDS_SUPPLEMENTARY_GIDS) {
758 n = (d->size - offsetof(struct kdbus_item, data64)) / sizeof(uint64_t);
765 for (i = 0; i < n; i++)
768 m->creds.supplementary_gids = g;
769 m->creds.n_supplementary_gids = n;
770 m->creds.mask |= SD_BUS_CREDS_SUPPLEMENTARY_GIDS;
776 case KDBUS_ITEM_SECLABEL:
780 log_debug("Got unknown field from kernel %llu", d->type);
784 /* If we requested the list of well-known names to be appended
785 * and the sender had none no item for it will be
786 * attached. However, this does *not* mean that the kernel
787 * didn't want to provide this information to us. Hence, let's
788 * explicitly mark this information as available if it was
790 m->creds.mask |= bus->creds_mask & SD_BUS_CREDS_WELL_KNOWN_NAMES;
792 r = bus_message_parse_fields(m);
796 /* Refuse messages if kdbus and dbus1 cookie doesn't match up */
797 if ((uint64_t) m->header->dbus2.cookie != k->cookie) {
802 /* Refuse messages where the reply flag doesn't match up */
803 if (!(m->header->flags & BUS_MESSAGE_NO_REPLY_EXPECTED) != !!(k->flags & KDBUS_MSG_EXPECT_REPLY)) {
808 /* Refuse reply messages where the reply cookie doesn't match up */
809 if ((m->header->flags & BUS_MESSAGE_NO_REPLY_EXPECTED) && m->reply_cookie != k->cookie_reply) {
814 /* Refuse messages where the autostart flag doesn't match up */
815 if (!(m->header->flags & BUS_MESSAGE_NO_AUTO_START) != !(k->flags & KDBUS_MSG_NO_AUTO_START)) {
820 /* Override information from the user header with data from the kernel */
821 if (k->src_id == KDBUS_SRC_ID_KERNEL)
822 bus_message_set_sender_driver(bus, m);
824 snprintf(m->sender_buffer, sizeof(m->sender_buffer), ":1.%llu", (unsigned long long) k->src_id);
825 m->sender = m->creds.unique_name = m->sender_buffer;
829 m->destination = destination;
830 else if (k->dst_id == KDBUS_DST_ID_BROADCAST)
831 m->destination = NULL;
832 else if (k->dst_id == KDBUS_DST_ID_NAME)
833 m->destination = bus->unique_name; /* fill in unique name if the well-known name is missing */
835 snprintf(m->destination_buffer, sizeof(m->destination_buffer), ":1.%llu", (unsigned long long) k->dst_id);
836 m->destination = m->destination_buffer;
839 /* We take possession of the kmsg struct now */
841 m->release_kdbus = true;
845 bus->rqueue[bus->rqueue_size++] = m;
851 sd_bus_message_unref(m);
856 int bus_kernel_take_fd(sd_bus *b) {
857 struct kdbus_bloom_parameter *bloom = NULL;
858 struct kdbus_item *items, *item;
859 struct kdbus_cmd_hello *hello;
860 _cleanup_free_ char *g = NULL;
862 size_t l = 0, m = 0, sz;
872 if (b->description) {
873 g = bus_label_escape(b->description);
881 /* If no name is explicitly set, we'll include a hint
882 * indicating the library implementation, a hint which
883 * kind of bus this is and the thread name */
885 assert_se(prctl(PR_GET_NAME, (unsigned long) pr) >= 0);
888 name = b->is_system ? "sd-system" :
889 b->is_user ? "sd-user" : "sd";
891 _cleanup_free_ char *e = NULL;
893 e = bus_label_escape(pr);
897 g = strappend(b->is_system ? "sd-system-" :
898 b->is_user ? "sd-user-" : "sd-",
906 b->description = bus_label_unescape(name);
913 sz = ALIGN8(offsetof(struct kdbus_cmd_hello, items)) +
914 ALIGN8(offsetof(struct kdbus_item, str) + m + 1);
916 if (b->fake_creds_valid)
917 sz += ALIGN8(offsetof(struct kdbus_item, creds) + sizeof(struct kdbus_creds));
919 if (b->fake_pids_valid)
920 sz += ALIGN8(offsetof(struct kdbus_item, pids) + sizeof(struct kdbus_pids));
923 l = strlen(b->fake_label);
924 sz += ALIGN8(offsetof(struct kdbus_item, str) + l + 1);
927 hello = alloca0_align(sz, 8);
929 hello->flags = b->hello_flags;
930 hello->attach_flags_send = _KDBUS_ATTACH_ANY;
931 hello->attach_flags_recv = b->attach_flags;
932 hello->pool_size = KDBUS_POOL_SIZE;
936 item->size = offsetof(struct kdbus_item, str) + m + 1;
937 item->type = KDBUS_ITEM_CONN_DESCRIPTION;
938 memcpy(item->str, name, m + 1);
939 item = KDBUS_ITEM_NEXT(item);
941 if (b->fake_creds_valid) {
942 item->size = offsetof(struct kdbus_item, creds) + sizeof(struct kdbus_creds);
943 item->type = KDBUS_ITEM_CREDS;
944 item->creds = b->fake_creds;
946 item = KDBUS_ITEM_NEXT(item);
949 if (b->fake_pids_valid) {
950 item->size = offsetof(struct kdbus_item, pids) + sizeof(struct kdbus_pids);
951 item->type = KDBUS_ITEM_PIDS;
952 item->pids = b->fake_pids;
954 item = KDBUS_ITEM_NEXT(item);
958 item->size = offsetof(struct kdbus_item, str) + l + 1;
959 item->type = KDBUS_ITEM_SECLABEL;
960 memcpy(item->str, b->fake_label, l+1);
963 r = ioctl(b->input_fd, KDBUS_CMD_HELLO, hello);
966 /* If the ioctl is not supported we assume that the
967 * API version changed in a major incompatible way,
968 * let's indicate an API incompatibility in this
970 return -ESOCKTNOSUPPORT;
975 if (!b->kdbus_buffer) {
976 b->kdbus_buffer = mmap(NULL, KDBUS_POOL_SIZE, PROT_READ, MAP_SHARED, b->input_fd, 0);
977 if (b->kdbus_buffer == MAP_FAILED) {
978 b->kdbus_buffer = NULL;
984 /* The higher 32bit of the bus_flags fields are considered
985 * 'incompatible flags'. Refuse them all for now. */
986 if (hello->bus_flags > 0xFFFFFFFFULL) {
987 r = -ESOCKTNOSUPPORT;
991 /* extract bloom parameters from items */
992 items = (void*)((uint8_t*)b->kdbus_buffer + hello->offset);
993 KDBUS_FOREACH(item, items, hello->items_size) {
994 switch (item->type) {
995 case KDBUS_ITEM_BLOOM_PARAMETER:
996 bloom = &item->bloom_parameter;
1001 if (!bloom || !bloom_validate_parameters((size_t) bloom->size, (unsigned) bloom->n_hash)) {
1006 b->bloom_size = (size_t) bloom->size;
1007 b->bloom_n_hash = (unsigned) bloom->n_hash;
1009 if (asprintf(&b->unique_name, ":1.%llu", (unsigned long long) hello->id) < 0) {
1014 b->unique_id = hello->id;
1016 b->is_kernel = true;
1017 b->bus_client = true;
1018 b->can_fds = !!(hello->flags & KDBUS_HELLO_ACCEPT_FD);
1019 b->message_version = 2;
1020 b->message_endian = BUS_NATIVE_ENDIAN;
1022 /* the kernel told us the UUID of the underlying bus */
1023 memcpy(b->server_id.bytes, hello->id128, sizeof(b->server_id.bytes));
1025 /* free returned items */
1026 (void) bus_kernel_cmd_free(b, hello->offset);
1027 return bus_start_running(b);
1030 (void) bus_kernel_cmd_free(b, hello->offset);
1034 int bus_kernel_connect(sd_bus *b) {
1036 assert(b->input_fd < 0);
1037 assert(b->output_fd < 0);
1043 b->input_fd = open(b->kernel, O_RDWR|O_NOCTTY|O_CLOEXEC);
1044 if (b->input_fd < 0)
1047 b->output_fd = b->input_fd;
1049 return bus_kernel_take_fd(b);
1052 int bus_kernel_cmd_free(sd_bus *bus, uint64_t offset) {
1053 struct kdbus_cmd_free cmd = {
1054 .size = sizeof(cmd),
1060 assert(bus->is_kernel);
1062 r = ioctl(bus->input_fd, KDBUS_CMD_FREE, &cmd);
1069 static void close_kdbus_msg(sd_bus *bus, struct kdbus_msg *k) {
1070 struct kdbus_item *d;
1075 KDBUS_ITEM_FOREACH(d, k, items) {
1076 if (d->type == KDBUS_ITEM_FDS)
1077 close_many(d->fds, (d->size - offsetof(struct kdbus_item, fds)) / sizeof(int));
1078 else if (d->type == KDBUS_ITEM_PAYLOAD_MEMFD)
1079 safe_close(d->memfd.fd);
1082 bus_kernel_cmd_free(bus, (uint8_t*) k - (uint8_t*) bus->kdbus_buffer);
1085 int bus_kernel_write_message(sd_bus *bus, sd_bus_message *m, bool hint_sync_call) {
1086 struct kdbus_cmd_send cmd = { };
1091 assert(bus->state == BUS_RUNNING);
1093 /* If we can't deliver, we want room for the error message */
1094 r = bus_rqueue_make_room(bus);
1098 r = bus_message_setup_kmsg(bus, m);
1102 cmd.size = sizeof(cmd);
1103 cmd.msg_address = (uintptr_t)m->kdbus;
1105 /* If this is a synchronous method call, then let's tell the
1106 * kernel, so that it can pass CPU time/scheduling to the
1107 * destination for the time, if it wants to. If we
1108 * synchronously wait for the result anyway, we won't need CPU
1110 if (hint_sync_call) {
1111 m->kdbus->flags |= KDBUS_MSG_EXPECT_REPLY;
1112 cmd.flags |= KDBUS_SEND_SYNC_REPLY;
1115 r = ioctl(bus->output_fd, KDBUS_CMD_SEND, &cmd);
1117 _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
1118 sd_bus_message *reply;
1120 if (errno == EAGAIN || errno == EINTR)
1122 else if (errno == ENXIO || errno == ESRCH) {
1124 /* ENXIO: unique name not known
1125 * ESRCH: well-known name not known */
1127 if (m->header->type == SD_BUS_MESSAGE_METHOD_CALL)
1128 sd_bus_error_setf(&error, SD_BUS_ERROR_SERVICE_UNKNOWN, "Destination %s not known", m->destination);
1130 log_debug("Could not deliver message to %s as destination is not known. Ignoring.", m->destination);
1134 } else if (errno == EADDRNOTAVAIL) {
1136 /* EADDRNOTAVAIL: activation is possible, but turned off in request flags */
1138 if (m->header->type == SD_BUS_MESSAGE_METHOD_CALL)
1139 sd_bus_error_setf(&error, SD_BUS_ERROR_SERVICE_UNKNOWN, "Activation of %s not requested", m->destination);
1141 log_debug("Could not deliver message to %s as destination is not activated. Ignoring.", m->destination);
1147 r = bus_message_new_synthetic_error(
1149 BUS_MESSAGE_COOKIE(m),
1156 r = bus_seal_synthetic_message(bus, reply);
1160 bus->rqueue[bus->rqueue_size++] = reply;
1162 } else if (hint_sync_call) {
1163 struct kdbus_msg *k;
1165 k = (struct kdbus_msg *)((uint8_t *)bus->kdbus_buffer + cmd.reply.offset);
1168 if (k->payload_type == KDBUS_PAYLOAD_DBUS) {
1170 r = bus_kernel_make_message(bus, k);
1172 close_kdbus_msg(bus, k);
1174 /* Anybody can send us invalid messages, let's just drop them. */
1175 if (r == -EBADMSG || r == -EPROTOTYPE)
1176 log_debug_errno(r, "Ignoring invalid synchronous reply: %m");
1181 log_debug("Ignoring message with unknown payload type %llu.", (unsigned long long) k->payload_type);
1182 close_kdbus_msg(bus, k);
1189 static int push_name_owner_changed(
1192 const char *old_owner,
1193 const char *new_owner,
1194 const struct kdbus_timestamp *ts) {
1196 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
1201 r = sd_bus_message_new_signal(
1204 "/org/freedesktop/DBus",
1205 "org.freedesktop.DBus",
1206 "NameOwnerChanged");
1210 r = sd_bus_message_append(m, "sss", name, old_owner, new_owner);
1214 bus_message_set_sender_driver(bus, m);
1215 message_set_timestamp(bus, m, ts);
1217 r = bus_seal_synthetic_message(bus, m);
1221 bus->rqueue[bus->rqueue_size++] = m;
1227 static int translate_name_change(
1229 const struct kdbus_msg *k,
1230 const struct kdbus_item *d,
1231 const struct kdbus_timestamp *ts) {
1233 char new_owner[UNIQUE_NAME_MAX], old_owner[UNIQUE_NAME_MAX];
1239 if (d->type == KDBUS_ITEM_NAME_ADD || (d->name_change.old_id.flags & (KDBUS_NAME_IN_QUEUE|KDBUS_NAME_ACTIVATOR)))
1242 sprintf(old_owner, ":1.%llu", (unsigned long long) d->name_change.old_id.id);
1244 if (d->type == KDBUS_ITEM_NAME_REMOVE || (d->name_change.new_id.flags & (KDBUS_NAME_IN_QUEUE|KDBUS_NAME_ACTIVATOR))) {
1246 if (isempty(old_owner))
1251 sprintf(new_owner, ":1.%llu", (unsigned long long) d->name_change.new_id.id);
1253 return push_name_owner_changed(bus, d->name_change.name, old_owner, new_owner, ts);
1256 static int translate_id_change(
1258 const struct kdbus_msg *k,
1259 const struct kdbus_item *d,
1260 const struct kdbus_timestamp *ts) {
1262 char owner[UNIQUE_NAME_MAX];
1268 sprintf(owner, ":1.%llu", d->id_change.id);
1270 return push_name_owner_changed(
1272 d->type == KDBUS_ITEM_ID_ADD ? NULL : owner,
1273 d->type == KDBUS_ITEM_ID_ADD ? owner : NULL,
1277 static int translate_reply(
1279 const struct kdbus_msg *k,
1280 const struct kdbus_item *d,
1281 const struct kdbus_timestamp *ts) {
1283 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
1290 r = bus_message_new_synthetic_error(
1293 d->type == KDBUS_ITEM_REPLY_TIMEOUT ?
1294 &SD_BUS_ERROR_MAKE_CONST(SD_BUS_ERROR_NO_REPLY, "Method call timed out") :
1295 &SD_BUS_ERROR_MAKE_CONST(SD_BUS_ERROR_NO_REPLY, "Method call peer died"),
1300 message_set_timestamp(bus, m, ts);
1302 r = bus_seal_synthetic_message(bus, m);
1306 bus->rqueue[bus->rqueue_size++] = m;
1312 static int bus_kernel_translate_message(sd_bus *bus, struct kdbus_msg *k) {
1313 static int (* const translate[])(sd_bus *bus, const struct kdbus_msg *k, const struct kdbus_item *d, const struct kdbus_timestamp *ts) = {
1314 [KDBUS_ITEM_NAME_ADD - _KDBUS_ITEM_KERNEL_BASE] = translate_name_change,
1315 [KDBUS_ITEM_NAME_REMOVE - _KDBUS_ITEM_KERNEL_BASE] = translate_name_change,
1316 [KDBUS_ITEM_NAME_CHANGE - _KDBUS_ITEM_KERNEL_BASE] = translate_name_change,
1318 [KDBUS_ITEM_ID_ADD - _KDBUS_ITEM_KERNEL_BASE] = translate_id_change,
1319 [KDBUS_ITEM_ID_REMOVE - _KDBUS_ITEM_KERNEL_BASE] = translate_id_change,
1321 [KDBUS_ITEM_REPLY_TIMEOUT - _KDBUS_ITEM_KERNEL_BASE] = translate_reply,
1322 [KDBUS_ITEM_REPLY_DEAD - _KDBUS_ITEM_KERNEL_BASE] = translate_reply,
1325 struct kdbus_item *d, *found = NULL;
1326 struct kdbus_timestamp *ts = NULL;
1330 assert(k->payload_type == KDBUS_PAYLOAD_KERNEL);
1332 KDBUS_ITEM_FOREACH(d, k, items) {
1333 if (d->type == KDBUS_ITEM_TIMESTAMP)
1335 else if (d->type >= _KDBUS_ITEM_KERNEL_BASE && d->type < _KDBUS_ITEM_KERNEL_BASE + ELEMENTSOF(translate)) {
1340 log_debug("Got unknown field from kernel %llu", d->type);
1344 log_debug("Didn't find a kernel message to translate.");
1348 return translate[found->type - _KDBUS_ITEM_KERNEL_BASE](bus, k, found, ts);
1351 int bus_kernel_read_message(sd_bus *bus, bool hint_priority, int64_t priority) {
1352 struct kdbus_cmd_recv recv = { .size = sizeof(recv) };
1353 struct kdbus_msg *k;
1358 r = bus_rqueue_make_room(bus);
1362 if (hint_priority) {
1363 recv.flags |= KDBUS_RECV_USE_PRIORITY;
1364 recv.priority = priority;
1367 r = ioctl(bus->input_fd, KDBUS_CMD_RECV, &recv);
1368 if (recv.return_flags & KDBUS_RECV_RETURN_DROPPED_MSGS)
1369 log_debug("%s: kdbus reports %" PRIu64 " dropped broadcast messages, ignoring.", strna(bus->description), (uint64_t) recv.dropped_msgs);
1371 if (errno == EAGAIN)
1377 k = (struct kdbus_msg *)((uint8_t *)bus->kdbus_buffer + recv.msg.offset);
1378 if (k->payload_type == KDBUS_PAYLOAD_DBUS) {
1379 r = bus_kernel_make_message(bus, k);
1381 /* Anybody can send us invalid messages, let's just drop them. */
1382 if (r == -EBADMSG || r == -EPROTOTYPE) {
1383 log_debug_errno(r, "Ignoring invalid message: %m");
1388 close_kdbus_msg(bus, k);
1389 } else if (k->payload_type == KDBUS_PAYLOAD_KERNEL) {
1390 r = bus_kernel_translate_message(bus, k);
1391 close_kdbus_msg(bus, k);
1393 log_debug("Ignoring message with unknown payload type %llu.", (unsigned long long) k->payload_type);
1395 close_kdbus_msg(bus, k);
1398 return r < 0 ? r : 1;
1401 int bus_kernel_pop_memfd(sd_bus *bus, void **address, size_t *mapped, size_t *allocated) {
1402 struct memfd_cache *c;
1409 if (!bus || !bus->is_kernel)
1412 assert_se(pthread_mutex_lock(&bus->memfd_cache_mutex) >= 0);
1414 if (bus->n_memfd_cache <= 0) {
1417 assert_se(pthread_mutex_unlock(&bus->memfd_cache_mutex) >= 0);
1419 r = memfd_new(bus->description);
1429 c = &bus->memfd_cache[--bus->n_memfd_cache];
1432 assert(c->mapped == 0 || c->address);
1434 *address = c->address;
1435 *mapped = c->mapped;
1436 *allocated = c->allocated;
1439 assert_se(pthread_mutex_unlock(&bus->memfd_cache_mutex) >= 0);
1444 static void close_and_munmap(int fd, void *address, size_t size) {
1446 assert_se(munmap(address, PAGE_ALIGN(size)) >= 0);
1451 void bus_kernel_push_memfd(sd_bus *bus, int fd, void *address, size_t mapped, size_t allocated) {
1452 struct memfd_cache *c;
1453 uint64_t max_mapped = PAGE_ALIGN(MEMFD_CACHE_ITEM_SIZE_MAX);
1456 assert(mapped == 0 || address);
1458 if (!bus || !bus->is_kernel) {
1459 close_and_munmap(fd, address, mapped);
1463 assert_se(pthread_mutex_lock(&bus->memfd_cache_mutex) >= 0);
1465 if (bus->n_memfd_cache >= ELEMENTSOF(bus->memfd_cache)) {
1466 assert_se(pthread_mutex_unlock(&bus->memfd_cache_mutex) >= 0);
1468 close_and_munmap(fd, address, mapped);
1472 c = &bus->memfd_cache[bus->n_memfd_cache++];
1474 c->address = address;
1476 /* If overly long, let's return a bit to the OS */
1477 if (mapped > max_mapped) {
1478 assert_se(memfd_set_size(fd, max_mapped) >= 0);
1479 assert_se(munmap((uint8_t*) address + max_mapped, PAGE_ALIGN(mapped - max_mapped)) >= 0);
1480 c->mapped = c->allocated = max_mapped;
1483 c->allocated = allocated;
1486 assert_se(pthread_mutex_unlock(&bus->memfd_cache_mutex) >= 0);
1489 void bus_kernel_flush_memfd(sd_bus *b) {
1494 for (i = 0; i < b->n_memfd_cache; i++)
1495 close_and_munmap(b->memfd_cache[i].fd, b->memfd_cache[i].address, b->memfd_cache[i].mapped);
1498 uint64_t request_name_flags_to_kdbus(uint64_t flags) {
1501 if (flags & SD_BUS_NAME_ALLOW_REPLACEMENT)
1502 f |= KDBUS_NAME_ALLOW_REPLACEMENT;
1504 if (flags & SD_BUS_NAME_REPLACE_EXISTING)
1505 f |= KDBUS_NAME_REPLACE_EXISTING;
1507 if (flags & SD_BUS_NAME_QUEUE)
1508 f |= KDBUS_NAME_QUEUE;
1513 uint64_t attach_flags_to_kdbus(uint64_t mask) {
1516 if (mask & (SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_SUID|SD_BUS_CREDS_FSUID|
1517 SD_BUS_CREDS_GID|SD_BUS_CREDS_EGID|SD_BUS_CREDS_SGID|SD_BUS_CREDS_FSGID))
1518 m |= KDBUS_ATTACH_CREDS;
1520 if (mask & (SD_BUS_CREDS_PID|SD_BUS_CREDS_TID|SD_BUS_CREDS_PPID))
1521 m |= KDBUS_ATTACH_PIDS;
1523 if (mask & SD_BUS_CREDS_COMM)
1524 m |= KDBUS_ATTACH_PID_COMM;
1526 if (mask & SD_BUS_CREDS_TID_COMM)
1527 m |= KDBUS_ATTACH_TID_COMM;
1529 if (mask & SD_BUS_CREDS_EXE)
1530 m |= KDBUS_ATTACH_EXE;
1532 if (mask & SD_BUS_CREDS_CMDLINE)
1533 m |= KDBUS_ATTACH_CMDLINE;
1535 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))
1536 m |= KDBUS_ATTACH_CGROUP;
1538 if (mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS))
1539 m |= KDBUS_ATTACH_CAPS;
1541 if (mask & SD_BUS_CREDS_SELINUX_CONTEXT)
1542 m |= KDBUS_ATTACH_SECLABEL;
1544 if (mask & (SD_BUS_CREDS_AUDIT_SESSION_ID|SD_BUS_CREDS_AUDIT_LOGIN_UID))
1545 m |= KDBUS_ATTACH_AUDIT;
1547 if (mask & SD_BUS_CREDS_WELL_KNOWN_NAMES)
1548 m |= KDBUS_ATTACH_NAMES;
1550 if (mask & SD_BUS_CREDS_DESCRIPTION)
1551 m |= KDBUS_ATTACH_CONN_DESCRIPTION;
1553 if (mask & SD_BUS_CREDS_SUPPLEMENTARY_GIDS)
1554 m |= KDBUS_ATTACH_AUXGROUPS;
1559 int bus_kernel_create_bus(const char *name, bool world, char **s) {
1560 struct kdbus_cmd *make;
1561 struct kdbus_item *n;
1568 fd = open("/sys/fs/kdbus/control", O_RDWR|O_NOCTTY|O_CLOEXEC);
1573 make = alloca0_align(offsetof(struct kdbus_cmd, items) +
1574 ALIGN8(offsetof(struct kdbus_item, bloom_parameter) + sizeof(struct kdbus_bloom_parameter)) +
1575 ALIGN8(offsetof(struct kdbus_item, data64) + sizeof(uint64_t)) +
1576 ALIGN8(offsetof(struct kdbus_item, str) + DECIMAL_STR_MAX(uid_t) + 1 + l + 1),
1579 make->size = offsetof(struct kdbus_cmd, items);
1581 /* Set the bloom parameters */
1583 n->size = offsetof(struct kdbus_item, bloom_parameter) +
1584 sizeof(struct kdbus_bloom_parameter);
1585 n->type = KDBUS_ITEM_BLOOM_PARAMETER;
1586 n->bloom_parameter.size = DEFAULT_BLOOM_SIZE;
1587 n->bloom_parameter.n_hash = DEFAULT_BLOOM_N_HASH;
1589 assert_cc(DEFAULT_BLOOM_SIZE > 0);
1590 assert_cc(DEFAULT_BLOOM_N_HASH > 0);
1592 make->size += ALIGN8(n->size);
1594 /* Provide all metadata via bus-owner queries */
1595 n = KDBUS_ITEM_NEXT(n);
1596 n->type = KDBUS_ITEM_ATTACH_FLAGS_SEND;
1597 n->size = offsetof(struct kdbus_item, data64) + sizeof(uint64_t);
1598 n->data64[0] = _KDBUS_ATTACH_ANY;
1599 make->size += ALIGN8(n->size);
1601 /* Set the a good name */
1602 n = KDBUS_ITEM_NEXT(n);
1603 sprintf(n->str, UID_FMT "-%s", getuid(), name);
1604 n->size = offsetof(struct kdbus_item, str) + strlen(n->str) + 1;
1605 n->type = KDBUS_ITEM_MAKE_NAME;
1606 make->size += ALIGN8(n->size);
1608 make->flags = world ? KDBUS_MAKE_ACCESS_WORLD : 0;
1610 if (ioctl(fd, KDBUS_CMD_BUS_MAKE, make) < 0) {
1613 /* Major API change? then the ioctls got shuffled around. */
1614 if (errno == ENOTTY)
1615 return -ESOCKTNOSUPPORT;
1623 p = strjoin("/sys/fs/kdbus/", n->str, "/bus", NULL);
1635 int bus_kernel_open_bus_fd(const char *bus, char **path) {
1642 len = strlen("/sys/fs/kdbus/") + DECIMAL_STR_MAX(uid_t) + 1 + strlen(bus) + strlen("/bus") + 1;
1649 p = newa(char, len);
1651 sprintf(p, "/sys/fs/kdbus/" UID_FMT "-%s/bus", getuid(), bus);
1653 fd = open(p, O_RDWR|O_NOCTTY|O_CLOEXEC);
1667 int bus_kernel_create_endpoint(const char *bus_name, const char *ep_name, char **ep_path) {
1668 _cleanup_free_ char *path = NULL;
1669 struct kdbus_cmd *make;
1670 struct kdbus_item *n;
1674 fd = bus_kernel_open_bus_fd(bus_name, &path);
1678 make = alloca0_align(ALIGN8(offsetof(struct kdbus_cmd, items)) +
1679 ALIGN8(offsetof(struct kdbus_item, str) + DECIMAL_STR_MAX(uid_t) + 1 + strlen(ep_name) + 1),
1681 make->size = ALIGN8(offsetof(struct kdbus_cmd, items));
1682 make->flags = KDBUS_MAKE_ACCESS_WORLD;
1685 sprintf(n->str, UID_FMT "-%s", getuid(), ep_name);
1686 n->size = offsetof(struct kdbus_item, str) + strlen(n->str) + 1;
1687 n->type = KDBUS_ITEM_MAKE_NAME;
1688 make->size += ALIGN8(n->size);
1691 if (ioctl(fd, KDBUS_CMD_ENDPOINT_MAKE, make) < 0) {
1699 p = strjoin(dirname(path), "/", name, NULL);
1711 int bus_kernel_try_close(sd_bus *bus) {
1712 struct kdbus_cmd byebye = { .size = sizeof(byebye) };
1715 assert(bus->is_kernel);
1717 if (ioctl(bus->input_fd, KDBUS_CMD_BYEBYE, &byebye) < 0)
1723 int bus_kernel_drop_one(int fd) {
1724 struct kdbus_cmd_recv recv = {
1725 .size = sizeof(recv),
1726 .flags = KDBUS_RECV_DROP,
1731 if (ioctl(fd, KDBUS_CMD_RECV, &recv) < 0)
1737 int bus_kernel_realize_attach_flags(sd_bus *bus) {
1738 struct kdbus_cmd *update;
1739 struct kdbus_item *n;
1742 assert(bus->is_kernel);
1744 update = alloca0_align(offsetof(struct kdbus_cmd, items) +
1745 ALIGN8(offsetof(struct kdbus_item, data64) + sizeof(uint64_t)),
1749 n->type = KDBUS_ITEM_ATTACH_FLAGS_RECV;
1750 n->size = offsetof(struct kdbus_item, data64) + sizeof(uint64_t);
1751 n->data64[0] = bus->attach_flags;
1754 offsetof(struct kdbus_cmd, items) +
1757 if (ioctl(bus->input_fd, KDBUS_CMD_UPDATE, update) < 0)
1763 int bus_kernel_get_bus_name(sd_bus *bus, char **name) {
1764 struct kdbus_cmd_info cmd = {
1765 .size = sizeof(struct kdbus_cmd_info),
1767 struct kdbus_info *info;
1768 struct kdbus_item *item;
1774 assert(bus->is_kernel);
1776 r = ioctl(bus->input_fd, KDBUS_CMD_BUS_CREATOR_INFO, &cmd);
1780 info = (struct kdbus_info*) ((uint8_t*) bus->kdbus_buffer + cmd.offset);
1782 KDBUS_ITEM_FOREACH(item, info, items)
1783 if (item->type == KDBUS_ITEM_MAKE_NAME) {
1784 r = free_and_strdup(&n, item->str);
1788 bus_kernel_cmd_free(bus, cmd.offset);