2013-11-28 17:50:02 +01:00
|
|
|
/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
|
|
|
|
|
|
|
|
/***
|
|
|
|
This file is part of systemd.
|
|
|
|
|
|
|
|
Copyright 2013 Lennart Poettering
|
|
|
|
|
|
|
|
systemd is free software; you can redistribute it and/or modify it
|
|
|
|
under the terms of the GNU Lesser General Public License as published by
|
|
|
|
the Free Software Foundation; either version 2.1 of the License, or
|
|
|
|
(at your option) any later version.
|
|
|
|
|
|
|
|
systemd is distributed in the hope that it will be useful, but
|
|
|
|
WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
Lesser General Public License for more details.
|
|
|
|
|
|
|
|
You should have received a copy of the GNU Lesser General Public License
|
|
|
|
along with systemd; If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
***/
|
|
|
|
|
|
|
|
#include <stdlib.h>
|
2014-12-30 09:09:41 +01:00
|
|
|
#include <linux/capability.h>
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
#include "util.h"
|
2015-04-10 20:43:52 +02:00
|
|
|
#include "formats-util.h"
|
2015-04-10 19:10:00 +02:00
|
|
|
#include "process-util.h"
|
2015-04-23 19:43:40 +02:00
|
|
|
#include "terminal-util.h"
|
2014-12-30 08:42:53 +01:00
|
|
|
#include "capability.h"
|
2013-11-28 17:50:02 +01:00
|
|
|
#include "cgroup-util.h"
|
|
|
|
#include "fileio.h"
|
|
|
|
#include "audit.h"
|
|
|
|
#include "bus-message.h"
|
2015-08-27 16:32:22 +02:00
|
|
|
#include "bus-util.h"
|
2013-11-30 04:14:10 +01:00
|
|
|
#include "strv.h"
|
2013-11-28 17:50:02 +01:00
|
|
|
#include "bus-creds.h"
|
2014-03-11 19:03:50 +01:00
|
|
|
#include "bus-label.h"
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
enum {
|
|
|
|
CAP_OFFSET_INHERITABLE = 0,
|
|
|
|
CAP_OFFSET_PERMITTED = 1,
|
|
|
|
CAP_OFFSET_EFFECTIVE = 2,
|
|
|
|
CAP_OFFSET_BOUNDING = 3
|
|
|
|
};
|
|
|
|
|
|
|
|
void bus_creds_done(sd_bus_creds *c) {
|
|
|
|
assert(c);
|
|
|
|
|
|
|
|
/* For internal bus cred structures that are allocated by
|
|
|
|
* something else */
|
|
|
|
|
|
|
|
free(c->session);
|
|
|
|
free(c->unit);
|
|
|
|
free(c->user_unit);
|
|
|
|
free(c->slice);
|
2015-04-30 11:58:06 +02:00
|
|
|
free(c->user_slice);
|
2014-11-04 16:13:49 +01:00
|
|
|
free(c->unescaped_description);
|
2015-03-02 11:36:35 +01:00
|
|
|
free(c->supplementary_gids);
|
2015-04-23 19:43:40 +02:00
|
|
|
free(c->tty);
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2014-11-27 02:28:23 +01:00
|
|
|
free(c->well_known_names); /* note that this is an strv, but
|
|
|
|
* we only free the array, not the
|
|
|
|
* strings the array points to. The
|
|
|
|
* full strv we only free if
|
|
|
|
* c->allocated is set, see
|
|
|
|
* below. */
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
strv_free(c->cmdline_array);
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
_public_ sd_bus_creds *sd_bus_creds_ref(sd_bus_creds *c) {
|
|
|
|
assert_return(c, NULL);
|
|
|
|
|
|
|
|
if (c->allocated) {
|
|
|
|
assert(c->n_ref > 0);
|
|
|
|
c->n_ref++;
|
|
|
|
} else {
|
|
|
|
sd_bus_message *m;
|
|
|
|
|
|
|
|
/* If this is an embedded creds structure, then
|
|
|
|
* forward ref counting to the message */
|
|
|
|
m = container_of(c, sd_bus_message, creds);
|
|
|
|
sd_bus_message_ref(m);
|
|
|
|
}
|
|
|
|
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ sd_bus_creds *sd_bus_creds_unref(sd_bus_creds *c) {
|
2013-12-10 21:38:04 +01:00
|
|
|
|
|
|
|
if (!c)
|
|
|
|
return NULL;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
if (c->allocated) {
|
|
|
|
assert(c->n_ref > 0);
|
|
|
|
c->n_ref--;
|
|
|
|
|
|
|
|
if (c->n_ref == 0) {
|
|
|
|
free(c->comm);
|
|
|
|
free(c->tid_comm);
|
|
|
|
free(c->exe);
|
|
|
|
free(c->cmdline);
|
|
|
|
free(c->cgroup);
|
|
|
|
free(c->capability);
|
|
|
|
free(c->label);
|
2013-11-30 04:14:10 +01:00
|
|
|
free(c->unique_name);
|
2013-12-24 19:31:44 +01:00
|
|
|
free(c->cgroup_root);
|
2014-11-04 16:13:49 +01:00
|
|
|
free(c->description);
|
2015-03-02 11:36:35 +01:00
|
|
|
|
2015-09-08 18:43:11 +02:00
|
|
|
c->supplementary_gids = mfree(c->supplementary_gids);
|
2014-11-27 02:28:23 +01:00
|
|
|
|
2015-09-09 23:05:10 +02:00
|
|
|
c->well_known_names = strv_free(c->well_known_names);
|
2014-11-27 02:28:23 +01:00
|
|
|
|
|
|
|
bus_creds_done(c);
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
free(c);
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
sd_bus_message *m;
|
|
|
|
|
|
|
|
m = container_of(c, sd_bus_message, creds);
|
|
|
|
sd_bus_message_unref(m);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2014-01-05 01:28:52 +01:00
|
|
|
_public_ uint64_t sd_bus_creds_get_mask(const sd_bus_creds *c) {
|
2013-11-28 17:50:02 +01:00
|
|
|
assert_return(c, 0);
|
|
|
|
|
|
|
|
return c->mask;
|
|
|
|
}
|
|
|
|
|
2015-04-21 00:58:08 +02:00
|
|
|
_public_ uint64_t sd_bus_creds_get_augmented_mask(const sd_bus_creds *c) {
|
|
|
|
assert_return(c, 0);
|
|
|
|
|
|
|
|
return c->augmented;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
sd_bus_creds* bus_creds_new(void) {
|
|
|
|
sd_bus_creds *c;
|
|
|
|
|
|
|
|
c = new0(sd_bus_creds, 1);
|
|
|
|
if (!c)
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
c->allocated = true;
|
|
|
|
c->n_ref = 1;
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
|
2014-02-19 23:54:58 +01:00
|
|
|
_public_ int sd_bus_creds_new_from_pid(sd_bus_creds **ret, pid_t pid, uint64_t mask) {
|
2013-11-28 17:50:02 +01:00
|
|
|
sd_bus_creds *c;
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(pid >= 0, -EINVAL);
|
2015-03-13 14:08:00 +01:00
|
|
|
assert_return(mask <= _SD_BUS_CREDS_ALL, -EOPNOTSUPP);
|
2013-11-28 17:50:02 +01:00
|
|
|
assert_return(ret, -EINVAL);
|
|
|
|
|
|
|
|
if (pid == 0)
|
|
|
|
pid = getpid();
|
|
|
|
|
|
|
|
c = bus_creds_new();
|
|
|
|
if (!c)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
r = bus_creds_add_more(c, mask | SD_BUS_CREDS_AUGMENT, pid, 0);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0) {
|
2014-01-01 04:45:45 +01:00
|
|
|
sd_bus_creds_unref(c);
|
2013-11-28 17:50:02 +01:00
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Check if the process existed at all, in case we haven't
|
|
|
|
* figured that out already */
|
2014-02-17 18:28:53 +01:00
|
|
|
if (!pid_is_alive(pid)) {
|
2013-11-28 17:50:02 +01:00
|
|
|
sd_bus_creds_unref(c);
|
|
|
|
return -ESRCH;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_uid(sd_bus_creds *c, uid_t *uid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(uid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_UID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
*uid = c->uid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
_public_ int sd_bus_creds_get_euid(sd_bus_creds *c, uid_t *euid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(euid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_EUID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*euid = c->euid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_suid(sd_bus_creds *c, uid_t *suid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(suid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SUID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*suid = c->suid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_fsuid(sd_bus_creds *c, uid_t *fsuid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(fsuid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_FSUID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*fsuid = c->fsuid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
_public_ int sd_bus_creds_get_gid(sd_bus_creds *c, gid_t *gid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(gid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
2015-01-23 02:59:30 +01:00
|
|
|
if (!(c->mask & SD_BUS_CREDS_GID))
|
2013-12-12 00:20:11 +01:00
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
*gid = c->gid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
_public_ int sd_bus_creds_get_egid(sd_bus_creds *c, gid_t *egid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(egid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_EGID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*egid = c->egid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_sgid(sd_bus_creds *c, gid_t *sgid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(sgid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SGID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*sgid = c->sgid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_fsgid(sd_bus_creds *c, gid_t *fsgid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(fsgid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_FSGID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*fsgid = c->fsgid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2014-11-25 13:21:23 +01:00
|
|
|
_public_ int sd_bus_creds_get_supplementary_gids(sd_bus_creds *c, const gid_t **gids) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(gids, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SUPPLEMENTARY_GIDS))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
*gids = c->supplementary_gids;
|
|
|
|
return (int) c->n_supplementary_gids;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
_public_ int sd_bus_creds_get_pid(sd_bus_creds *c, pid_t *pid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(pid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_PID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->pid > 0);
|
|
|
|
*pid = c->pid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2015-04-21 20:58:09 +02:00
|
|
|
_public_ int sd_bus_creds_get_ppid(sd_bus_creds *c, pid_t *ppid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ppid, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_PPID))
|
|
|
|
return -ENODATA;
|
|
|
|
|
2015-05-26 19:17:30 +02:00
|
|
|
/* PID 1 has no parent process. Let's distinguish the case of
|
2015-04-29 21:40:54 +02:00
|
|
|
* not knowing and not having a parent process by the returned
|
|
|
|
* error code. */
|
|
|
|
if (c->ppid == 0)
|
|
|
|
return -ENXIO;
|
|
|
|
|
2015-04-21 20:58:09 +02:00
|
|
|
*ppid = c->ppid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
_public_ int sd_bus_creds_get_tid(sd_bus_creds *c, pid_t *tid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(tid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_TID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->tid > 0);
|
|
|
|
*tid = c->tid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_selinux_context(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SELINUX_CONTEXT))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->label);
|
|
|
|
*ret = c->label;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_comm(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_COMM))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->comm);
|
|
|
|
*ret = c->comm;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_tid_comm(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_TID_COMM))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->tid_comm);
|
|
|
|
*ret = c->tid_comm;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_exe(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_EXE))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
if (!c->exe)
|
|
|
|
return -ENXIO;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
*ret = c->exe;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_cgroup(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_CGROUP))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
*ret = c->cgroup;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_unit(sd_bus_creds *c, const char **ret) {
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_UNIT))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
|
|
|
if (!c->unit) {
|
2013-12-24 19:31:44 +01:00
|
|
|
const char *shifted;
|
|
|
|
|
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
r = cg_path_get_unit(shifted, (char**) &c->unit);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c->unit;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_user_unit(sd_bus_creds *c, const char **ret) {
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_USER_UNIT))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
|
|
|
if (!c->user_unit) {
|
2013-12-24 19:31:44 +01:00
|
|
|
const char *shifted;
|
|
|
|
|
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
r = cg_path_get_user_unit(shifted, (char**) &c->user_unit);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c->user_unit;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_slice(sd_bus_creds *c, const char **ret) {
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SLICE))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
|
|
|
if (!c->slice) {
|
2013-12-24 19:31:44 +01:00
|
|
|
const char *shifted;
|
|
|
|
|
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
r = cg_path_get_slice(shifted, (char**) &c->slice);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c->slice;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2015-04-30 11:58:06 +02:00
|
|
|
_public_ int sd_bus_creds_get_user_slice(sd_bus_creds *c, const char **ret) {
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_USER_SLICE))
|
|
|
|
return -ENODATA;
|
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
|
|
|
if (!c->user_slice) {
|
|
|
|
const char *shifted;
|
|
|
|
|
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
r = cg_path_get_user_slice(shifted, (char**) &c->user_slice);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c->user_slice;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
_public_ int sd_bus_creds_get_session(sd_bus_creds *c, const char **ret) {
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_SESSION))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
|
|
|
if (!c->session) {
|
2013-12-24 19:31:44 +01:00
|
|
|
const char *shifted;
|
|
|
|
|
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
r = cg_path_get_session(shifted, (char**) &c->session);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
*ret = c->session;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_owner_uid(sd_bus_creds *c, uid_t *uid) {
|
2013-12-24 19:31:44 +01:00
|
|
|
const char *shifted;
|
|
|
|
int r;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(uid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_OWNER_UID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c->cgroup);
|
|
|
|
|
2013-12-24 19:31:44 +01:00
|
|
|
r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
return cg_path_get_owner_uid(shifted, uid);
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_cmdline(sd_bus_creds *c, char ***cmdline) {
|
|
|
|
assert_return(c, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_CMDLINE))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
if (!c->cmdline)
|
|
|
|
return -ENXIO;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
if (!c->cmdline_array) {
|
|
|
|
c->cmdline_array = strv_parse_nulstr(c->cmdline, c->cmdline_size);
|
|
|
|
if (!c->cmdline_array)
|
|
|
|
return -ENOMEM;
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
*cmdline = c->cmdline_array;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_audit_session_id(sd_bus_creds *c, uint32_t *sessionid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(sessionid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_AUDIT_SESSION_ID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
if (c->audit_session_id == AUDIT_SESSION_INVALID)
|
|
|
|
return -ENXIO;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
*sessionid = c->audit_session_id;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_audit_login_uid(sd_bus_creds *c, uid_t *uid) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(uid, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_AUDIT_LOGIN_UID))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
if (c->audit_login_uid == UID_INVALID)
|
|
|
|
return -ENXIO;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
*uid = c->audit_login_uid;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2015-04-23 19:43:40 +02:00
|
|
|
_public_ int sd_bus_creds_get_tty(sd_bus_creds *c, const char **ret) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_TTY))
|
|
|
|
return -ENODATA;
|
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
if (!c->tty)
|
|
|
|
return -ENXIO;
|
|
|
|
|
2015-04-23 19:43:40 +02:00
|
|
|
*ret = c->tty;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
_public_ int sd_bus_creds_get_unique_name(sd_bus_creds *c, const char **unique_name) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(unique_name, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_UNIQUE_NAME))
|
|
|
|
return -ENODATA;
|
2013-11-30 04:14:10 +01:00
|
|
|
|
|
|
|
*unique_name = c->unique_name;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_get_well_known_names(sd_bus_creds *c, char ***well_known_names) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(well_known_names, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_WELL_KNOWN_NAMES))
|
|
|
|
return -ENODATA;
|
2013-11-30 04:14:10 +01:00
|
|
|
|
2014-11-27 02:37:05 +01:00
|
|
|
/* As a special hack we return the bus driver as well-known
|
|
|
|
* names list when this is requested. */
|
|
|
|
if (c->well_known_names_driver) {
|
|
|
|
static const char* const wkn[] = {
|
|
|
|
"org.freedesktop.DBus",
|
|
|
|
NULL
|
|
|
|
};
|
|
|
|
|
|
|
|
*well_known_names = (char**) wkn;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2014-11-27 12:52:13 +01:00
|
|
|
if (c->well_known_names_local) {
|
|
|
|
static const char* const wkn[] = {
|
|
|
|
"org.freedesktop.DBus.Local",
|
|
|
|
NULL
|
|
|
|
};
|
|
|
|
|
|
|
|
*well_known_names = (char**) wkn;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-12-04 23:36:02 +01:00
|
|
|
*well_known_names = c->well_known_names;
|
2013-11-30 04:14:10 +01:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2014-11-04 16:13:49 +01:00
|
|
|
_public_ int sd_bus_creds_get_description(sd_bus_creds *c, const char **ret) {
|
2014-01-22 16:28:58 +01:00
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(ret, -EINVAL);
|
|
|
|
|
2014-11-04 16:13:49 +01:00
|
|
|
if (!(c->mask & SD_BUS_CREDS_DESCRIPTION))
|
2014-01-22 16:28:58 +01:00
|
|
|
return -ENODATA;
|
|
|
|
|
2014-11-04 16:13:49 +01:00
|
|
|
assert(c->description);
|
2014-01-22 18:45:38 +01:00
|
|
|
|
2014-11-04 16:13:49 +01:00
|
|
|
if (!c->unescaped_description) {
|
|
|
|
c->unescaped_description = bus_label_unescape(c->description);
|
|
|
|
if (!c->unescaped_description)
|
2014-01-22 18:45:38 +01:00
|
|
|
return -ENOMEM;
|
|
|
|
}
|
|
|
|
|
2014-11-04 16:13:49 +01:00
|
|
|
*ret = c->unescaped_description;
|
2014-01-22 16:28:58 +01:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
static int has_cap(sd_bus_creds *c, unsigned offset, int capability) {
|
|
|
|
size_t sz;
|
|
|
|
|
|
|
|
assert(c);
|
2014-12-30 08:42:53 +01:00
|
|
|
assert(capability >= 0);
|
2013-11-28 17:50:02 +01:00
|
|
|
assert(c->capability);
|
|
|
|
|
2015-04-21 00:50:43 +02:00
|
|
|
if ((unsigned) capability > cap_last_cap())
|
2013-11-28 17:50:02 +01:00
|
|
|
return 0;
|
|
|
|
|
2015-04-21 00:50:43 +02:00
|
|
|
sz = DIV_ROUND_UP(cap_last_cap(), 32U);
|
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
return !!(c->capability[offset * sz + CAP_TO_INDEX(capability)] & CAP_TO_MASK(capability));
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_has_effective_cap(sd_bus_creds *c, int capability) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(capability >= 0, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_EFFECTIVE_CAPS))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
return has_cap(c, CAP_OFFSET_EFFECTIVE, capability);
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_has_permitted_cap(sd_bus_creds *c, int capability) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(capability >= 0, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_PERMITTED_CAPS))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
return has_cap(c, CAP_OFFSET_PERMITTED, capability);
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_has_inheritable_cap(sd_bus_creds *c, int capability) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(capability >= 0, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_INHERITABLE_CAPS))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
return has_cap(c, CAP_OFFSET_INHERITABLE, capability);
|
|
|
|
}
|
|
|
|
|
|
|
|
_public_ int sd_bus_creds_has_bounding_cap(sd_bus_creds *c, int capability) {
|
|
|
|
assert_return(c, -EINVAL);
|
|
|
|
assert_return(capability >= 0, -EINVAL);
|
2013-12-12 00:20:11 +01:00
|
|
|
|
|
|
|
if (!(c->mask & SD_BUS_CREDS_BOUNDING_CAPS))
|
|
|
|
return -ENODATA;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
return has_cap(c, CAP_OFFSET_BOUNDING, capability);
|
|
|
|
}
|
|
|
|
|
|
|
|
static int parse_caps(sd_bus_creds *c, unsigned offset, const char *p) {
|
2014-12-30 08:42:53 +01:00
|
|
|
size_t sz, max;
|
2014-12-30 09:09:41 +01:00
|
|
|
unsigned i, j;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
assert(c);
|
|
|
|
assert(p);
|
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
max = DIV_ROUND_UP(cap_last_cap(), 32U);
|
2013-11-28 17:50:02 +01:00
|
|
|
p += strspn(p, WHITESPACE);
|
|
|
|
|
|
|
|
sz = strlen(p);
|
2014-12-30 09:09:41 +01:00
|
|
|
if (sz % 8 != 0)
|
2013-11-28 17:50:02 +01:00
|
|
|
return -EINVAL;
|
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
sz /= 8;
|
2014-12-30 08:42:53 +01:00
|
|
|
if (sz > max)
|
|
|
|
return -EINVAL;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
if (!c->capability) {
|
2014-12-30 09:09:41 +01:00
|
|
|
c->capability = new0(uint32_t, max * 4);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (!c->capability)
|
|
|
|
return -ENOMEM;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (i = 0; i < sz; i ++) {
|
2014-12-30 09:09:41 +01:00
|
|
|
uint32_t v = 0;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
for (j = 0; j < 8; ++j) {
|
|
|
|
int t;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
t = unhexchar(*p++);
|
|
|
|
if (t < 0)
|
|
|
|
return -EINVAL;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2014-12-30 09:09:41 +01:00
|
|
|
v = (v << 4) | t;
|
|
|
|
}
|
|
|
|
|
|
|
|
c->capability[offset * max + (sz - i - 1)] = v;
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
int bus_creds_add_more(sd_bus_creds *c, uint64_t mask, pid_t pid, pid_t tid) {
|
|
|
|
uint64_t missing;
|
|
|
|
int r;
|
|
|
|
|
|
|
|
assert(c);
|
|
|
|
assert(c->allocated);
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (!(mask & SD_BUS_CREDS_AUGMENT))
|
|
|
|
return 0;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
/* Try to retrieve PID from creds if it wasn't passed to us */
|
2015-05-25 02:20:06 +02:00
|
|
|
if (pid > 0) {
|
|
|
|
c->pid = pid;
|
|
|
|
c->mask |= SD_BUS_CREDS_PID;
|
|
|
|
} else if (c->mask & SD_BUS_CREDS_PID)
|
2013-11-28 17:50:02 +01:00
|
|
|
pid = c->pid;
|
2015-05-25 02:20:06 +02:00
|
|
|
else
|
|
|
|
/* Without pid we cannot do much... */
|
2013-11-28 17:50:02 +01:00
|
|
|
return 0;
|
|
|
|
|
2015-04-21 00:58:08 +02:00
|
|
|
/* Try to retrieve TID from creds if it wasn't passed to us */
|
|
|
|
if (tid <= 0 && (c->mask & SD_BUS_CREDS_TID))
|
|
|
|
tid = c->tid;
|
|
|
|
|
|
|
|
/* Calculate what we shall and can add */
|
|
|
|
missing = mask & ~(c->mask|SD_BUS_CREDS_PID|SD_BUS_CREDS_TID|SD_BUS_CREDS_UNIQUE_NAME|SD_BUS_CREDS_WELL_KNOWN_NAMES|SD_BUS_CREDS_DESCRIPTION|SD_BUS_CREDS_AUGMENT);
|
|
|
|
if (missing == 0)
|
|
|
|
return 0;
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (tid > 0) {
|
|
|
|
c->tid = tid;
|
|
|
|
c->mask |= SD_BUS_CREDS_TID;
|
|
|
|
}
|
|
|
|
|
2015-04-21 20:58:09 +02:00
|
|
|
if (missing & (SD_BUS_CREDS_PPID |
|
|
|
|
SD_BUS_CREDS_UID | SD_BUS_CREDS_EUID | SD_BUS_CREDS_SUID | SD_BUS_CREDS_FSUID |
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
SD_BUS_CREDS_GID | SD_BUS_CREDS_EGID | SD_BUS_CREDS_SGID | SD_BUS_CREDS_FSGID |
|
2014-11-25 13:21:23 +01:00
|
|
|
SD_BUS_CREDS_SUPPLEMENTARY_GIDS |
|
2013-11-28 17:50:02 +01:00
|
|
|
SD_BUS_CREDS_EFFECTIVE_CAPS | SD_BUS_CREDS_INHERITABLE_CAPS |
|
|
|
|
SD_BUS_CREDS_PERMITTED_CAPS | SD_BUS_CREDS_BOUNDING_CAPS)) {
|
|
|
|
|
|
|
|
_cleanup_fclose_ FILE *f = NULL;
|
|
|
|
const char *p;
|
|
|
|
|
|
|
|
p = procfs_file_alloca(pid, "status");
|
|
|
|
|
|
|
|
f = fopen(p, "re");
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (!f) {
|
|
|
|
if (errno == ENOENT)
|
|
|
|
return -ESRCH;
|
|
|
|
else if (errno != EPERM && errno != EACCES)
|
|
|
|
return -errno;
|
|
|
|
} else {
|
|
|
|
char line[LINE_MAX];
|
|
|
|
|
|
|
|
FOREACH_LINE(line, f, return -errno) {
|
|
|
|
truncate_nl(line);
|
|
|
|
|
2015-04-21 20:58:09 +02:00
|
|
|
if (missing & SD_BUS_CREDS_PPID) {
|
|
|
|
p = startswith(line, "PPid:");
|
|
|
|
if (p) {
|
|
|
|
p += strspn(p, WHITESPACE);
|
|
|
|
|
2015-04-22 13:27:29 +02:00
|
|
|
/* Explicitly check for PPID 0 (which is the case for PID 1) */
|
|
|
|
if (!streq(p, "0")) {
|
|
|
|
r = parse_pid(p, &c->ppid);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
} else
|
|
|
|
c->ppid = 0;
|
|
|
|
|
|
|
|
c->mask |= SD_BUS_CREDS_PPID;
|
2015-04-21 20:58:09 +02:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & (SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_SUID|SD_BUS_CREDS_FSUID)) {
|
|
|
|
p = startswith(line, "Uid:");
|
|
|
|
if (p) {
|
|
|
|
unsigned long uid, euid, suid, fsuid;
|
|
|
|
|
|
|
|
p += strspn(p, WHITESPACE);
|
|
|
|
if (sscanf(p, "%lu %lu %lu %lu", &uid, &euid, &suid, &fsuid) != 4)
|
|
|
|
return -EIO;
|
|
|
|
|
2015-04-21 00:52:24 +02:00
|
|
|
if (missing & SD_BUS_CREDS_UID)
|
|
|
|
c->uid = (uid_t) uid;
|
|
|
|
if (missing & SD_BUS_CREDS_EUID)
|
|
|
|
c->euid = (uid_t) euid;
|
|
|
|
if (missing & SD_BUS_CREDS_SUID)
|
|
|
|
c->suid = (uid_t) suid;
|
|
|
|
if (missing & SD_BUS_CREDS_FSUID)
|
|
|
|
c->fsuid = (uid_t) fsuid;
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= missing & (SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_SUID|SD_BUS_CREDS_FSUID);
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & (SD_BUS_CREDS_GID|SD_BUS_CREDS_EGID|SD_BUS_CREDS_SGID|SD_BUS_CREDS_FSGID)) {
|
|
|
|
p = startswith(line, "Gid:");
|
|
|
|
if (p) {
|
|
|
|
unsigned long gid, egid, sgid, fsgid;
|
|
|
|
|
|
|
|
p += strspn(p, WHITESPACE);
|
|
|
|
if (sscanf(p, "%lu %lu %lu %lu", &gid, &egid, &sgid, &fsgid) != 4)
|
|
|
|
return -EIO;
|
|
|
|
|
2015-04-21 00:52:24 +02:00
|
|
|
if (missing & SD_BUS_CREDS_GID)
|
|
|
|
c->gid = (gid_t) gid;
|
|
|
|
if (missing & SD_BUS_CREDS_EGID)
|
|
|
|
c->egid = (gid_t) egid;
|
|
|
|
if (missing & SD_BUS_CREDS_SGID)
|
|
|
|
c->sgid = (gid_t) sgid;
|
|
|
|
if (missing & SD_BUS_CREDS_FSGID)
|
|
|
|
c->fsgid = (gid_t) fsgid;
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= missing & (SD_BUS_CREDS_GID|SD_BUS_CREDS_EGID|SD_BUS_CREDS_SGID|SD_BUS_CREDS_FSGID);
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
2014-11-25 13:21:23 +01:00
|
|
|
if (missing & SD_BUS_CREDS_SUPPLEMENTARY_GIDS) {
|
|
|
|
p = startswith(line, "Groups:");
|
|
|
|
if (p) {
|
|
|
|
size_t allocated = 0;
|
|
|
|
|
|
|
|
for (;;) {
|
|
|
|
unsigned long g;
|
|
|
|
int n = 0;
|
|
|
|
|
|
|
|
p += strspn(p, WHITESPACE);
|
|
|
|
if (*p == 0)
|
|
|
|
break;
|
|
|
|
|
|
|
|
if (sscanf(p, "%lu%n", &g, &n) != 1)
|
|
|
|
return -EIO;
|
|
|
|
|
|
|
|
if (!GREEDY_REALLOC(c->supplementary_gids, allocated, c->n_supplementary_gids+1))
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
c->supplementary_gids[c->n_supplementary_gids++] = (gid_t) g;
|
|
|
|
p += n;
|
|
|
|
}
|
|
|
|
|
|
|
|
c->mask |= SD_BUS_CREDS_SUPPLEMENTARY_GIDS;
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & SD_BUS_CREDS_EFFECTIVE_CAPS) {
|
|
|
|
p = startswith(line, "CapEff:");
|
|
|
|
if (p) {
|
|
|
|
r = parse_caps(c, CAP_OFFSET_EFFECTIVE, p);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_EFFECTIVE_CAPS;
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & SD_BUS_CREDS_PERMITTED_CAPS) {
|
|
|
|
p = startswith(line, "CapPrm:");
|
|
|
|
if (p) {
|
|
|
|
r = parse_caps(c, CAP_OFFSET_PERMITTED, p);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_PERMITTED_CAPS;
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & SD_BUS_CREDS_INHERITABLE_CAPS) {
|
|
|
|
p = startswith(line, "CapInh:");
|
|
|
|
if (p) {
|
|
|
|
r = parse_caps(c, CAP_OFFSET_INHERITABLE, p);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_INHERITABLE_CAPS;
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (missing & SD_BUS_CREDS_BOUNDING_CAPS) {
|
|
|
|
p = startswith(line, "CapBnd:");
|
|
|
|
if (p) {
|
|
|
|
r = parse_caps(c, CAP_OFFSET_BOUNDING, p);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_BOUNDING_CAPS;
|
|
|
|
continue;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_SELINUX_CONTEXT) {
|
|
|
|
const char *p;
|
|
|
|
|
|
|
|
p = procfs_file_alloca(pid, "attr/current");
|
|
|
|
r = read_one_line_file(p, &c->label);
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (r < 0) {
|
|
|
|
if (r != -ENOENT && r != -EINVAL && r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
} else
|
2013-11-28 17:50:02 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_COMM) {
|
|
|
|
r = get_process_comm(pid, &c->comm);
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (r < 0) {
|
|
|
|
if (r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
} else
|
|
|
|
c->mask |= SD_BUS_CREDS_COMM;
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_EXE) {
|
|
|
|
r = get_process_exe(pid, &c->exe);
|
2015-04-29 21:40:54 +02:00
|
|
|
if (r == -ESRCH) {
|
2015-05-26 19:17:30 +02:00
|
|
|
/* Unfortunately we cannot really distinguish
|
2015-04-29 21:40:54 +02:00
|
|
|
* the case here where the process does not
|
|
|
|
* exist, and /proc/$PID/exe being unreadable
|
|
|
|
* because $PID is a kernel thread. Hence,
|
|
|
|
* assume it is a kernel thread, and rely on
|
|
|
|
* that this case is caught with a later
|
|
|
|
* call. */
|
|
|
|
c->exe = NULL;
|
|
|
|
c->mask |= SD_BUS_CREDS_EXE;
|
|
|
|
} else if (r < 0) {
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
} else
|
|
|
|
c->mask |= SD_BUS_CREDS_EXE;
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_CMDLINE) {
|
|
|
|
const char *p;
|
|
|
|
|
|
|
|
p = procfs_file_alloca(pid, "cmdline");
|
2013-11-30 04:14:10 +01:00
|
|
|
r = read_full_file(p, &c->cmdline, &c->cmdline_size);
|
2015-04-29 21:40:54 +02:00
|
|
|
if (r == -ENOENT)
|
|
|
|
return -ESRCH;
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (r < 0) {
|
|
|
|
if (r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
} else {
|
2015-09-08 23:03:38 +02:00
|
|
|
if (c->cmdline_size == 0)
|
2015-09-08 18:43:11 +02:00
|
|
|
c->cmdline = mfree(c->cmdline);
|
2015-04-29 21:40:54 +02:00
|
|
|
|
|
|
|
c->mask |= SD_BUS_CREDS_CMDLINE;
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (tid > 0 && (missing & SD_BUS_CREDS_TID_COMM)) {
|
|
|
|
_cleanup_free_ char *p = NULL;
|
|
|
|
|
2014-04-25 13:45:15 +02:00
|
|
|
if (asprintf(&p, "/proc/"PID_FMT"/task/"PID_FMT"/comm", pid, tid) < 0)
|
2013-11-28 17:50:02 +01:00
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
r = read_one_line_file(p, &c->tid_comm);
|
2015-04-29 21:40:54 +02:00
|
|
|
if (r == -ENOENT)
|
|
|
|
return -ESRCH;
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (r < 0) {
|
|
|
|
if (r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
} else
|
|
|
|
c->mask |= SD_BUS_CREDS_TID_COMM;
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
2015-04-30 11:58:06 +02:00
|
|
|
if (missing & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_USER_SLICE|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_OWNER_UID)) {
|
2013-11-28 17:50:02 +01:00
|
|
|
|
2015-04-21 00:53:43 +02:00
|
|
|
if (!c->cgroup) {
|
|
|
|
r = cg_pid_get_path(NULL, pid, &c->cgroup);
|
|
|
|
if (r < 0) {
|
|
|
|
if (r != -EPERM && r != -EACCES)
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!c->cgroup_root) {
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
r = cg_get_root_path(&c->cgroup_root);
|
|
|
|
if (r < 0)
|
|
|
|
return r;
|
2015-04-21 00:53:43 +02:00
|
|
|
}
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
|
2015-04-21 00:53:43 +02:00
|
|
|
if (c->cgroup)
|
2015-04-30 11:58:06 +02:00
|
|
|
c->mask |= missing & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_USER_SLICE|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_OWNER_UID);
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_AUDIT_SESSION_ID) {
|
|
|
|
r = audit_session_from_pid(pid, &c->audit_session_id);
|
2015-09-03 18:24:57 +02:00
|
|
|
if (r == -ENODATA) {
|
|
|
|
/* ENODATA means: no audit session id assigned */
|
2015-04-29 21:40:54 +02:00
|
|
|
c->audit_session_id = AUDIT_SESSION_INVALID;
|
|
|
|
c->mask |= SD_BUS_CREDS_AUDIT_SESSION_ID;
|
|
|
|
} else if (r < 0) {
|
|
|
|
if (r != -EOPNOTSUPP && r != -ENOENT && r != -EPERM && r != -EACCES)
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
return r;
|
|
|
|
} else
|
2013-11-28 17:50:02 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_AUDIT_SESSION_ID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (missing & SD_BUS_CREDS_AUDIT_LOGIN_UID) {
|
|
|
|
r = audit_loginuid_from_pid(pid, &c->audit_login_uid);
|
2015-09-03 18:24:57 +02:00
|
|
|
if (r == -ENODATA) {
|
|
|
|
/* ENODATA means: no audit login uid assigned */
|
2015-04-29 21:40:54 +02:00
|
|
|
c->audit_login_uid = UID_INVALID;
|
|
|
|
c->mask |= SD_BUS_CREDS_AUDIT_LOGIN_UID;
|
|
|
|
} else if (r < 0) {
|
|
|
|
if (r != -EOPNOTSUPP && r != -ENOENT && r != -EPERM && r != -EACCES)
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
return r;
|
|
|
|
} else
|
2013-11-28 17:50:02 +01:00
|
|
|
c->mask |= SD_BUS_CREDS_AUDIT_LOGIN_UID;
|
|
|
|
}
|
|
|
|
|
2015-04-23 19:43:40 +02:00
|
|
|
if (missing & SD_BUS_CREDS_TTY) {
|
|
|
|
r = get_ctty(pid, NULL, &c->tty);
|
2015-04-29 21:40:54 +02:00
|
|
|
if (r == -ENXIO) {
|
|
|
|
/* ENXIO means: process has no controlling TTY */
|
|
|
|
c->tty = NULL;
|
|
|
|
c->mask |= SD_BUS_CREDS_TTY;
|
|
|
|
} else if (r < 0) {
|
2015-04-23 19:43:40 +02:00
|
|
|
if (r != -EPERM && r != -EACCES && r != -ENOENT)
|
|
|
|
return r;
|
|
|
|
} else
|
|
|
|
c->mask |= SD_BUS_CREDS_TTY;
|
|
|
|
}
|
|
|
|
|
2015-04-29 21:40:54 +02:00
|
|
|
/* In case only the exe path was to be read we cannot
|
2015-05-26 19:17:30 +02:00
|
|
|
* distinguish the case where the exe path was unreadable
|
2015-04-29 21:40:54 +02:00
|
|
|
* because the process was a kernel thread, or when the
|
|
|
|
* process didn't exist at all. Hence, let's do a final check,
|
|
|
|
* to be sure. */
|
|
|
|
if (!pid_is_alive(pid))
|
|
|
|
return -ESRCH;
|
|
|
|
|
|
|
|
if (tid > 0 && tid != pid && !pid_is_unwaited(tid))
|
|
|
|
return -ESRCH;
|
|
|
|
|
2015-04-21 00:58:08 +02:00
|
|
|
c->augmented = missing & c->mask;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
int bus_creds_extend_by_pid(sd_bus_creds *c, uint64_t mask, sd_bus_creds **ret) {
|
2013-11-28 17:50:02 +01:00
|
|
|
_cleanup_bus_creds_unref_ sd_bus_creds *n = NULL;
|
|
|
|
int r;
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
assert(c);
|
|
|
|
assert(ret);
|
2013-11-28 17:50:02 +01:00
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if ((mask & ~c->mask) == 0 || (!(mask & SD_BUS_CREDS_AUGMENT))) {
|
|
|
|
/* There's already all data we need, or augmentation
|
|
|
|
* wasn't turned on. */
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
*ret = sd_bus_creds_ref(c);
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
n = bus_creds_new();
|
|
|
|
if (!n)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
/* Copy the original data over */
|
|
|
|
|
2015-04-21 00:50:43 +02:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_PID) {
|
|
|
|
n->pid = c->pid;
|
|
|
|
n->mask |= SD_BUS_CREDS_PID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_TID) {
|
|
|
|
n->tid = c->tid;
|
|
|
|
n->mask |= SD_BUS_CREDS_TID;
|
|
|
|
}
|
|
|
|
|
2015-04-21 20:58:09 +02:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_PPID) {
|
|
|
|
n->ppid = c->ppid;
|
|
|
|
n->mask |= SD_BUS_CREDS_PPID;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_UID) {
|
|
|
|
n->uid = c->uid;
|
|
|
|
n->mask |= SD_BUS_CREDS_UID;
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_EUID) {
|
|
|
|
n->euid = c->euid;
|
|
|
|
n->mask |= SD_BUS_CREDS_EUID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_SUID) {
|
|
|
|
n->suid = c->suid;
|
|
|
|
n->mask |= SD_BUS_CREDS_SUID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_FSUID) {
|
|
|
|
n->fsuid = c->fsuid;
|
|
|
|
n->mask |= SD_BUS_CREDS_FSUID;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_GID) {
|
|
|
|
n->gid = c->gid;
|
|
|
|
n->mask |= SD_BUS_CREDS_GID;
|
|
|
|
}
|
|
|
|
|
sd-bus: update to current kernel version, by splitting off the extended KDBUS_ITEM_PIDS structure from KDBUS_ITEM_CREDS
Also:
- adds support for euid, suid, fsuid, egid, sgid, fsgid fields.
- makes augmentation of creds with data from /proc explicitly
controllable to give apps better control over this, given that this is
racy.
- enables augmentation for kdbus connections (previously we only did it
for dbus1). This is useful since with recent kdbus versions it is
possible for clients to control the metadata they want to send.
- changes sd_bus_query_sender_privilege() to take the euid of the client
into consideration, if known
- when we don't have permissions to read augmentation data from /proc,
don't fail, just don't add the data in
2014-11-24 21:41:40 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_EGID) {
|
|
|
|
n->egid = c->egid;
|
|
|
|
n->mask |= SD_BUS_CREDS_EGID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_SGID) {
|
|
|
|
n->sgid = c->sgid;
|
|
|
|
n->mask |= SD_BUS_CREDS_SGID;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_FSGID) {
|
|
|
|
n->fsgid = c->fsgid;
|
|
|
|
n->mask |= SD_BUS_CREDS_FSGID;
|
|
|
|
}
|
|
|
|
|
2014-11-25 13:21:23 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_SUPPLEMENTARY_GIDS) {
|
2015-04-29 21:40:54 +02:00
|
|
|
if (c->supplementary_gids) {
|
|
|
|
n->supplementary_gids = newdup(gid_t, c->supplementary_gids, c->n_supplementary_gids);
|
|
|
|
if (!n->supplementary_gids)
|
|
|
|
return -ENOMEM;
|
|
|
|
n->n_supplementary_gids = c->n_supplementary_gids;
|
|
|
|
} else {
|
|
|
|
n->supplementary_gids = NULL;
|
|
|
|
n->n_supplementary_gids = 0;
|
|
|
|
}
|
|
|
|
|
2014-11-25 13:21:23 +01:00
|
|
|
n->mask |= SD_BUS_CREDS_SUPPLEMENTARY_GIDS;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_COMM) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->comm);
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
n->comm = strdup(c->comm);
|
|
|
|
if (!n->comm)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
n->mask |= SD_BUS_CREDS_COMM;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_TID_COMM) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->tid_comm);
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
n->tid_comm = strdup(c->tid_comm);
|
|
|
|
if (!n->tid_comm)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
n->mask |= SD_BUS_CREDS_TID_COMM;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_EXE) {
|
2015-04-29 21:40:54 +02:00
|
|
|
if (c->exe) {
|
|
|
|
n->exe = strdup(c->exe);
|
|
|
|
if (!n->exe)
|
|
|
|
return -ENOMEM;
|
|
|
|
} else
|
|
|
|
n->exe = NULL;
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
n->mask |= SD_BUS_CREDS_EXE;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_CMDLINE) {
|
2015-04-29 21:40:54 +02:00
|
|
|
if (c->cmdline) {
|
|
|
|
n->cmdline = memdup(c->cmdline, c->cmdline_size);
|
|
|
|
if (!n->cmdline)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
n->cmdline_size = c->cmdline_size;
|
|
|
|
} else {
|
|
|
|
n->cmdline = NULL;
|
|
|
|
n->cmdline_size = 0;
|
|
|
|
}
|
2013-11-28 17:50:02 +01:00
|
|
|
|
|
|
|
n->mask |= SD_BUS_CREDS_CMDLINE;
|
|
|
|
}
|
|
|
|
|
2015-04-30 11:58:06 +02:00
|
|
|
if (c->mask & mask & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_USER_SLICE|SD_BUS_CREDS_OWNER_UID)) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->cgroup);
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
n->cgroup = strdup(c->cgroup);
|
|
|
|
if (!n->cgroup)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
2013-12-24 19:31:44 +01:00
|
|
|
n->cgroup_root = strdup(c->cgroup_root);
|
|
|
|
if (!n->cgroup_root)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
2015-04-30 11:58:06 +02:00
|
|
|
n->mask |= mask & (SD_BUS_CREDS_CGROUP|SD_BUS_CREDS_SESSION|SD_BUS_CREDS_UNIT|SD_BUS_CREDS_USER_UNIT|SD_BUS_CREDS_SLICE|SD_BUS_CREDS_USER_SLICE|SD_BUS_CREDS_OWNER_UID);
|
2013-11-28 17:50:02 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS)) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->capability);
|
|
|
|
|
2014-12-30 08:42:53 +01:00
|
|
|
n->capability = memdup(c->capability, DIV_ROUND_UP(cap_last_cap(), 32U) * 4 * 4);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (!n->capability)
|
|
|
|
return -ENOMEM;
|
|
|
|
|
|
|
|
n->mask |= c->mask & mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS);
|
|
|
|
}
|
|
|
|
|
2014-11-25 13:22:19 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_SELINUX_CONTEXT) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->label);
|
|
|
|
|
2014-11-25 13:22:19 +01:00
|
|
|
n->label = strdup(c->label);
|
|
|
|
if (!n->label)
|
|
|
|
return -ENOMEM;
|
|
|
|
n->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
|
|
|
|
}
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_AUDIT_SESSION_ID) {
|
|
|
|
n->audit_session_id = c->audit_session_id;
|
|
|
|
n->mask |= SD_BUS_CREDS_AUDIT_SESSION_ID;
|
|
|
|
}
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_AUDIT_LOGIN_UID) {
|
|
|
|
n->audit_login_uid = c->audit_login_uid;
|
|
|
|
n->mask |= SD_BUS_CREDS_AUDIT_LOGIN_UID;
|
|
|
|
}
|
|
|
|
|
2015-04-23 19:43:40 +02:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_TTY) {
|
|
|
|
if (c->tty) {
|
|
|
|
n->tty = strdup(c->tty);
|
|
|
|
if (!n->tty)
|
|
|
|
return -ENOMEM;
|
|
|
|
} else
|
|
|
|
n->tty = NULL;
|
|
|
|
n->mask |= SD_BUS_CREDS_TTY;
|
|
|
|
}
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
if (c->mask & mask & SD_BUS_CREDS_UNIQUE_NAME) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->unique_name);
|
|
|
|
|
2013-11-30 04:14:10 +01:00
|
|
|
n->unique_name = strdup(c->unique_name);
|
|
|
|
if (!n->unique_name)
|
|
|
|
return -ENOMEM;
|
2014-11-25 13:22:19 +01:00
|
|
|
n->mask |= SD_BUS_CREDS_UNIQUE_NAME;
|
2013-11-30 04:14:10 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_WELL_KNOWN_NAMES) {
|
2015-04-29 21:40:54 +02:00
|
|
|
if (strv_isempty(c->well_known_names))
|
|
|
|
n->well_known_names = NULL;
|
|
|
|
else {
|
|
|
|
n->well_known_names = strv_copy(c->well_known_names);
|
|
|
|
if (!n->well_known_names)
|
|
|
|
return -ENOMEM;
|
|
|
|
}
|
2015-04-21 00:50:43 +02:00
|
|
|
n->well_known_names_driver = c->well_known_names_driver;
|
|
|
|
n->well_known_names_local = c->well_known_names_local;
|
2014-11-25 13:22:19 +01:00
|
|
|
n->mask |= SD_BUS_CREDS_WELL_KNOWN_NAMES;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (c->mask & mask & SD_BUS_CREDS_DESCRIPTION) {
|
2015-04-29 21:40:54 +02:00
|
|
|
assert(c->description);
|
2014-11-25 13:22:19 +01:00
|
|
|
n->description = strdup(c->description);
|
|
|
|
if (!n->description)
|
|
|
|
return -ENOMEM;
|
|
|
|
n->mask |= SD_BUS_CREDS_DESCRIPTION;
|
2013-11-30 04:14:10 +01:00
|
|
|
}
|
|
|
|
|
2015-04-21 00:58:08 +02:00
|
|
|
n->augmented = c->augmented & n->mask;
|
|
|
|
|
2013-11-28 17:50:02 +01:00
|
|
|
/* Get more data */
|
|
|
|
|
2015-04-21 00:58:08 +02:00
|
|
|
r = bus_creds_add_more(n, mask, 0, 0);
|
2013-11-28 17:50:02 +01:00
|
|
|
if (r < 0)
|
|
|
|
return r;
|
|
|
|
|
|
|
|
*ret = n;
|
|
|
|
n = NULL;
|
|
|
|
return 0;
|
|
|
|
}
|