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>
32 #include "bus-internal.h"
33 #include "bus-message.h"
34 #include "bus-control.h"
35 #include "bus-bloom.h"
38 _public_ int sd_bus_get_unique_name(sd_bus *bus, const char **unique) {
41 assert_return(bus, -EINVAL);
42 assert_return(unique, -EINVAL);
43 assert_return(!bus_pid_changed(bus), -ECHILD);
45 r = bus_ensure_running(bus);
49 *unique = bus->unique_name;
53 static int bus_request_name_kernel(sd_bus *bus, const char *name, unsigned flags) {
54 struct kdbus_cmd_name *n;
62 n = alloca0(offsetof(struct kdbus_cmd_name, name) + l + 1);
63 n->size = offsetof(struct kdbus_cmd_name, name) + l + 1;
64 kdbus_translate_request_name_flags(flags, (uint64_t *) &n->flags);
65 memcpy(n->name, name, l+1);
67 #ifdef HAVE_VALGRIND_MEMCHECK_H
68 VALGRIND_MAKE_MEM_DEFINED(n, n->size);
71 r = ioctl(bus->input_fd, KDBUS_CMD_NAME_ACQUIRE, n);
75 if (n->flags & KDBUS_NAME_IN_QUEUE)
81 static int bus_request_name_dbus1(sd_bus *bus, const char *name, unsigned flags) {
82 _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
89 r = sd_bus_call_method(
91 "org.freedesktop.DBus",
93 "org.freedesktop.DBus",
103 r = sd_bus_message_read(reply, "u", &ret);
107 if (ret == BUS_NAME_ALREADY_OWNER)
109 else if (ret == BUS_NAME_EXISTS)
111 else if (ret == BUS_NAME_IN_QUEUE)
113 else if (ret == BUS_NAME_PRIMARY_OWNER)
119 _public_ int sd_bus_request_name(sd_bus *bus, const char *name, unsigned flags) {
120 assert_return(bus, -EINVAL);
121 assert_return(name, -EINVAL);
122 assert_return(bus->bus_client, -EINVAL);
123 assert_return(BUS_IS_OPEN(bus->state), -ENOTCONN);
124 assert_return(!bus_pid_changed(bus), -ECHILD);
125 assert_return(!(flags & ~(SD_BUS_NAME_ALLOW_REPLACEMENT|SD_BUS_NAME_REPLACE_EXISTING|SD_BUS_NAME_DO_NOT_QUEUE)), -EINVAL);
128 return bus_request_name_kernel(bus, name, flags);
130 return bus_request_name_dbus1(bus, name, flags);
133 static int bus_release_name_kernel(sd_bus *bus, const char *name) {
134 struct kdbus_cmd_name *n;
142 n = alloca0(offsetof(struct kdbus_cmd_name, name) + l + 1);
143 n->size = offsetof(struct kdbus_cmd_name, name) + l + 1;
144 memcpy(n->name, name, l+1);
146 #ifdef HAVE_VALGRIND_MEMCHECK_H
147 VALGRIND_MAKE_MEM_DEFINED(n, n->size);
149 r = ioctl(bus->input_fd, KDBUS_CMD_NAME_RELEASE, n);
156 static int bus_release_name_dbus1(sd_bus *bus, const char *name) {
157 _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
164 r = sd_bus_call_method(
166 "org.freedesktop.DBus",
168 "org.freedesktop.DBus",
177 r = sd_bus_message_read(reply, "u", &ret);
180 if (ret == BUS_NAME_NON_EXISTENT)
182 if (ret == BUS_NAME_NOT_OWNER)
183 return -EADDRNOTAVAIL;
184 if (ret == BUS_NAME_RELEASED)
190 _public_ int sd_bus_release_name(sd_bus *bus, const char *name) {
191 assert_return(bus, -EINVAL);
192 assert_return(name, -EINVAL);
193 assert_return(bus->bus_client, -EINVAL);
194 assert_return(BUS_IS_OPEN(bus->state), -ENOTCONN);
195 assert_return(!bus_pid_changed(bus), -ECHILD);
198 return bus_release_name_kernel(bus, name);
200 return bus_release_name_dbus1(bus, name);
203 static int kernel_get_list(sd_bus *bus, uint64_t flags, char ***x) {
204 struct kdbus_cmd_name_list cmd = {};
205 struct kdbus_name_list *name_list;
206 struct kdbus_cmd_name *name;
209 /* Caller will free half-constructed list on failure... */
213 r = ioctl(bus->input_fd, KDBUS_CMD_NAME_LIST, &cmd);
217 name_list = (struct kdbus_name_list *) ((uint8_t *) bus->kdbus_buffer + cmd.offset);
219 KDBUS_PART_FOREACH(name, name_list, names) {
221 if (name->size > sizeof(*name)) {
222 r = strv_extend(x, name->name);
228 if (asprintf(&n, ":1.%llu", (unsigned long long) name->id) < 0)
240 r = ioctl(sd_bus_get_fd(bus), KDBUS_CMD_FREE, &cmd.offset);
247 static int bus_list_names_kernel(sd_bus *bus, char ***acquired, char ***activatable) {
248 _cleanup_strv_free_ char **x = NULL, **y = NULL;
252 r = kernel_get_list(bus, KDBUS_NAME_LIST_UNIQUE | KDBUS_NAME_LIST_NAMES, &x);
258 r = kernel_get_list(bus, KDBUS_NAME_LIST_STARTERS, &y);
274 static int bus_list_names_dbus1(sd_bus *bus, char ***acquired, char ***activatable) {
275 _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
276 _cleanup_strv_free_ char **x = NULL, **y = NULL;
280 r = sd_bus_call_method(
282 "org.freedesktop.DBus",
284 "org.freedesktop.DBus",
292 r = sd_bus_message_read_strv(reply, &x);
296 reply = sd_bus_message_unref(reply);
300 r = sd_bus_call_method(
302 "org.freedesktop.DBus",
304 "org.freedesktop.DBus",
305 "ListActivatableNames",
312 r = sd_bus_message_read_strv(reply, &y);
328 _public_ int sd_bus_list_names(sd_bus *bus, char ***acquired, char ***activatable) {
329 assert_return(bus, -EINVAL);
330 assert_return(acquired || activatable, -EINVAL);
331 assert_return(BUS_IS_OPEN(bus->state), -ENOTCONN);
332 assert_return(!bus_pid_changed(bus), -ECHILD);
335 return bus_list_names_kernel(bus, acquired, activatable);
337 return bus_list_names_dbus1(bus, acquired, activatable);
340 static int bus_get_owner_kdbus(
344 sd_bus_creds **creds) {
346 _cleanup_bus_creds_unref_ sd_bus_creds *c = NULL;
347 struct kdbus_cmd_conn_info *cmd;
348 struct kdbus_conn_info *conn_info;
349 struct kdbus_item *item;
354 r = bus_kernel_parse_unique_name(name, &id);
358 size = offsetof(struct kdbus_cmd_conn_info, name);
362 size = offsetof(struct kdbus_cmd_conn_info, name) + strlen(name) + 1;
364 strcpy(cmd->name, name);
368 r = ioctl(bus->input_fd, KDBUS_CMD_CONN_INFO, cmd);
372 conn_info = (struct kdbus_conn_info *) ((uint8_t *) bus->kdbus_buffer + cmd->offset);
378 if (mask & SD_BUS_CREDS_UNIQUE_NAME) {
379 if (asprintf(&c->unique_name, ":1.%llu", (unsigned long long) conn_info->id) < 0)
382 c->mask |= SD_BUS_CREDS_UNIQUE_NAME;
385 KDBUS_PART_FOREACH(item, conn_info, items) {
387 switch (item->type) {
389 case KDBUS_ITEM_CREDS:
390 m = (SD_BUS_CREDS_UID | SD_BUS_CREDS_GID | SD_BUS_CREDS_PID |
391 SD_BUS_CREDS_TID | SD_BUS_CREDS_PID_STARTTIME) & mask;
394 c->uid = item->creds.uid;
395 c->pid = item->creds.pid;
396 c->gid = item->creds.gid;
397 c->tid = item->creds.tid;
398 c->pid_starttime = item->creds.starttime;
403 case KDBUS_ITEM_PID_COMM:
404 if (mask & SD_BUS_CREDS_COMM) {
405 c->comm = strdup(item->str);
411 c->mask |= SD_BUS_CREDS_COMM;
415 case KDBUS_ITEM_TID_COMM:
416 if (mask & SD_BUS_CREDS_TID_COMM) {
417 c->tid_comm = strdup(item->str);
423 c->mask |= SD_BUS_CREDS_TID_COMM;
428 if (mask & SD_BUS_CREDS_EXE) {
429 c->exe = strdup(item->str);
435 c->mask |= SD_BUS_CREDS_EXE;
439 case KDBUS_ITEM_CMDLINE:
440 if (mask & SD_BUS_CREDS_CMDLINE) {
441 c->cmdline_size = item->size - KDBUS_PART_HEADER_SIZE;
442 c->cmdline = memdup(item->data, c->cmdline_size);
448 c->mask |= SD_BUS_CREDS_CMDLINE;
452 case KDBUS_ITEM_CGROUP:
453 m = (SD_BUS_CREDS_CGROUP | SD_BUS_CREDS_UNIT |
454 SD_BUS_CREDS_USER_UNIT | SD_BUS_CREDS_SLICE |
455 SD_BUS_CREDS_SESSION | SD_BUS_CREDS_OWNER_UID) & mask;
458 c->cgroup = strdup(item->str);
468 case KDBUS_ITEM_CAPS:
469 m = (SD_BUS_CREDS_EFFECTIVE_CAPS | SD_BUS_CREDS_PERMITTED_CAPS |
470 SD_BUS_CREDS_INHERITABLE_CAPS | SD_BUS_CREDS_BOUNDING_CAPS) & mask;
473 c->capability_size = item->size - KDBUS_PART_HEADER_SIZE;
474 c->capability = memdup(item->data, c->capability_size);
475 if (!c->capability) {
484 case KDBUS_ITEM_SECLABEL:
485 if (mask & SD_BUS_CREDS_SELINUX_CONTEXT) {
486 c->label = strdup(item->str);
492 c->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
496 case KDBUS_ITEM_AUDIT:
497 m = (SD_BUS_CREDS_AUDIT_SESSION_ID | SD_BUS_CREDS_AUDIT_LOGIN_UID) & mask;
500 c->audit_session_id = item->audit.sessionid;
501 c->audit_login_uid = item->audit.loginuid;
506 case KDBUS_ITEM_NAMES:
507 if (mask & SD_BUS_CREDS_WELL_KNOWN_NAMES) {
508 c->well_known_names_size = item->size - KDBUS_PART_HEADER_SIZE;
509 c->well_known_names = memdup(item->data, c->well_known_names_size);
510 if (!c->well_known_names) {
515 c->mask |= SD_BUS_CREDS_WELL_KNOWN_NAMES;
529 ioctl(bus->input_fd, KDBUS_CMD_FREE, &cmd->offset);
533 static int bus_get_owner_dbus1(
537 sd_bus_creds **creds) {
539 _cleanup_bus_message_unref_ sd_bus_message *reply_unique = NULL, *reply = NULL;
540 _cleanup_bus_creds_unref_ sd_bus_creds *c = NULL;
541 const char *unique = NULL;
545 /* Only query the owner if the caller wants to know it or if
546 * the caller just wants to check whether a name exists */
547 if ((mask & SD_BUS_CREDS_UNIQUE_NAME) || mask == 0) {
548 r = sd_bus_call_method(
550 "org.freedesktop.DBus",
552 "org.freedesktop.DBus",
561 r = sd_bus_message_read(reply_unique, "s", &unique);
571 if ((mask & SD_BUS_CREDS_UNIQUE_NAME) && unique) {
572 c->unique_name = strdup(unique);
576 c->mask |= SD_BUS_CREDS_UNIQUE_NAME;
579 if (mask & (SD_BUS_CREDS_PID|SD_BUS_CREDS_PID_STARTTIME|SD_BUS_CREDS_GID|
580 SD_BUS_CREDS_COMM|SD_BUS_CREDS_EXE|SD_BUS_CREDS_CMDLINE|
581 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|
582 SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS|
583 SD_BUS_CREDS_AUDIT_SESSION_ID|SD_BUS_CREDS_AUDIT_LOGIN_UID)) {
586 r = sd_bus_call_method(
588 "org.freedesktop.DBus",
590 "org.freedesktop.DBus",
591 "GetConnectionUnixProcessID",
595 unique ? unique : name);
599 r = sd_bus_message_read(reply, "u", &u);
604 if (mask & SD_BUS_CREDS_PID) {
606 c->mask |= SD_BUS_CREDS_PID;
609 reply = sd_bus_message_unref(reply);
612 if (mask & SD_BUS_CREDS_UID) {
615 r = sd_bus_call_method(
617 "org.freedesktop.DBus",
619 "org.freedesktop.DBus",
620 "GetConnectionUnixUser",
624 unique ? unique : name);
628 r = sd_bus_message_read(reply, "u", &u);
633 c->mask |= SD_BUS_CREDS_UID;
635 reply = sd_bus_message_unref(reply);
638 if (mask & SD_BUS_CREDS_SELINUX_CONTEXT) {
642 r = sd_bus_call_method(
644 "org.freedesktop.DBus",
646 "org.freedesktop.DBus",
647 "GetConnectionSELinuxSecurityContext",
651 unique ? unique : name);
655 r = sd_bus_message_read_array(reply, 'y', &p, &sz);
659 c->label = strndup(p, sz);
663 c->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
666 r = bus_creds_add_more(c, mask, pid, 0);
679 _public_ int sd_bus_get_owner(
683 sd_bus_creds **creds) {
685 assert_return(bus, -EINVAL);
686 assert_return(name, -EINVAL);
687 assert_return(mask <= _SD_BUS_CREDS_ALL, -ENOTSUP);
688 assert_return(mask == 0 || creds, -EINVAL);
689 assert_return(BUS_IS_OPEN(bus->state), -ENOTCONN);
690 assert_return(!bus_pid_changed(bus), -ECHILD);
693 return bus_get_owner_kdbus(bus, name, mask, creds);
695 return bus_get_owner_dbus1(bus, name, mask, creds);
698 static int add_name_change_match(sd_bus *bus,
701 const char *old_owner,
702 const char *new_owner) {
704 uint64_t name_id = 0, old_owner_id = 0, new_owner_id = 0;
705 int is_name_id = -1, r;
706 struct kdbus_item *item;
710 /* If we encounter a match that could match against
711 * NameOwnerChanged messages, then we need to create
712 * KDBUS_MATCH_NAME_{ADD,REMOVE,CHANGE} and
713 * KDBUS_MATCH_ID_{ADD,REMOVE} matches for it, possibly
714 * multiple if the match is underspecified.
716 * The NameOwnerChanged signals take three parameters with
717 * unique or well-known names, but only some forms actually
720 * WELLKNOWN, "", UNIQUE → KDBUS_MATCH_NAME_ADD
721 * WELLKNOWN, UNIQUE, "" → KDBUS_MATCH_NAME_REMOVE
722 * WELLKNOWN, UNIQUE, UNIQUE → KDBUS_MATCH_NAME_CHANGE
723 * UNIQUE, "", UNIQUE → KDBUS_MATCH_ID_ADD
724 * UNIQUE, UNIQUE, "" → KDBUS_MATCH_ID_REMOVE
726 * For the latter two the two unique names must be identical.
731 is_name_id = bus_kernel_parse_unique_name(name, &name_id);
737 r = bus_kernel_parse_unique_name(old_owner, &old_owner_id);
742 if (is_name_id > 0 && old_owner_id != name_id)
747 r = bus_kernel_parse_unique_name(new_owner, &new_owner_id);
752 if (is_name_id > 0 && new_owner_id != name_id)
756 if (is_name_id <= 0) {
757 struct kdbus_cmd_match *m;
760 /* If the name argument is missing or is a well-known
761 * name, then add KDBUS_MATCH_NAME_{ADD,REMOVE,CHANGE}
764 l = name ? strlen(name) : 0;
766 sz = ALIGN8(offsetof(struct kdbus_cmd_match, items) +
767 offsetof(struct kdbus_item, name_change) +
768 offsetof(struct kdbus_notify_name_change, name) +
774 m->src_id = KDBUS_SRC_ID_KERNEL;
778 offsetof(struct kdbus_item, name_change) +
779 offsetof(struct kdbus_notify_name_change, name) +
782 item->name_change.old_id = old_owner_id;
783 item->name_change.new_id = new_owner_id;
786 strcpy(item->name_change.name, name);
788 /* If the old name is unset or empty, then
789 * this can match against added names */
790 if (!old_owner || old_owner[0] == 0) {
791 item->type = KDBUS_MATCH_NAME_ADD;
793 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
798 /* If the new name is unset or empty, then
799 * this can match against removed names */
800 if (!new_owner || new_owner[0] == 0) {
801 item->type = KDBUS_MATCH_NAME_REMOVE;
803 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
808 /* If the neither name is explicitly set to
809 * the empty string, then this can match
810 * agains changed names */
811 if (!(old_owner && old_owner[0] == 0) &&
812 !(new_owner && new_owner[0] == 0)) {
813 item->type = KDBUS_MATCH_NAME_CHANGE;
815 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
821 if (is_name_id != 0) {
822 struct kdbus_cmd_match *m;
825 /* If the name argument is missing or is a unique
826 * name, then add KDBUS_MATCH_ID_{ADD,REMOVE} matches
829 sz = ALIGN8(offsetof(struct kdbus_cmd_match, items) +
830 offsetof(struct kdbus_item, id_change) +
831 sizeof(struct kdbus_notify_id_change));
836 m->src_id = KDBUS_SRC_ID_KERNEL;
839 item->size = offsetof(struct kdbus_item, id_change) + sizeof(struct kdbus_notify_id_change);
840 item->id_change.id = name_id;
842 /* If the old name is unset or empty, then this can
843 * match against added ids */
844 if (!old_owner || old_owner[0] == 0) {
845 item->type = KDBUS_MATCH_ID_ADD;
847 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
852 /* If thew new name is unset or empty, then this can
853 match against removed ids */
854 if (!new_owner || new_owner[0] == 0) {
855 item->type = KDBUS_MATCH_ID_REMOVE;
857 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
866 static int bus_add_match_internal_kernel(
869 struct bus_match_component *components,
870 unsigned n_components,
873 struct kdbus_cmd_match *m;
874 struct kdbus_item *item;
875 uint64_t bloom[BLOOM_SIZE/8];
877 const char *sender = NULL;
878 size_t sender_length = 0;
879 uint64_t src_id = KDBUS_MATCH_SRC_ID_ANY;
880 bool using_bloom = false;
882 bool matches_name_change = true;
883 const char *name_change_arg[3] = {};
891 sz = offsetof(struct kdbus_cmd_match, items);
893 for (i = 0; i < n_components; i++) {
894 struct bus_match_component *c = &components[i];
898 case BUS_MATCH_SENDER:
899 if (!streq(c->value_str, "org.freedesktop.DBus"))
900 matches_name_change = false;
902 r = bus_kernel_parse_unique_name(c->value_str, &src_id);
907 sender = c->value_str;
908 sender_length = strlen(sender);
909 sz += ALIGN8(offsetof(struct kdbus_item, str) + sender_length + 1);
914 case BUS_MATCH_MESSAGE_TYPE:
915 if (c->value_u8 != SD_BUS_MESSAGE_SIGNAL)
916 matches_name_change = false;
918 bloom_add_pair(bloom, "message-type", bus_message_type_to_string(c->value_u8));
922 case BUS_MATCH_INTERFACE:
923 if (!streq(c->value_str, "org.freedesktop.DBus"))
924 matches_name_change = false;
926 bloom_add_pair(bloom, "interface", c->value_str);
930 case BUS_MATCH_MEMBER:
931 if (!streq(c->value_str, "NameOwnerChanged"))
932 matches_name_change = false;
934 bloom_add_pair(bloom, "member", c->value_str);
939 if (!streq(c->value_str, "/org/freedesktop/DBus"))
940 matches_name_change = false;
942 bloom_add_pair(bloom, "path", c->value_str);
946 case BUS_MATCH_PATH_NAMESPACE:
947 if (!streq(c->value_str, "/")) {
948 bloom_add_pair(bloom, "path-slash-prefix", c->value_str);
953 case BUS_MATCH_ARG...BUS_MATCH_ARG_LAST: {
954 char buf[sizeof("arg")-1 + 2 + 1];
956 if (c->type - BUS_MATCH_ARG < 3)
957 name_change_arg[c->type - BUS_MATCH_ARG] = c->value_str;
959 snprintf(buf, sizeof(buf), "arg%u", c->type - BUS_MATCH_ARG);
960 bloom_add_pair(bloom, buf, c->value_str);
965 case BUS_MATCH_ARG_PATH...BUS_MATCH_ARG_PATH_LAST: {
966 char buf[sizeof("arg")-1 + 2 + sizeof("-slash-prefix")];
968 snprintf(buf, sizeof(buf), "arg%u-slash-prefix", c->type - BUS_MATCH_ARG_PATH);
969 bloom_add_pair(bloom, buf, c->value_str);
974 case BUS_MATCH_ARG_NAMESPACE...BUS_MATCH_ARG_NAMESPACE_LAST: {
975 char buf[sizeof("arg")-1 + 2 + sizeof("-dot-prefix")];
977 snprintf(buf, sizeof(buf), "arg%u-dot-prefix", c->type - BUS_MATCH_ARG_NAMESPACE);
978 bloom_add_pair(bloom, buf, c->value_str);
983 case BUS_MATCH_DESTINATION:
984 /* The bloom filter does not include
985 the destination, since it is only
986 available for broadcast messages
987 which do not carry a destination
988 since they are undirected. */
992 case BUS_MATCH_VALUE:
994 case _BUS_MATCH_NODE_TYPE_MAX:
995 case _BUS_MATCH_NODE_TYPE_INVALID:
996 assert_not_reached("Invalid match type?");
1001 sz += ALIGN8(offsetof(struct kdbus_item, data64) + BLOOM_SIZE);
1011 item->size = offsetof(struct kdbus_item, data64) + BLOOM_SIZE;
1012 item->type = KDBUS_MATCH_BLOOM;
1013 memcpy(item->data64, bloom, BLOOM_SIZE);
1015 item = KDBUS_PART_NEXT(item);
1019 item->size = offsetof(struct kdbus_item, str) + sender_length + 1;
1020 item->type = KDBUS_MATCH_SRC_NAME;
1021 memcpy(item->str, sender, sender_length + 1);
1024 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_ADD, m);
1028 if (matches_name_change) {
1030 /* If this match could theoretically match
1031 * NameOwnerChanged messages, we need to
1032 * install a second non-bloom filter explitly
1035 r = add_name_change_match(bus, cookie, name_change_arg[0], name_change_arg[1], name_change_arg[2]);
1043 static int bus_add_match_internal_dbus1(
1045 const char *match) {
1050 return sd_bus_call_method(
1052 "org.freedesktop.DBus",
1054 "org.freedesktop.DBus",
1062 int bus_add_match_internal(
1065 struct bus_match_component *components,
1066 unsigned n_components,
1073 return bus_add_match_internal_kernel(bus, match, components, n_components, cookie);
1075 return bus_add_match_internal_dbus1(bus, match);
1078 static int bus_remove_match_internal_kernel(
1083 struct kdbus_cmd_match m;
1090 m.size = offsetof(struct kdbus_cmd_match, items);
1093 r = ioctl(bus->input_fd, KDBUS_CMD_MATCH_REMOVE, &m);
1100 static int bus_remove_match_internal_dbus1(
1102 const char *match) {
1107 return sd_bus_call_method(
1109 "org.freedesktop.DBus",
1111 "org.freedesktop.DBus",
1119 int bus_remove_match_internal(
1128 return bus_remove_match_internal_kernel(bus, match, cookie);
1130 return bus_remove_match_internal_dbus1(bus, match);
1133 _public_ int sd_bus_get_owner_machine_id(sd_bus *bus, const char *name, sd_id128_t *machine) {
1134 _cleanup_bus_message_unref_ sd_bus_message *reply = NULL, *m = NULL;
1138 assert_return(bus, -EINVAL);
1139 assert_return(name, -EINVAL);
1140 assert_return(machine, -EINVAL);
1141 assert_return(BUS_IS_OPEN(bus->state), -ENOTCONN);
1142 assert_return(!bus_pid_changed(bus), -ECHILD);
1144 if (streq_ptr(name, bus->unique_name))
1145 return sd_id128_get_machine(machine);
1147 r = sd_bus_message_new_method_call(
1151 "org.freedesktop.DBus.Peer",
1152 "GetMachineId", &m);
1156 r = sd_bus_message_set_no_auto_start(m, true);
1160 r = sd_bus_call(bus, m, 0, NULL, &reply);
1164 r = sd_bus_message_read(reply, "s", &mid);
1168 return sd_id128_from_string(mid, machine);