2 This file is part of systemd.
4 Copyright 2014 Daniel Mack
6 systemd is free software; you can redistribute it and/or modify it
7 under the terms of the GNU Lesser General Public License as published by
8 the Free Software Foundation; either version 2.1 of the License, or
9 (at your option) any later version.
11 systemd is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Lesser General Public License for more details.
16 You should have received a copy of the GNU Lesser General Public License
17 along with systemd; If not, see <http://www.gnu.org/licenses/>.
24 #include "bus-kernel.h"
25 #include "bus-policy.h"
27 int bus_kernel_translate_access(BusPolicyAccess access) {
29 assert(access < _BUS_POLICY_ACCESS_MAX);
33 case BUS_POLICY_ACCESS_SEE:
34 return KDBUS_POLICY_SEE;
36 case BUS_POLICY_ACCESS_TALK:
37 return KDBUS_POLICY_TALK;
39 case BUS_POLICY_ACCESS_OWN:
40 return KDBUS_POLICY_OWN;
43 assert_not_reached("Unknown policy access");
47 int bus_kernel_translate_policy(const BusNamePolicy *policy, struct kdbus_item *item) {
53 switch (policy->type) {
55 case BUSNAME_POLICY_TYPE_USER: {
56 const char *user = policy->name;
59 r = get_user_creds(&user, &uid, NULL, NULL, NULL);
63 item->policy_access.type = KDBUS_POLICY_ACCESS_USER;
64 item->policy_access.id = uid;
68 case BUSNAME_POLICY_TYPE_GROUP: {
69 const char *group = policy->name;
72 r = get_group_creds(&group, &gid);
76 item->policy_access.type = KDBUS_POLICY_ACCESS_GROUP;
77 item->policy_access.id = gid;
82 assert_not_reached("Unknown policy type");
85 item->policy_access.access = bus_kernel_translate_access(policy->access);
90 int bus_kernel_make_starter(
95 BusNamePolicy *policy,
96 BusPolicyAccess world_policy) {
98 struct kdbus_cmd_free cmd_free = { .size = sizeof(cmd_free) };
99 struct kdbus_cmd_hello *hello;
100 struct kdbus_item *n;
101 size_t policy_cnt = 0;
109 LIST_FOREACH(policy, po, policy)
112 if (world_policy >= 0)
115 size = offsetof(struct kdbus_cmd_hello, items) +
116 ALIGN8(offsetof(struct kdbus_item, str) + strlen(name) + 1) +
117 policy_cnt * ALIGN8(offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access));
119 hello = alloca0_align(size, 8);
122 strcpy(n->str, name);
123 n->size = offsetof(struct kdbus_item, str) + strlen(n->str) + 1;
124 n->type = KDBUS_ITEM_NAME;
125 n = KDBUS_ITEM_NEXT(n);
127 LIST_FOREACH(policy, po, policy) {
128 n->type = KDBUS_ITEM_POLICY_ACCESS;
129 n->size = offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access);
131 r = bus_kernel_translate_policy(po, n);
135 n = KDBUS_ITEM_NEXT(n);
138 if (world_policy >= 0) {
139 n->type = KDBUS_ITEM_POLICY_ACCESS;
140 n->size = offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access);
141 n->policy_access.type = KDBUS_POLICY_ACCESS_WORLD;
142 n->policy_access.access = bus_kernel_translate_access(world_policy);
147 (activating ? KDBUS_HELLO_ACTIVATOR : KDBUS_HELLO_POLICY_HOLDER) |
148 (accept_fd ? KDBUS_HELLO_ACCEPT_FD : 0);
149 hello->pool_size = KDBUS_POOL_SIZE;
150 hello->attach_flags_send = _KDBUS_ATTACH_ANY;
151 hello->attach_flags_recv = _KDBUS_ATTACH_ANY;
153 if (ioctl(fd, KDBUS_CMD_HELLO, hello) < 0)
156 /* not interested in any output values */
157 cmd_free.offset = hello->offset;
158 (void) ioctl(fd, KDBUS_CMD_FREE, &cmd_free);
160 /* The higher 32bit of the bus_flags fields are considered
161 * 'incompatible flags'. Refuse them all for now. */
162 if (hello->bus_flags > 0xFFFFFFFFULL)
168 static const char* const bus_policy_access_table[_BUS_POLICY_ACCESS_MAX] = {
169 [BUS_POLICY_ACCESS_SEE] = "see",
170 [BUS_POLICY_ACCESS_TALK] = "talk",
171 [BUS_POLICY_ACCESS_OWN] = "own",
174 DEFINE_STRING_TABLE_LOOKUP(bus_policy_access, BusPolicyAccess);