LCOV - code coverage report
Current view: top level - core - bus-policy.c (source / functions) Hit Total Coverage
Test: systemd test coverage Lines: 1 76 1.3 %
Date: 2015-07-29 18:47:03 Functions: 2 5 40.0 %

          Line data    Source code
       1             : /***
       2             :   This file is part of systemd.
       3             : 
       4             :   Copyright 2014 Daniel Mack
       5             : 
       6             :   systemd is free software; you can redistribute it and/or modify it
       7             :   under the terms of the GNU Lesser General Public License as published by
       8             :   the Free Software Foundation; either version 2.1 of the License, or
       9             :   (at your option) any later version.
      10             : 
      11             :   systemd is distributed in the hope that it will be useful, but
      12             :   WITHOUT ANY WARRANTY; without even the implied warranty of
      13             :   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
      14             :   Lesser General Public License for more details.
      15             : 
      16             :   You should have received a copy of the GNU Lesser General Public License
      17             :   along with systemd; If not, see <http://www.gnu.org/licenses/>.
      18             : ***/
      19             : 
      20             : #include <stdlib.h>
      21             : 
      22             : #include "kdbus.h"
      23             : #include "util.h"
      24             : #include "bus-kernel.h"
      25             : #include "bus-policy.h"
      26             : 
      27           0 : int bus_kernel_translate_access(BusPolicyAccess access) {
      28           0 :         assert(access >= 0);
      29           0 :         assert(access < _BUS_POLICY_ACCESS_MAX);
      30             : 
      31           0 :         switch (access) {
      32             : 
      33             :         case BUS_POLICY_ACCESS_SEE:
      34           0 :                 return KDBUS_POLICY_SEE;
      35             : 
      36             :         case BUS_POLICY_ACCESS_TALK:
      37           0 :                 return KDBUS_POLICY_TALK;
      38             : 
      39             :         case BUS_POLICY_ACCESS_OWN:
      40           0 :                 return KDBUS_POLICY_OWN;
      41             : 
      42             :         default:
      43           0 :                 assert_not_reached("Unknown policy access");
      44             :         }
      45             : }
      46             : 
      47           0 : int bus_kernel_translate_policy(const BusNamePolicy *policy, struct kdbus_item *item) {
      48             :         int r;
      49             : 
      50           0 :         assert(policy);
      51           0 :         assert(item);
      52             : 
      53           0 :         switch (policy->type) {
      54             : 
      55             :         case BUSNAME_POLICY_TYPE_USER: {
      56           0 :                 const char *user = policy->name;
      57             :                 uid_t uid;
      58             : 
      59           0 :                 r = get_user_creds(&user, &uid, NULL, NULL, NULL);
      60           0 :                 if (r < 0)
      61           0 :                         return r;
      62             : 
      63           0 :                 item->policy_access.type = KDBUS_POLICY_ACCESS_USER;
      64           0 :                 item->policy_access.id = uid;
      65           0 :                 break;
      66             :         }
      67             : 
      68             :         case BUSNAME_POLICY_TYPE_GROUP: {
      69           0 :                 const char *group = policy->name;
      70             :                 gid_t gid;
      71             : 
      72           0 :                 r = get_group_creds(&group, &gid);
      73           0 :                 if (r < 0)
      74           0 :                         return r;
      75             : 
      76           0 :                 item->policy_access.type = KDBUS_POLICY_ACCESS_GROUP;
      77           0 :                 item->policy_access.id = gid;
      78           0 :                 break;
      79             :         }
      80             : 
      81             :         default:
      82           0 :                 assert_not_reached("Unknown policy type");
      83             :         }
      84             : 
      85           0 :         item->policy_access.access = bus_kernel_translate_access(policy->access);
      86             : 
      87           0 :         return 0;
      88             : }
      89             : 
      90           0 : int bus_kernel_make_starter(
      91             :                 int fd,
      92             :                 const char *name,
      93             :                 bool activating,
      94             :                 bool accept_fd,
      95             :                 BusNamePolicy *policy,
      96             :                 BusPolicyAccess world_policy) {
      97             : 
      98           0 :         struct kdbus_cmd_free cmd_free = { .size = sizeof(cmd_free) };
      99             :         struct kdbus_cmd_hello *hello;
     100             :         struct kdbus_item *n;
     101           0 :         size_t policy_cnt = 0;
     102             :         BusNamePolicy *po;
     103             :         size_t size;
     104             :         int r;
     105             : 
     106           0 :         assert(fd >= 0);
     107           0 :         assert(name);
     108             : 
     109           0 :         LIST_FOREACH(policy, po, policy)
     110           0 :                 policy_cnt++;
     111             : 
     112           0 :         if (world_policy >= 0)
     113           0 :                 policy_cnt++;
     114             : 
     115           0 :         size = offsetof(struct kdbus_cmd_hello, items) +
     116           0 :                ALIGN8(offsetof(struct kdbus_item, str) + strlen(name) + 1) +
     117           0 :                policy_cnt * ALIGN8(offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access));
     118             : 
     119           0 :         hello = alloca0_align(size, 8);
     120             : 
     121           0 :         n = hello->items;
     122           0 :         strcpy(n->str, name);
     123           0 :         n->size = offsetof(struct kdbus_item, str) + strlen(n->str) + 1;
     124           0 :         n->type = KDBUS_ITEM_NAME;
     125           0 :         n = KDBUS_ITEM_NEXT(n);
     126             : 
     127           0 :         LIST_FOREACH(policy, po, policy) {
     128           0 :                 n->type = KDBUS_ITEM_POLICY_ACCESS;
     129           0 :                 n->size = offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access);
     130             : 
     131           0 :                 r = bus_kernel_translate_policy(po, n);
     132           0 :                 if (r < 0)
     133           0 :                         return r;
     134             : 
     135           0 :                 n = KDBUS_ITEM_NEXT(n);
     136             :         }
     137             : 
     138           0 :         if (world_policy >= 0) {
     139           0 :                 n->type = KDBUS_ITEM_POLICY_ACCESS;
     140           0 :                 n->size = offsetof(struct kdbus_item, policy_access) + sizeof(struct kdbus_policy_access);
     141           0 :                 n->policy_access.type = KDBUS_POLICY_ACCESS_WORLD;
     142           0 :                 n->policy_access.access = bus_kernel_translate_access(world_policy);
     143             :         }
     144             : 
     145           0 :         hello->size = size;
     146           0 :         hello->flags =
     147           0 :                 (activating ? KDBUS_HELLO_ACTIVATOR : KDBUS_HELLO_POLICY_HOLDER) |
     148           0 :                 (accept_fd ? KDBUS_HELLO_ACCEPT_FD : 0);
     149           0 :         hello->pool_size = KDBUS_POOL_SIZE;
     150           0 :         hello->attach_flags_send = _KDBUS_ATTACH_ANY;
     151           0 :         hello->attach_flags_recv = _KDBUS_ATTACH_ANY;
     152             : 
     153           0 :         if (ioctl(fd, KDBUS_CMD_HELLO, hello) < 0) {
     154           0 :                 if (errno == ENOTTY) /* Major API change */
     155           0 :                         return -ESOCKTNOSUPPORT;
     156           0 :                 return -errno;
     157             :         }
     158             : 
     159             :         /* not interested in any output values */
     160           0 :         cmd_free.offset = hello->offset;
     161           0 :         (void) ioctl(fd, KDBUS_CMD_FREE, &cmd_free);
     162             : 
     163             :         /* The higher 32bit of the bus_flags fields are considered
     164             :          * 'incompatible flags'. Refuse them all for now. */
     165           0 :         if (hello->bus_flags > 0xFFFFFFFFULL)
     166           0 :                 return -ESOCKTNOSUPPORT;
     167             : 
     168           0 :         return fd;
     169             : }
     170             : 
     171             : static const char* const bus_policy_access_table[_BUS_POLICY_ACCESS_MAX] = {
     172             :         [BUS_POLICY_ACCESS_SEE] = "see",
     173             :         [BUS_POLICY_ACCESS_TALK] = "talk",
     174             :         [BUS_POLICY_ACCESS_OWN] = "own",
     175             : };
     176             : 
     177          10 : DEFINE_STRING_TABLE_LOOKUP(bus_policy_access, BusPolicyAccess);

Generated by: LCOV version 1.11