bus-creds.c revision 50c4521675e94ade38b8af9e3b0f7fd2f300b6f4
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen/***
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen This file is part of systemd.
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen Copyright 2013 Lennart Poettering
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen systemd is free software; you can redistribute it and/or modify it
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen under the terms of the GNU Lesser General Public License as published by
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen the Free Software Foundation; either version 2.1 of the License, or
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen (at your option) any later version.
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen systemd is distributed in the hope that it will be useful, but
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen WITHOUT ANY WARRANTY; without even the implied warranty of
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen Lesser General Public License for more details.
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen You should have received a copy of the GNU Lesser General Public License
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen along with systemd; If not, see <http://www.gnu.org/licenses/>.
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen***/
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen#include <stdlib.h>
2a73e0d39a9bec82c3800071e375d27164727e71Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen#include "util.h"
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen#include "cgroup-util.h"
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen#include "fileio.h"
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen#include "audit.h"
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen#include "bus-message.h"
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen#include "bus-util.h"
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen#include "time-util.h"
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen#include "strv.h"
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen#include "bus-creds.h"
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen#include "bus-label.h"
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersenenum {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen CAP_OFFSET_INHERITABLE = 0,
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen CAP_OFFSET_PERMITTED = 1,
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen CAP_OFFSET_EFFECTIVE = 2,
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen CAP_OFFSET_BOUNDING = 3
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen};
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersenvoid bus_creds_done(sd_bus_creds *c) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert(c);
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen /* For internal bus cred structures that are allocated by
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen * something else */
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->session);
97f2d76d4f4dfab8b0629c09926a05a1e5621125Tom Gundersen free(c->unit);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->user_unit);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->slice);
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen free(c->unescaped_description);
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen free(c->well_known_names); /* note that this is an strv, but
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen * we only free the array, not the
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen * strings the array points to. The
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen * full strv we only free if
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen * c->allocated is set, see
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen * below. */
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen strv_free(c->cmdline_array);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ sd_bus_creds *sd_bus_creds_ref(sd_bus_creds *c) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, NULL);
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen if (c->allocated) {
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen assert(c->n_ref > 0);
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen c->n_ref++;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen } else {
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen sd_bus_message *m;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen /* If this is an embedded creds structure, then
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen * forward ref counting to the message */
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen m = container_of(c, sd_bus_message, creds);
9dc670ea766c711741f462b29572f2e5f8f3f6bcTom Gundersen sd_bus_message_ref(m);
9dc670ea766c711741f462b29572f2e5f8f3f6bcTom Gundersen }
9dc670ea766c711741f462b29572f2e5f8f3f6bcTom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return c;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ sd_bus_creds *sd_bus_creds_unref(sd_bus_creds *c) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen if (!c)
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return NULL;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (c->allocated) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert(c->n_ref > 0);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen c->n_ref--;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen if (c->n_ref == 0) {
5b9d4dc05560ddda89e48b6b39365824b15e1300Tom Gundersen free(c->comm);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->tid_comm);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->exe);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->cmdline);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->cgroup);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->capability);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->label);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->unique_name);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->cgroup_root);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->description);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c->supplementary_gids);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen strv_free(c->well_known_names);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen c->well_known_names = NULL;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen bus_creds_done(c);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen free(c);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen }
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen } else {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_message *m;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen m = container_of(c, sd_bus_message, creds);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_message_unref(m);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen }
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return NULL;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen}
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ uint64_t sd_bus_creds_get_mask(const sd_bus_creds *c) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, 0);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return c->mask;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersensd_bus_creds* bus_creds_new(void) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_creds *c;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen c = new0(sd_bus_creds, 1);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!c)
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return NULL;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen c->allocated = true;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen c->n_ref = 1;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return c;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_new_from_pid(sd_bus_creds **ret, pid_t pid, uint64_t mask) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_creds *c;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen int r;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(pid >= 0, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(mask <= _SD_BUS_CREDS_ALL, -ENOTSUP);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(ret, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (pid == 0)
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen pid = getpid();
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen c = bus_creds_new();
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen if (!c)
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return -ENOMEM;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen r = bus_creds_add_more(c, mask | SD_BUS_CREDS_AUGMENT, pid, 0);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (r < 0) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_creds_unref(c);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return r;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen }
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen /* Check if the process existed at all, in case we haven't
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen * figured that out already */
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!pid_is_alive(pid)) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen sd_bus_creds_unref(c);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ESRCH;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen }
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *ret = c;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_uid(sd_bus_creds *c, uid_t *uid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(uid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_UID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
97f2d76d4f4dfab8b0629c09926a05a1e5621125Tom Gundersen *uid = c->uid;
97f2d76d4f4dfab8b0629c09926a05a1e5621125Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_euid(sd_bus_creds *c, uid_t *euid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(euid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_EUID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *euid = c->euid;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_suid(sd_bus_creds *c, uid_t *suid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(suid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
97f2d76d4f4dfab8b0629c09926a05a1e5621125Tom Gundersen if (!(c->mask & SD_BUS_CREDS_SUID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *suid = c->suid;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen_public_ int sd_bus_creds_get_fsuid(sd_bus_creds *c, uid_t *fsuid) {
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(c, -EINVAL);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(fsuid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_FSUID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *fsuid = c->fsuid;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen}
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen_public_ int sd_bus_creds_get_gid(sd_bus_creds *c, gid_t *gid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(gid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_UID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen *gid = c->gid;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return 0;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_egid(sd_bus_creds *c, gid_t *egid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(egid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen if (!(c->mask & SD_BUS_CREDS_EGID))
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return -ENODATA;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *egid = c->egid;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_sgid(sd_bus_creds *c, gid_t *sgid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(sgid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_SGID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *sgid = c->sgid;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return 0;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen_public_ int sd_bus_creds_get_fsgid(sd_bus_creds *c, gid_t *fsgid) {
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(c, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen assert_return(fsgid, -EINVAL);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (!(c->mask & SD_BUS_CREDS_FSGID))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen *fsgid = c->fsgid;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen_public_ int sd_bus_creds_get_supplementary_gids(sd_bus_creds *c, const gid_t **gids) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(c, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(gids, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (!(c->mask & SD_BUS_CREDS_SUPPLEMENTARY_GIDS))
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return -ENODATA;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen *gids = c->supplementary_gids;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return (int) c->n_supplementary_gids;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen_public_ int sd_bus_creds_get_pid(sd_bus_creds *c, pid_t *pid) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(c, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(pid, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (!(c->mask & SD_BUS_CREDS_PID))
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return -ENODATA;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->pid > 0);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen *pid = c->pid;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return 0;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen}
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen_public_ int sd_bus_creds_get_tid(sd_bus_creds *c, pid_t *tid) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(c, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(tid, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (!(c->mask & SD_BUS_CREDS_TID))
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return -ENODATA;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert(c->tid > 0);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen *tid = c->tid;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return 0;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen_public_ int sd_bus_creds_get_pid_starttime(sd_bus_creds *c, uint64_t *usec) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(c, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen assert_return(usec, -EINVAL);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (!(c->mask & SD_BUS_CREDS_PID_STARTTIME))
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return -ENODATA;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert(c->pid_starttime > 0);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen *usec = c->pid_starttime;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen return 0;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen}
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen_public_ int sd_bus_creds_get_selinux_context(sd_bus_creds *c, const char **ret) {
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert_return(c, -EINVAL);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen if (!(c->mask & SD_BUS_CREDS_SELINUX_CONTEXT))
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen return -ENODATA;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert(c->label);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen *ret = c->label;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen return 0;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen}
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen_public_ int sd_bus_creds_get_comm(sd_bus_creds *c, const char **ret) {
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert_return(c, -EINVAL);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert_return(ret, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!(c->mask & SD_BUS_CREDS_COMM))
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen return -ENODATA;
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->comm);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen *ret = c->comm;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen}
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen_public_ int sd_bus_creds_get_tid_comm(sd_bus_creds *c, const char **ret) {
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen assert_return(c, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(ret, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!(c->mask & SD_BUS_CREDS_TID_COMM))
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->tid_comm);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen *ret = c->tid_comm;
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen return 0;
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen_public_ int sd_bus_creds_get_exe(sd_bus_creds *c, const char **ret) {
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(c, -EINVAL);
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen assert_return(ret, -EINVAL);
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen if (!(c->mask & SD_BUS_CREDS_EXE))
f1ac700248f231b7bdac2aafe8c35650efddb89fTom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->exe);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen *ret = c->exe;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen}
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen_public_ int sd_bus_creds_get_cgroup(sd_bus_creds *c, const char **ret) {
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(c, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(ret, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!(c->mask & SD_BUS_CREDS_CGROUP))
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->cgroup);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen *ret = c->cgroup;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen_public_ int sd_bus_creds_get_unit(sd_bus_creds *c, const char **ret) {
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen int r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(c, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(ret, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
55428d84f31b52da1c50b7469f14e15740547f20Tom Gundersen if (!(c->mask & SD_BUS_CREDS_UNIT))
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->cgroup);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!c->unit) {
55428d84f31b52da1c50b7469f14e15740547f20Tom Gundersen const char *shifted;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (r < 0)
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen r = cg_path_get_unit(shifted, (char**) &c->unit);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (r < 0)
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen }
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen *ret = c->unit;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen}
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen_public_ int sd_bus_creds_get_user_unit(sd_bus_creds *c, const char **ret) {
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen int r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(c, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(ret, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!(c->mask & SD_BUS_CREDS_USER_UNIT))
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert(c->cgroup);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (!c->user_unit) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen const char *shifted;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (r < 0)
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return r;
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen r = cg_path_get_user_unit(shifted, (char**) &c->user_unit);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen if (r < 0)
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen return r;
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen }
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen *ret = c->user_unit;
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen return 0;
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen}
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen_public_ int sd_bus_creds_get_slice(sd_bus_creds *c, const char **ret) {
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen int r;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(c, -EINVAL);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(ret, -EINVAL);
a501033335ed402c8f7e86fe41a15531ba69abd7Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen if (!(c->mask & SD_BUS_CREDS_SLICE))
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return -ENODATA;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert(c->cgroup);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (!c->slice) {
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen const char *shifted;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen if (r < 0)
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return r;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen r = cg_path_get_slice(shifted, (char**) &c->slice);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen if (r < 0)
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return r;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen }
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen *ret = c->slice;
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen return 0;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen}
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen_public_ int sd_bus_creds_get_session(sd_bus_creds *c, const char **ret) {
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen int r;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen assert_return(c, -EINVAL);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(ret, -EINVAL);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen if (!(c->mask & SD_BUS_CREDS_SESSION))
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return -ENODATA;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert(c->cgroup);
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen if (!c->session) {
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen const char *shifted;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (r < 0)
daeb71a36a98834664e4d95773a3629b746f4db8Tom Gundersen return r;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen r = cg_path_get_session(shifted, (char**) &c->session);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (r < 0)
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen }
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen *ret = c->session;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen return 0;
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen}
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen_public_ int sd_bus_creds_get_owner_uid(sd_bus_creds *c, uid_t *uid) {
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen const char *shifted;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen int r;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen assert_return(c, -EINVAL);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert_return(uid, -EINVAL);
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen if (!(c->mask & SD_BUS_CREDS_OWNER_UID))
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return -ENODATA;
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen assert(c->cgroup);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen r = cg_shift_path(c->cgroup, c->cgroup_root, &shifted);
16b9b87aeee9353b5b8dae6089a69752422a5b09Tom Gundersen if (r < 0)
5fde13d748749f0e06e2e6cdd15f0980a79ea82cTom Gundersen return r;
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen
43b3a5ef61859f06cdbaf26765cab8e1adac4296Tom Gundersen return cg_path_get_owner_uid(shifted, uid);
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen}
af6f0d422c521374ee6a2dd92df5935a5a476ae5Tom Gundersen
_public_ int sd_bus_creds_get_cmdline(sd_bus_creds *c, char ***cmdline) {
assert_return(c, -EINVAL);
if (!(c->mask & SD_BUS_CREDS_CMDLINE))
return -ENODATA;
assert_return(c->cmdline, -ESRCH);
assert(c->cmdline);
if (!c->cmdline_array) {
c->cmdline_array = strv_parse_nulstr(c->cmdline, c->cmdline_size);
if (!c->cmdline_array)
return -ENOMEM;
}
*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);
if (!(c->mask & SD_BUS_CREDS_AUDIT_SESSION_ID))
return -ENODATA;
*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);
if (!(c->mask & SD_BUS_CREDS_AUDIT_LOGIN_UID))
return -ENODATA;
*uid = c->audit_login_uid;
return 0;
}
_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);
if (!(c->mask & SD_BUS_CREDS_UNIQUE_NAME))
return -ENODATA;
*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);
if (!(c->mask & SD_BUS_CREDS_WELL_KNOWN_NAMES))
return -ENODATA;
*well_known_names = c->well_known_names;
return 0;
}
_public_ int sd_bus_creds_get_description(sd_bus_creds *c, const char **ret) {
assert_return(c, -EINVAL);
assert_return(ret, -EINVAL);
if (!(c->mask & SD_BUS_CREDS_DESCRIPTION))
return -ENODATA;
assert(c->description);
if (!c->unescaped_description) {
c->unescaped_description = bus_label_unescape(c->description);
if (!c->unescaped_description)
return -ENOMEM;
}
*ret = c->unescaped_description;
return 0;
}
static int has_cap(sd_bus_creds *c, unsigned offset, int capability) {
size_t sz;
assert(c);
assert(c->capability);
sz = c->capability_size / 4;
if ((size_t) capability >= sz*8)
return 0;
return !!(c->capability[offset * sz + (capability / 8)] & (1 << (capability % 8)));
}
_public_ int sd_bus_creds_has_effective_cap(sd_bus_creds *c, int capability) {
assert_return(c, -EINVAL);
assert_return(capability >= 0, -EINVAL);
if (!(c->mask & SD_BUS_CREDS_EFFECTIVE_CAPS))
return -ENODATA;
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);
if (!(c->mask & SD_BUS_CREDS_PERMITTED_CAPS))
return -ENODATA;
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);
if (!(c->mask & SD_BUS_CREDS_INHERITABLE_CAPS))
return -ENODATA;
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);
if (!(c->mask & SD_BUS_CREDS_BOUNDING_CAPS))
return -ENODATA;
return has_cap(c, CAP_OFFSET_BOUNDING, capability);
}
static int parse_caps(sd_bus_creds *c, unsigned offset, const char *p) {
size_t sz;
unsigned i;
assert(c);
assert(p);
p += strspn(p, WHITESPACE);
sz = strlen(p);
if (sz % 2 != 0)
return -EINVAL;
sz /= 2;
if (!c->capability) {
c->capability = new0(uint8_t, sz * 4);
if (!c->capability)
return -ENOMEM;
c->capability_size = sz * 4;
}
for (i = 0; i < sz; i ++) {
int x, y;
x = unhexchar(p[i*2]);
y = unhexchar(p[i*2+1]);
if (x < 0 || y < 0)
return -EINVAL;
c->capability[offset * sz + (sz - i - 1)] = (uint8_t) x << 4 | (uint8_t) y;
}
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);
if (!(mask & SD_BUS_CREDS_AUGMENT))
return 0;
missing = mask & ~c->mask;
if (missing == 0)
return 0;
/* Try to retrieve PID from creds if it wasn't passed to us */
if (pid <= 0 && (c->mask & SD_BUS_CREDS_PID))
pid = c->pid;
if (tid <= 0 && (c->mask & SD_BUS_CREDS_TID))
tid = c->pid;
/* Without pid we cannot do much... */
if (pid <= 0)
return 0;
if (pid > 0) {
c->pid = pid;
c->mask |= SD_BUS_CREDS_PID;
}
if (tid > 0) {
c->tid = tid;
c->mask |= SD_BUS_CREDS_TID;
}
if (missing & (SD_BUS_CREDS_UID | SD_BUS_CREDS_EUID | SD_BUS_CREDS_SUID | SD_BUS_CREDS_FSUID |
SD_BUS_CREDS_GID | SD_BUS_CREDS_EGID | SD_BUS_CREDS_SGID | SD_BUS_CREDS_FSGID |
SD_BUS_CREDS_SUPPLEMENTARY_GIDS |
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");
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);
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;
c->uid = (uid_t) uid;
c->euid = (uid_t) euid;
c->suid = (uid_t) suid;
c->fsuid = (uid_t) fsuid;
c->mask |= missing & (SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_SUID|SD_BUS_CREDS_FSUID);
continue;
}
}
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;
c->gid = (gid_t) gid;
c->egid = (gid_t) egid;
c->sgid = (gid_t) sgid;
c->fsgid = (gid_t) fsgid;
c->mask |= missing & (SD_BUS_CREDS_GID|SD_BUS_CREDS_EGID|SD_BUS_CREDS_SGID|SD_BUS_CREDS_FSGID);
continue;
}
}
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;
}
}
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;
c->mask |= SD_BUS_CREDS_EFFECTIVE_CAPS;
continue;
}
}
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;
c->mask |= SD_BUS_CREDS_PERMITTED_CAPS;
continue;
}
}
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;
c->mask |= SD_BUS_CREDS_INHERITABLE_CAPS;
continue;
}
}
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;
c->mask |= SD_BUS_CREDS_BOUNDING_CAPS;
continue;
}
}
}
}
}
if (missing & (SD_BUS_CREDS_PID_STARTTIME)) {
unsigned long long st;
r = get_starttime_of_pid(pid, &st);
if (r < 0) {
if (r != -EPERM && r != -EACCES)
return r;
} else {
c->pid_starttime = ((usec_t) st * USEC_PER_SEC) / (usec_t) sysconf(_SC_CLK_TCK);
c->mask |= SD_BUS_CREDS_PID_STARTTIME;
}
}
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);
if (r < 0) {
if (r != -ENOENT && r != -EINVAL && r != -EPERM && r != -EACCES)
return r;
} else
c->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
}
if (missing & SD_BUS_CREDS_COMM) {
r = get_process_comm(pid, &c->comm);
if (r < 0) {
if (r != -EPERM && r != -EACCES)
return r;
} else
c->mask |= SD_BUS_CREDS_COMM;
}
if (missing & SD_BUS_CREDS_EXE) {
r = get_process_exe(pid, &c->exe);
if (r < 0) {
if (r != -EPERM && r != -EACCES)
return r;
} else
c->mask |= SD_BUS_CREDS_EXE;
}
if (missing & SD_BUS_CREDS_CMDLINE) {
const char *p;
p = procfs_file_alloca(pid, "cmdline");
r = read_full_file(p, &c->cmdline, &c->cmdline_size);
if (r < 0) {
if (r == -ENOENT)
return -ESRCH;
if (r != -EPERM && r != -EACCES)
return r;
} else {
if (c->cmdline_size == 0) {
free(c->cmdline);
c->cmdline = NULL;
} else
c->mask |= SD_BUS_CREDS_CMDLINE;
}
}
if (tid > 0 && (missing & SD_BUS_CREDS_TID_COMM)) {
_cleanup_free_ char *p = NULL;
if (asprintf(&p, "/proc/"PID_FMT"/task/"PID_FMT"/comm", pid, tid) < 0)
return -ENOMEM;
r = read_one_line_file(p, &c->tid_comm);
if (r < 0) {
if (r == -ENOENT)
return -ESRCH;
if (r != -EPERM && r != -EACCES)
return r;
} else
c->mask |= SD_BUS_CREDS_TID_COMM;
}
if (missing & (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)) {
r = cg_pid_get_path(NULL, pid, &c->cgroup);
if (r < 0) {
if (r != -EPERM && r != -EACCES)
return r;
} else {
r = cg_get_root_path(&c->cgroup_root);
if (r < 0)
return r;
c->mask |= missing & (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);
}
}
if (missing & SD_BUS_CREDS_AUDIT_SESSION_ID) {
r = audit_session_from_pid(pid, &c->audit_session_id);
if (r < 0) {
if (r != -ENOTSUP && r != -ENXIO && r != -ENOENT && r != -EPERM && r != -EACCES)
return r;
} else
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);
if (r < 0) {
if (r != -ENOTSUP && r != -ENXIO && r != -ENOENT && r != -EPERM && r != -EACCES)
return r;
} else
c->mask |= SD_BUS_CREDS_AUDIT_LOGIN_UID;
}
return 0;
}
int bus_creds_extend_by_pid(sd_bus_creds *c, uint64_t mask, sd_bus_creds **ret) {
_cleanup_bus_creds_unref_ sd_bus_creds *n = NULL;
int r;
assert(c);
assert(ret);
if ((mask & ~c->mask) == 0 || (!(mask & SD_BUS_CREDS_AUGMENT))) {
/* There's already all data we need, or augmentation
* wasn't turned on. */
*ret = sd_bus_creds_ref(c);
return 0;
}
n = bus_creds_new();
if (!n)
return -ENOMEM;
/* Copy the original data over */
if (c->mask & mask & SD_BUS_CREDS_UID) {
n->uid = c->uid;
n->mask |= SD_BUS_CREDS_UID;
}
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;
}
if (c->mask & mask & SD_BUS_CREDS_GID) {
n->gid = c->gid;
n->mask |= SD_BUS_CREDS_GID;
}
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;
}
if (c->mask & mask & SD_BUS_CREDS_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;
n->mask |= SD_BUS_CREDS_SUPPLEMENTARY_GIDS;
}
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;
}
if (c->mask & mask & SD_BUS_CREDS_PID_STARTTIME) {
n->pid_starttime = c->pid_starttime;
n->mask |= SD_BUS_CREDS_PID_STARTTIME;
}
if (c->mask & mask & SD_BUS_CREDS_COMM) {
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) {
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) {
n->exe = strdup(c->exe);
if (!n->exe)
return -ENOMEM;
n->mask |= SD_BUS_CREDS_EXE;
}
if (c->mask & mask & SD_BUS_CREDS_CMDLINE) {
n->cmdline = memdup(c->cmdline, c->cmdline_size);
if (!n->cmdline)
return -ENOMEM;
n->cmdline_size = c->cmdline_size;
n->mask |= SD_BUS_CREDS_CMDLINE;
}
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_OWNER_UID)) {
n->cgroup = strdup(c->cgroup);
if (!n->cgroup)
return -ENOMEM;
n->cgroup_root = strdup(c->cgroup_root);
if (!n->cgroup_root)
return -ENOMEM;
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_OWNER_UID);
}
if (c->mask & mask & (SD_BUS_CREDS_EFFECTIVE_CAPS|SD_BUS_CREDS_PERMITTED_CAPS|SD_BUS_CREDS_INHERITABLE_CAPS|SD_BUS_CREDS_BOUNDING_CAPS)) {
n->capability = memdup(c->capability, c->capability_size);
if (!n->capability)
return -ENOMEM;
n->capability_size = c->capability_size;
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);
}
if (c->mask & mask & SD_BUS_CREDS_SELINUX_CONTEXT) {
n->label = strdup(c->label);
if (!n->label)
return -ENOMEM;
n->mask |= SD_BUS_CREDS_SELINUX_CONTEXT;
}
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;
}
if (c->mask & mask & SD_BUS_CREDS_UNIQUE_NAME) {
n->unique_name = strdup(c->unique_name);
if (!n->unique_name)
return -ENOMEM;
n->mask |= SD_BUS_CREDS_UNIQUE_NAME;
}
if (c->mask & mask & SD_BUS_CREDS_WELL_KNOWN_NAMES) {
n->well_known_names = strv_copy(c->well_known_names);
if (!n->well_known_names)
return -ENOMEM;
n->mask |= SD_BUS_CREDS_WELL_KNOWN_NAMES;
}
if (c->mask & mask & SD_BUS_CREDS_DESCRIPTION) {
n->description = strdup(c->description);
if (!n->description)
return -ENOMEM;
n->mask |= SD_BUS_CREDS_DESCRIPTION;
}
/* Get more data */
r = bus_creds_add_more(n, mask,
c->mask & SD_BUS_CREDS_PID ? c->pid : 0,
c->mask & SD_BUS_CREDS_TID ? c->tid : 0);
if (r < 0)
return r;
*ret = n;
n = NULL;
return 0;
}