LCOV - code coverage report
Current view: top level - core - dbus-execute.c (source / functions) Hit Total Coverage
Test: systemd test coverage Lines: 0 396 0.0 %
Date: 2015-07-29 18:47:03 Functions: 0 27 0.0 %

          Line data    Source code
       1             : /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
       2             : 
       3             : /***
       4             :   This file is part of systemd.
       5             : 
       6             :   Copyright 2010 Lennart Poettering
       7             : 
       8             :   systemd is free software; you can redistribute it and/or modify it
       9             :   under the terms of the GNU Lesser General Public License as published by
      10             :   the Free Software Foundation; either version 2.1 of the License, or
      11             :   (at your option) any later version.
      12             : 
      13             :   systemd is distributed in the hope that it will be useful, but
      14             :   WITHOUT ANY WARRANTY; without even the implied warranty of
      15             :   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
      16             :   Lesser General Public License for more details.
      17             : 
      18             :   You should have received a copy of the GNU Lesser General Public License
      19             :   along with systemd; If not, see <http://www.gnu.org/licenses/>.
      20             : ***/
      21             : 
      22             : #include <sys/prctl.h>
      23             : 
      24             : #ifdef HAVE_SECCOMP
      25             : #include <seccomp.h>
      26             : #endif
      27             : 
      28             : #include "bus-util.h"
      29             : #include "missing.h"
      30             : #include "ioprio.h"
      31             : #include "strv.h"
      32             : #include "fileio.h"
      33             : #include "execute.h"
      34             : #include "capability.h"
      35             : #include "env-util.h"
      36             : #include "af-list.h"
      37             : #include "namespace.h"
      38             : #include "path-util.h"
      39             : #include "dbus-execute.h"
      40             : 
      41             : #ifdef HAVE_SECCOMP
      42             : #include "seccomp-util.h"
      43             : #endif
      44             : 
      45           0 : BUS_DEFINE_PROPERTY_GET_ENUM(bus_property_get_exec_output, exec_output, ExecOutput);
      46             : 
      47           0 : static BUS_DEFINE_PROPERTY_GET_ENUM(property_get_exec_input, exec_input, ExecInput);
      48             : 
      49           0 : static BUS_DEFINE_PROPERTY_GET_ENUM(bus_property_get_protect_home, protect_home, ProtectHome);
      50           0 : static BUS_DEFINE_PROPERTY_GET_ENUM(bus_property_get_protect_system, protect_system, ProtectSystem);
      51             : 
      52           0 : static int property_get_environment_files(
      53             :                 sd_bus *bus,
      54             :                 const char *path,
      55             :                 const char *interface,
      56             :                 const char *property,
      57             :                 sd_bus_message *reply,
      58             :                 void *userdata,
      59             :                 sd_bus_error *error) {
      60             : 
      61           0 :         ExecContext *c = userdata;
      62             :         char **j;
      63             :         int r;
      64             : 
      65           0 :         assert(bus);
      66           0 :         assert(reply);
      67           0 :         assert(c);
      68             : 
      69           0 :         r = sd_bus_message_open_container(reply, 'a', "(sb)");
      70           0 :         if (r < 0)
      71           0 :                 return r;
      72             : 
      73           0 :         STRV_FOREACH(j, c->environment_files) {
      74           0 :                 const char *fn = *j;
      75             : 
      76           0 :                 r = sd_bus_message_append(reply, "(sb)", fn[0] == '-' ? fn + 1 : fn, fn[0] == '-');
      77           0 :                 if (r < 0)
      78           0 :                         return r;
      79             :         }
      80             : 
      81           0 :         return sd_bus_message_close_container(reply);
      82             : }
      83             : 
      84           0 : static int property_get_rlimit(
      85             :                 sd_bus *bus,
      86             :                 const char *path,
      87             :                 const char *interface,
      88             :                 const char *property,
      89             :                 sd_bus_message *reply,
      90             :                 void *userdata,
      91             :                 sd_bus_error *error) {
      92             : 
      93             :         struct rlimit *rl;
      94             :         uint64_t u;
      95             :         rlim_t x;
      96             : 
      97           0 :         assert(bus);
      98           0 :         assert(reply);
      99           0 :         assert(userdata);
     100             : 
     101           0 :         rl = *(struct rlimit**) userdata;
     102           0 :         if (rl)
     103           0 :                 x = rl->rlim_max;
     104             :         else {
     105           0 :                 struct rlimit buf = {};
     106             :                 int z;
     107             : 
     108           0 :                 z = rlimit_from_string(property);
     109           0 :                 assert(z >= 0);
     110             : 
     111           0 :                 getrlimit(z, &buf);
     112           0 :                 x = buf.rlim_max;
     113             :         }
     114             : 
     115             :         /* rlim_t might have different sizes, let's map
     116             :          * RLIMIT_INFINITY to (uint64_t) -1, so that it is the same on
     117             :          * all archs */
     118           0 :         u = x == RLIM_INFINITY ? (uint64_t) -1 : (uint64_t) x;
     119             : 
     120           0 :         return sd_bus_message_append(reply, "t", u);
     121             : }
     122             : 
     123           0 : static int property_get_oom_score_adjust(
     124             :                 sd_bus *bus,
     125             :                 const char *path,
     126             :                 const char *interface,
     127             :                 const char *property,
     128             :                 sd_bus_message *reply,
     129             :                 void *userdata,
     130             :                 sd_bus_error *error) {
     131             : 
     132             : 
     133           0 :         ExecContext *c = userdata;
     134             :         int32_t n;
     135             : 
     136           0 :         assert(bus);
     137           0 :         assert(reply);
     138           0 :         assert(c);
     139             : 
     140           0 :         if (c->oom_score_adjust_set)
     141           0 :                 n = c->oom_score_adjust;
     142             :         else {
     143           0 :                 _cleanup_free_ char *t = NULL;
     144             : 
     145           0 :                 n = 0;
     146           0 :                 if (read_one_line_file("/proc/self/oom_score_adj", &t) >= 0)
     147           0 :                         safe_atoi(t, &n);
     148             :         }
     149             : 
     150           0 :         return sd_bus_message_append(reply, "i", n);
     151             : }
     152             : 
     153           0 : static int property_get_nice(
     154             :                 sd_bus *bus,
     155             :                 const char *path,
     156             :                 const char *interface,
     157             :                 const char *property,
     158             :                 sd_bus_message *reply,
     159             :                 void *userdata,
     160             :                 sd_bus_error *error) {
     161             : 
     162             : 
     163           0 :         ExecContext *c = userdata;
     164             :         int32_t n;
     165             : 
     166           0 :         assert(bus);
     167           0 :         assert(reply);
     168           0 :         assert(c);
     169             : 
     170           0 :         if (c->nice_set)
     171           0 :                 n = c->nice;
     172             :         else {
     173           0 :                 errno = 0;
     174           0 :                 n = getpriority(PRIO_PROCESS, 0);
     175           0 :                 if (errno != 0)
     176           0 :                         n = 0;
     177             :         }
     178             : 
     179           0 :         return sd_bus_message_append(reply, "i", n);
     180             : }
     181             : 
     182           0 : static int property_get_ioprio(
     183             :                 sd_bus *bus,
     184             :                 const char *path,
     185             :                 const char *interface,
     186             :                 const char *property,
     187             :                 sd_bus_message *reply,
     188             :                 void *userdata,
     189             :                 sd_bus_error *error) {
     190             : 
     191             : 
     192           0 :         ExecContext *c = userdata;
     193             :         int32_t n;
     194             : 
     195           0 :         assert(bus);
     196           0 :         assert(reply);
     197           0 :         assert(c);
     198             : 
     199           0 :         if (c->ioprio_set)
     200           0 :                 n = c->ioprio;
     201             :         else {
     202           0 :                 n = ioprio_get(IOPRIO_WHO_PROCESS, 0);
     203           0 :                 if (n < 0)
     204           0 :                         n = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_BE, 4);
     205             :         }
     206             : 
     207           0 :         return sd_bus_message_append(reply, "i", n);
     208             : }
     209             : 
     210           0 : static int property_get_cpu_sched_policy(
     211             :                 sd_bus *bus,
     212             :                 const char *path,
     213             :                 const char *interface,
     214             :                 const char *property,
     215             :                 sd_bus_message *reply,
     216             :                 void *userdata,
     217             :                 sd_bus_error *error) {
     218             : 
     219           0 :         ExecContext *c = userdata;
     220             :         int32_t n;
     221             : 
     222           0 :         assert(bus);
     223           0 :         assert(reply);
     224           0 :         assert(c);
     225             : 
     226           0 :         if (c->cpu_sched_set)
     227           0 :                 n = c->cpu_sched_policy;
     228             :         else {
     229           0 :                 n = sched_getscheduler(0);
     230           0 :                 if (n < 0)
     231           0 :                         n = SCHED_OTHER;
     232             :         }
     233             : 
     234           0 :         return sd_bus_message_append(reply, "i", n);
     235             : }
     236             : 
     237           0 : static int property_get_cpu_sched_priority(
     238             :                 sd_bus *bus,
     239             :                 const char *path,
     240             :                 const char *interface,
     241             :                 const char *property,
     242             :                 sd_bus_message *reply,
     243             :                 void *userdata,
     244             :                 sd_bus_error *error) {
     245             : 
     246           0 :         ExecContext *c = userdata;
     247             :         int32_t n;
     248             : 
     249           0 :         assert(bus);
     250           0 :         assert(reply);
     251           0 :         assert(c);
     252             : 
     253           0 :         if (c->cpu_sched_set)
     254           0 :                 n = c->cpu_sched_priority;
     255             :         else {
     256           0 :                 struct sched_param p = {};
     257             : 
     258           0 :                 if (sched_getparam(0, &p) >= 0)
     259           0 :                         n = p.sched_priority;
     260             :                 else
     261           0 :                         n = 0;
     262             :         }
     263             : 
     264           0 :         return sd_bus_message_append(reply, "i", n);
     265             : }
     266             : 
     267           0 : static int property_get_cpu_affinity(
     268             :                 sd_bus *bus,
     269             :                 const char *path,
     270             :                 const char *interface,
     271             :                 const char *property,
     272             :                 sd_bus_message *reply,
     273             :                 void *userdata,
     274             :                 sd_bus_error *error) {
     275             : 
     276           0 :         ExecContext *c = userdata;
     277             : 
     278           0 :         assert(bus);
     279           0 :         assert(reply);
     280           0 :         assert(c);
     281             : 
     282           0 :         if (c->cpuset)
     283           0 :                 return sd_bus_message_append_array(reply, 'y', c->cpuset, CPU_ALLOC_SIZE(c->cpuset_ncpus));
     284             :         else
     285           0 :                 return sd_bus_message_append_array(reply, 'y', NULL, 0);
     286             : }
     287             : 
     288           0 : static int property_get_timer_slack_nsec(
     289             :                 sd_bus *bus,
     290             :                 const char *path,
     291             :                 const char *interface,
     292             :                 const char *property,
     293             :                 sd_bus_message *reply,
     294             :                 void *userdata,
     295             :                 sd_bus_error *error) {
     296             : 
     297           0 :         ExecContext *c = userdata;
     298             :         uint64_t u;
     299             : 
     300           0 :         assert(bus);
     301           0 :         assert(reply);
     302           0 :         assert(c);
     303             : 
     304           0 :         if (c->timer_slack_nsec != NSEC_INFINITY)
     305           0 :                 u = (uint64_t) c->timer_slack_nsec;
     306             :         else
     307           0 :                 u = (uint64_t) prctl(PR_GET_TIMERSLACK);
     308             : 
     309           0 :         return sd_bus_message_append(reply, "t", u);
     310             : }
     311             : 
     312           0 : static int property_get_capability_bounding_set(
     313             :                 sd_bus *bus,
     314             :                 const char *path,
     315             :                 const char *interface,
     316             :                 const char *property,
     317             :                 sd_bus_message *reply,
     318             :                 void *userdata,
     319             :                 sd_bus_error *error) {
     320             : 
     321           0 :         ExecContext *c = userdata;
     322             : 
     323           0 :         assert(bus);
     324           0 :         assert(reply);
     325           0 :         assert(c);
     326             : 
     327             :         /* We store this negated internally, to match the kernel, but
     328             :          * we expose it normalized. */
     329           0 :         return sd_bus_message_append(reply, "t", ~c->capability_bounding_set_drop);
     330             : }
     331             : 
     332           0 : static int property_get_capabilities(
     333             :                 sd_bus *bus,
     334             :                 const char *path,
     335             :                 const char *interface,
     336             :                 const char *property,
     337             :                 sd_bus_message *reply,
     338             :                 void *userdata,
     339             :                 sd_bus_error *error) {
     340             : 
     341           0 :         ExecContext *c = userdata;
     342           0 :         _cleanup_cap_free_charp_ char *t = NULL;
     343             :         const char *s;
     344             : 
     345           0 :         assert(bus);
     346           0 :         assert(reply);
     347           0 :         assert(c);
     348             : 
     349           0 :         if (c->capabilities)
     350           0 :                 s = t = cap_to_text(c->capabilities, NULL);
     351             :         else
     352           0 :                 s = "";
     353             : 
     354           0 :         if (!s)
     355           0 :                 return -ENOMEM;
     356             : 
     357           0 :         return sd_bus_message_append(reply, "s", s);
     358             : }
     359             : 
     360           0 : static int property_get_syscall_filter(
     361             :                 sd_bus *bus,
     362             :                 const char *path,
     363             :                 const char *interface,
     364             :                 const char *property,
     365             :                 sd_bus_message *reply,
     366             :                 void *userdata,
     367             :                 sd_bus_error *error) {
     368             : 
     369           0 :         ExecContext *c = userdata;
     370           0 :         _cleanup_strv_free_ char **l = NULL;
     371             :         int r;
     372             : 
     373             : #ifdef HAVE_SECCOMP
     374             :         Iterator i;
     375             :         void *id;
     376             : #endif
     377             : 
     378           0 :         assert(bus);
     379           0 :         assert(reply);
     380           0 :         assert(c);
     381             : 
     382           0 :         r = sd_bus_message_open_container(reply, 'r', "bas");
     383           0 :         if (r < 0)
     384           0 :                 return r;
     385             : 
     386           0 :         r = sd_bus_message_append(reply, "b", c->syscall_whitelist);
     387           0 :         if (r < 0)
     388           0 :                 return r;
     389             : 
     390             : #ifdef HAVE_SECCOMP
     391           0 :         SET_FOREACH(id, c->syscall_filter, i) {
     392             :                 char *name;
     393             : 
     394           0 :                 name = seccomp_syscall_resolve_num_arch(SCMP_ARCH_NATIVE, PTR_TO_INT(id) - 1);
     395           0 :                 if (!name)
     396           0 :                         continue;
     397             : 
     398           0 :                 r = strv_consume(&l, name);
     399           0 :                 if (r < 0)
     400           0 :                         return r;
     401             :         }
     402             : #endif
     403             : 
     404           0 :         strv_sort(l);
     405             : 
     406           0 :         r = sd_bus_message_append_strv(reply, l);
     407           0 :         if (r < 0)
     408           0 :                 return r;
     409             : 
     410           0 :         return sd_bus_message_close_container(reply);
     411             : }
     412             : 
     413           0 : static int property_get_syscall_archs(
     414             :                 sd_bus *bus,
     415             :                 const char *path,
     416             :                 const char *interface,
     417             :                 const char *property,
     418             :                 sd_bus_message *reply,
     419             :                 void *userdata,
     420             :                 sd_bus_error *error) {
     421             : 
     422           0 :         ExecContext *c = userdata;
     423           0 :         _cleanup_strv_free_ char **l = NULL;
     424             :         int r;
     425             : 
     426             : #ifdef HAVE_SECCOMP
     427             :         Iterator i;
     428             :         void *id;
     429             : #endif
     430             : 
     431           0 :         assert(bus);
     432           0 :         assert(reply);
     433           0 :         assert(c);
     434             : 
     435             : #ifdef HAVE_SECCOMP
     436           0 :         SET_FOREACH(id, c->syscall_archs, i) {
     437             :                 const char *name;
     438             : 
     439           0 :                 name = seccomp_arch_to_string(PTR_TO_UINT32(id) - 1);
     440           0 :                 if (!name)
     441           0 :                         continue;
     442             : 
     443           0 :                 r = strv_extend(&l, name);
     444           0 :                 if (r < 0)
     445           0 :                         return -ENOMEM;
     446             :         }
     447             : #endif
     448             : 
     449           0 :         strv_sort(l);
     450             : 
     451           0 :         r = sd_bus_message_append_strv(reply, l);
     452           0 :         if (r < 0)
     453           0 :                 return r;
     454             : 
     455           0 :         return 0;
     456             : }
     457             : 
     458           0 : static int property_get_syscall_errno(
     459             :                 sd_bus *bus,
     460             :                 const char *path,
     461             :                 const char *interface,
     462             :                 const char *property,
     463             :                 sd_bus_message *reply,
     464             :                 void *userdata,
     465             :                 sd_bus_error *error) {
     466             : 
     467           0 :         ExecContext *c = userdata;
     468             : 
     469           0 :         assert(bus);
     470           0 :         assert(reply);
     471           0 :         assert(c);
     472             : 
     473           0 :         return sd_bus_message_append(reply, "i", (int32_t) c->syscall_errno);
     474             : }
     475             : 
     476           0 : static int property_get_selinux_context(
     477             :                 sd_bus *bus,
     478             :                 const char *path,
     479             :                 const char *interface,
     480             :                 const char *property,
     481             :                 sd_bus_message *reply,
     482             :                 void *userdata,
     483             :                 sd_bus_error *error) {
     484             : 
     485           0 :         ExecContext *c = userdata;
     486             : 
     487           0 :         assert(bus);
     488           0 :         assert(reply);
     489           0 :         assert(c);
     490             : 
     491           0 :         return sd_bus_message_append(reply, "(bs)", c->selinux_context_ignore, c->selinux_context);
     492             : }
     493             : 
     494           0 : static int property_get_apparmor_profile(
     495             :                 sd_bus *bus,
     496             :                 const char *path,
     497             :                 const char *interface,
     498             :                 const char *property,
     499             :                 sd_bus_message *reply,
     500             :                 void *userdata,
     501             :                 sd_bus_error *error) {
     502             : 
     503           0 :         ExecContext *c = userdata;
     504             : 
     505           0 :         assert(bus);
     506           0 :         assert(reply);
     507           0 :         assert(c);
     508             : 
     509           0 :         return sd_bus_message_append(reply, "(bs)", c->apparmor_profile_ignore, c->apparmor_profile);
     510             : }
     511             : 
     512           0 : static int property_get_smack_process_label(
     513             :                 sd_bus *bus,
     514             :                 const char *path,
     515             :                 const char *interface,
     516             :                 const char *property,
     517             :                 sd_bus_message *reply,
     518             :                 void *userdata,
     519             :                 sd_bus_error *error) {
     520             : 
     521           0 :         ExecContext *c = userdata;
     522             : 
     523           0 :         assert(bus);
     524           0 :         assert(reply);
     525           0 :         assert(c);
     526             : 
     527           0 :         return sd_bus_message_append(reply, "(bs)", c->smack_process_label_ignore, c->smack_process_label);
     528             : }
     529             : 
     530           0 : static int property_get_personality(
     531             :                 sd_bus *bus,
     532             :                 const char *path,
     533             :                 const char *interface,
     534             :                 const char *property,
     535             :                 sd_bus_message *reply,
     536             :                 void *userdata,
     537             :                 sd_bus_error *error) {
     538             : 
     539           0 :         ExecContext *c = userdata;
     540             : 
     541           0 :         assert(bus);
     542           0 :         assert(reply);
     543           0 :         assert(c);
     544             : 
     545           0 :         return sd_bus_message_append(reply, "s", personality_to_string(c->personality));
     546             : }
     547             : 
     548           0 : static int property_get_address_families(
     549             :                 sd_bus *bus,
     550             :                 const char *path,
     551             :                 const char *interface,
     552             :                 const char *property,
     553             :                 sd_bus_message *reply,
     554             :                 void *userdata,
     555             :                 sd_bus_error *error) {
     556             : 
     557           0 :         ExecContext *c = userdata;
     558           0 :         _cleanup_strv_free_ char **l = NULL;
     559             :         Iterator i;
     560             :         void *af;
     561             :         int r;
     562             : 
     563           0 :         assert(bus);
     564           0 :         assert(reply);
     565           0 :         assert(c);
     566             : 
     567           0 :         r = sd_bus_message_open_container(reply, 'r', "bas");
     568           0 :         if (r < 0)
     569           0 :                 return r;
     570             : 
     571           0 :         r = sd_bus_message_append(reply, "b", c->address_families_whitelist);
     572           0 :         if (r < 0)
     573           0 :                 return r;
     574             : 
     575           0 :         SET_FOREACH(af, c->address_families, i) {
     576             :                 const char *name;
     577             : 
     578           0 :                 name = af_to_name(PTR_TO_INT(af));
     579           0 :                 if (!name)
     580           0 :                         continue;
     581             : 
     582           0 :                 r = strv_extend(&l, name);
     583           0 :                 if (r < 0)
     584           0 :                         return -ENOMEM;
     585             :         }
     586             : 
     587           0 :         strv_sort(l);
     588             : 
     589           0 :         r = sd_bus_message_append_strv(reply, l);
     590           0 :         if (r < 0)
     591           0 :                 return r;
     592             : 
     593           0 :         return sd_bus_message_close_container(reply);
     594             : }
     595             : 
     596             : const sd_bus_vtable bus_exec_vtable[] = {
     597             :         SD_BUS_VTABLE_START(0),
     598             :         SD_BUS_PROPERTY("Environment", "as", NULL, offsetof(ExecContext, environment), SD_BUS_VTABLE_PROPERTY_CONST),
     599             :         SD_BUS_PROPERTY("EnvironmentFiles", "a(sb)", property_get_environment_files, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     600             :         SD_BUS_PROPERTY("UMask", "u", bus_property_get_mode, offsetof(ExecContext, umask), SD_BUS_VTABLE_PROPERTY_CONST),
     601             :         SD_BUS_PROPERTY("LimitCPU", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_CPU]), SD_BUS_VTABLE_PROPERTY_CONST),
     602             :         SD_BUS_PROPERTY("LimitFSIZE", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_FSIZE]), SD_BUS_VTABLE_PROPERTY_CONST),
     603             :         SD_BUS_PROPERTY("LimitDATA", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_DATA]), SD_BUS_VTABLE_PROPERTY_CONST),
     604             :         SD_BUS_PROPERTY("LimitSTACK", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_STACK]), SD_BUS_VTABLE_PROPERTY_CONST),
     605             :         SD_BUS_PROPERTY("LimitCORE", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_CORE]), SD_BUS_VTABLE_PROPERTY_CONST),
     606             :         SD_BUS_PROPERTY("LimitRSS", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_RSS]), SD_BUS_VTABLE_PROPERTY_CONST),
     607             :         SD_BUS_PROPERTY("LimitNOFILE", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_NOFILE]), SD_BUS_VTABLE_PROPERTY_CONST),
     608             :         SD_BUS_PROPERTY("LimitAS", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_AS]), SD_BUS_VTABLE_PROPERTY_CONST),
     609             :         SD_BUS_PROPERTY("LimitNPROC", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_NPROC]), SD_BUS_VTABLE_PROPERTY_CONST),
     610             :         SD_BUS_PROPERTY("LimitMEMLOCK", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_MEMLOCK]), SD_BUS_VTABLE_PROPERTY_CONST),
     611             :         SD_BUS_PROPERTY("LimitLOCKS", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_LOCKS]), SD_BUS_VTABLE_PROPERTY_CONST),
     612             :         SD_BUS_PROPERTY("LimitSIGPENDING", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_SIGPENDING]), SD_BUS_VTABLE_PROPERTY_CONST),
     613             :         SD_BUS_PROPERTY("LimitMSGQUEUE", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_MSGQUEUE]), SD_BUS_VTABLE_PROPERTY_CONST),
     614             :         SD_BUS_PROPERTY("LimitNICE", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_NICE]), SD_BUS_VTABLE_PROPERTY_CONST),
     615             :         SD_BUS_PROPERTY("LimitRTPRIO", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_RTPRIO]), SD_BUS_VTABLE_PROPERTY_CONST),
     616             :         SD_BUS_PROPERTY("LimitRTTIME", "t", property_get_rlimit, offsetof(ExecContext, rlimit[RLIMIT_RTTIME]), SD_BUS_VTABLE_PROPERTY_CONST),
     617             :         SD_BUS_PROPERTY("WorkingDirectory", "s", NULL, offsetof(ExecContext, working_directory), SD_BUS_VTABLE_PROPERTY_CONST),
     618             :         SD_BUS_PROPERTY("RootDirectory", "s", NULL, offsetof(ExecContext, root_directory), SD_BUS_VTABLE_PROPERTY_CONST),
     619             :         SD_BUS_PROPERTY("OOMScoreAdjust", "i", property_get_oom_score_adjust, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     620             :         SD_BUS_PROPERTY("Nice", "i", property_get_nice, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     621             :         SD_BUS_PROPERTY("IOScheduling", "i", property_get_ioprio, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     622             :         SD_BUS_PROPERTY("CPUSchedulingPolicy", "i", property_get_cpu_sched_policy, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     623             :         SD_BUS_PROPERTY("CPUSchedulingPriority", "i", property_get_cpu_sched_priority, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     624             :         SD_BUS_PROPERTY("CPUAffinity", "ay", property_get_cpu_affinity, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     625             :         SD_BUS_PROPERTY("TimerSlackNSec", "t", property_get_timer_slack_nsec, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     626             :         SD_BUS_PROPERTY("CPUSchedulingResetOnFork", "b", bus_property_get_bool, offsetof(ExecContext, cpu_sched_reset_on_fork), SD_BUS_VTABLE_PROPERTY_CONST),
     627             :         SD_BUS_PROPERTY("NonBlocking", "b", bus_property_get_bool, offsetof(ExecContext, non_blocking), SD_BUS_VTABLE_PROPERTY_CONST),
     628             :         SD_BUS_PROPERTY("StandardInput", "s", property_get_exec_input, offsetof(ExecContext, std_input), SD_BUS_VTABLE_PROPERTY_CONST),
     629             :         SD_BUS_PROPERTY("StandardOutput", "s", bus_property_get_exec_output, offsetof(ExecContext, std_output), SD_BUS_VTABLE_PROPERTY_CONST),
     630             :         SD_BUS_PROPERTY("StandardError", "s", bus_property_get_exec_output, offsetof(ExecContext, std_error), SD_BUS_VTABLE_PROPERTY_CONST),
     631             :         SD_BUS_PROPERTY("TTYPath", "s", NULL, offsetof(ExecContext, tty_path), SD_BUS_VTABLE_PROPERTY_CONST),
     632             :         SD_BUS_PROPERTY("TTYReset", "b", bus_property_get_bool, offsetof(ExecContext, tty_reset), SD_BUS_VTABLE_PROPERTY_CONST),
     633             :         SD_BUS_PROPERTY("TTYVHangup", "b", bus_property_get_bool, offsetof(ExecContext, tty_vhangup), SD_BUS_VTABLE_PROPERTY_CONST),
     634             :         SD_BUS_PROPERTY("TTYVTDisallocate", "b", bus_property_get_bool, offsetof(ExecContext, tty_vt_disallocate), SD_BUS_VTABLE_PROPERTY_CONST),
     635             :         SD_BUS_PROPERTY("SyslogPriority", "i", bus_property_get_int, offsetof(ExecContext, syslog_priority), SD_BUS_VTABLE_PROPERTY_CONST),
     636             :         SD_BUS_PROPERTY("SyslogIdentifier", "s", NULL, offsetof(ExecContext, syslog_identifier), SD_BUS_VTABLE_PROPERTY_CONST),
     637             :         SD_BUS_PROPERTY("SyslogLevelPrefix", "b", bus_property_get_bool, offsetof(ExecContext, syslog_level_prefix), SD_BUS_VTABLE_PROPERTY_CONST),
     638             :         SD_BUS_PROPERTY("Capabilities", "s", property_get_capabilities, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     639             :         SD_BUS_PROPERTY("SecureBits", "i", bus_property_get_int, offsetof(ExecContext, secure_bits), SD_BUS_VTABLE_PROPERTY_CONST),
     640             :         SD_BUS_PROPERTY("CapabilityBoundingSet", "t", property_get_capability_bounding_set, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     641             :         SD_BUS_PROPERTY("User", "s", NULL, offsetof(ExecContext, user), SD_BUS_VTABLE_PROPERTY_CONST),
     642             :         SD_BUS_PROPERTY("Group", "s", NULL, offsetof(ExecContext, group), SD_BUS_VTABLE_PROPERTY_CONST),
     643             :         SD_BUS_PROPERTY("SupplementaryGroups", "as", NULL, offsetof(ExecContext, supplementary_groups), SD_BUS_VTABLE_PROPERTY_CONST),
     644             :         SD_BUS_PROPERTY("PAMName", "s", NULL, offsetof(ExecContext, pam_name), SD_BUS_VTABLE_PROPERTY_CONST),
     645             :         SD_BUS_PROPERTY("ReadWriteDirectories", "as", NULL, offsetof(ExecContext, read_write_dirs), SD_BUS_VTABLE_PROPERTY_CONST),
     646             :         SD_BUS_PROPERTY("ReadOnlyDirectories", "as", NULL, offsetof(ExecContext, read_only_dirs), SD_BUS_VTABLE_PROPERTY_CONST),
     647             :         SD_BUS_PROPERTY("InaccessibleDirectories", "as", NULL, offsetof(ExecContext, inaccessible_dirs), SD_BUS_VTABLE_PROPERTY_CONST),
     648             :         SD_BUS_PROPERTY("MountFlags", "t", bus_property_get_ulong, offsetof(ExecContext, mount_flags), SD_BUS_VTABLE_PROPERTY_CONST),
     649             :         SD_BUS_PROPERTY("PrivateTmp", "b", bus_property_get_bool, offsetof(ExecContext, private_tmp), SD_BUS_VTABLE_PROPERTY_CONST),
     650             :         SD_BUS_PROPERTY("PrivateNetwork", "b", bus_property_get_bool, offsetof(ExecContext, private_network), SD_BUS_VTABLE_PROPERTY_CONST),
     651             :         SD_BUS_PROPERTY("PrivateDevices", "b", bus_property_get_bool, offsetof(ExecContext, private_devices), SD_BUS_VTABLE_PROPERTY_CONST),
     652             :         SD_BUS_PROPERTY("ProtectHome", "s", bus_property_get_protect_home, offsetof(ExecContext, protect_home), SD_BUS_VTABLE_PROPERTY_CONST),
     653             :         SD_BUS_PROPERTY("ProtectSystem", "s", bus_property_get_protect_system, offsetof(ExecContext, protect_system), SD_BUS_VTABLE_PROPERTY_CONST),
     654             :         SD_BUS_PROPERTY("SameProcessGroup", "b", bus_property_get_bool, offsetof(ExecContext, same_pgrp), SD_BUS_VTABLE_PROPERTY_CONST),
     655             :         SD_BUS_PROPERTY("UtmpIdentifier", "s", NULL, offsetof(ExecContext, utmp_id), SD_BUS_VTABLE_PROPERTY_CONST),
     656             :         SD_BUS_PROPERTY("SELinuxContext", "(bs)", property_get_selinux_context, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     657             :         SD_BUS_PROPERTY("AppArmorProfile", "(bs)", property_get_apparmor_profile, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     658             :         SD_BUS_PROPERTY("SmackProcessLabel", "(bs)", property_get_smack_process_label, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     659             :         SD_BUS_PROPERTY("IgnoreSIGPIPE", "b", bus_property_get_bool, offsetof(ExecContext, ignore_sigpipe), SD_BUS_VTABLE_PROPERTY_CONST),
     660             :         SD_BUS_PROPERTY("NoNewPrivileges", "b", bus_property_get_bool, offsetof(ExecContext, no_new_privileges), SD_BUS_VTABLE_PROPERTY_CONST),
     661             :         SD_BUS_PROPERTY("SystemCallFilter", "(bas)", property_get_syscall_filter, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     662             :         SD_BUS_PROPERTY("SystemCallArchitectures", "as", property_get_syscall_archs, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     663             :         SD_BUS_PROPERTY("SystemCallErrorNumber", "i", property_get_syscall_errno, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     664             :         SD_BUS_PROPERTY("Personality", "s", property_get_personality, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     665             :         SD_BUS_PROPERTY("RestrictAddressFamilies", "(bas)", property_get_address_families, 0, SD_BUS_VTABLE_PROPERTY_CONST),
     666             :         SD_BUS_PROPERTY("RuntimeDirectoryMode", "u", bus_property_get_mode, offsetof(ExecContext, runtime_directory_mode), SD_BUS_VTABLE_PROPERTY_CONST),
     667             :         SD_BUS_PROPERTY("RuntimeDirectory", "as", NULL, offsetof(ExecContext, runtime_directory), SD_BUS_VTABLE_PROPERTY_CONST),
     668             :         SD_BUS_VTABLE_END
     669             : };
     670             : 
     671           0 : static int append_exec_command(sd_bus_message *reply, ExecCommand *c) {
     672             :         int r;
     673             : 
     674           0 :         assert(reply);
     675           0 :         assert(c);
     676             : 
     677           0 :         if (!c->path)
     678           0 :                 return 0;
     679             : 
     680           0 :         r = sd_bus_message_open_container(reply, 'r', "sasbttttuii");
     681           0 :         if (r < 0)
     682           0 :                 return r;
     683             : 
     684           0 :         r = sd_bus_message_append(reply, "s", c->path);
     685           0 :         if (r < 0)
     686           0 :                 return r;
     687             : 
     688           0 :         r = sd_bus_message_append_strv(reply, c->argv);
     689           0 :         if (r < 0)
     690           0 :                 return r;
     691             : 
     692           0 :         r = sd_bus_message_append(reply, "bttttuii",
     693           0 :                                   c->ignore,
     694             :                                   c->exec_status.start_timestamp.realtime,
     695             :                                   c->exec_status.start_timestamp.monotonic,
     696             :                                   c->exec_status.exit_timestamp.realtime,
     697             :                                   c->exec_status.exit_timestamp.monotonic,
     698           0 :                                   (uint32_t) c->exec_status.pid,
     699             :                                   (int32_t) c->exec_status.code,
     700             :                                   (int32_t) c->exec_status.status);
     701           0 :         if (r < 0)
     702           0 :                 return r;
     703             : 
     704           0 :         return sd_bus_message_close_container(reply);
     705             : }
     706             : 
     707           0 : int bus_property_get_exec_command(
     708             :                 sd_bus *bus,
     709             :                 const char *path,
     710             :                 const char *interface,
     711             :                 const char *property,
     712             :                 sd_bus_message *reply,
     713             :                 void *userdata,
     714             :                 sd_bus_error *ret_error) {
     715             : 
     716           0 :         ExecCommand *c = (ExecCommand*) userdata;
     717             :         int r;
     718             : 
     719           0 :         assert(bus);
     720           0 :         assert(reply);
     721             : 
     722           0 :         r = sd_bus_message_open_container(reply, 'a', "(sasbttttuii)");
     723           0 :         if (r < 0)
     724           0 :                 return r;
     725             : 
     726           0 :         r = append_exec_command(reply, c);
     727           0 :         if (r < 0)
     728           0 :                 return r;
     729             : 
     730           0 :         return sd_bus_message_close_container(reply);
     731             : }
     732             : 
     733           0 : int bus_property_get_exec_command_list(
     734             :                 sd_bus *bus,
     735             :                 const char *path,
     736             :                 const char *interface,
     737             :                 const char *property,
     738             :                 sd_bus_message *reply,
     739             :                 void *userdata,
     740             :                 sd_bus_error *ret_error) {
     741             : 
     742           0 :         ExecCommand *c = *(ExecCommand**) userdata;
     743             :         int r;
     744             : 
     745           0 :         assert(bus);
     746           0 :         assert(reply);
     747             : 
     748           0 :         r = sd_bus_message_open_container(reply, 'a', "(sasbttttuii)");
     749           0 :         if (r < 0)
     750           0 :                 return r;
     751             : 
     752           0 :         LIST_FOREACH(command, c, c) {
     753           0 :                 r = append_exec_command(reply, c);
     754           0 :                 if (r < 0)
     755           0 :                         return r;
     756             :         }
     757             : 
     758           0 :         return sd_bus_message_close_container(reply);
     759             : }
     760             : 
     761           0 : int bus_exec_context_set_transient_property(
     762             :                 Unit *u,
     763             :                 ExecContext *c,
     764             :                 const char *name,
     765             :                 sd_bus_message *message,
     766             :                 UnitSetPropertiesMode mode,
     767             :                 sd_bus_error *error) {
     768             : 
     769             :         int r;
     770             : 
     771           0 :         assert(u);
     772           0 :         assert(c);
     773           0 :         assert(name);
     774           0 :         assert(message);
     775             : 
     776           0 :         if (streq(name, "User")) {
     777             :                 const char *uu;
     778             : 
     779           0 :                 r = sd_bus_message_read(message, "s", &uu);
     780           0 :                 if (r < 0)
     781           0 :                         return r;
     782             : 
     783           0 :                 if (mode != UNIT_CHECK) {
     784             : 
     785           0 :                         if (isempty(uu)) {
     786           0 :                                 free(c->user);
     787           0 :                                 c->user = NULL;
     788             :                         } else {
     789             :                                 char *t;
     790             : 
     791           0 :                                 t = strdup(uu);
     792           0 :                                 if (!t)
     793           0 :                                         return -ENOMEM;
     794             : 
     795           0 :                                 free(c->user);
     796           0 :                                 c->user = t;
     797             :                         }
     798             : 
     799           0 :                         unit_write_drop_in_private_format(u, mode, name, "User=%s\n", uu);
     800             :                 }
     801             : 
     802           0 :                 return 1;
     803             : 
     804           0 :         } else if (streq(name, "Group")) {
     805             :                 const char *gg;
     806             : 
     807           0 :                 r = sd_bus_message_read(message, "s", &gg);
     808           0 :                 if (r < 0)
     809           0 :                         return r;
     810             : 
     811           0 :                 if (mode != UNIT_CHECK) {
     812             : 
     813           0 :                         if (isempty(gg)) {
     814           0 :                                 free(c->group);
     815           0 :                                 c->group = NULL;
     816             :                         } else {
     817             :                                 char *t;
     818             : 
     819           0 :                                 t = strdup(gg);
     820           0 :                                 if (!t)
     821           0 :                                         return -ENOMEM;
     822             : 
     823           0 :                                 free(c->group);
     824           0 :                                 c->group = t;
     825             :                         }
     826             : 
     827           0 :                         unit_write_drop_in_private_format(u, mode, name, "Group=%s\n", gg);
     828             :                 }
     829             : 
     830           0 :                 return 1;
     831             : 
     832           0 :         } else if (streq(name, "Nice")) {
     833             :                 int n;
     834             : 
     835           0 :                 r = sd_bus_message_read(message, "i", &n);
     836           0 :                 if (r < 0)
     837           0 :                         return r;
     838             : 
     839           0 :                 if (n < PRIO_MIN || n >= PRIO_MAX)
     840           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Nice value out of range");
     841             : 
     842           0 :                 if (mode != UNIT_CHECK) {
     843           0 :                         c->nice = n;
     844           0 :                         unit_write_drop_in_private_format(u, mode, name, "Nice=%i\n", n);
     845             :                 }
     846             : 
     847           0 :                 return 1;
     848             : 
     849           0 :         } else if (streq(name, "TTYPath")) {
     850             :                 const char *tty;
     851             : 
     852           0 :                 r = sd_bus_message_read(message, "s", &tty);
     853           0 :                 if (r < 0)
     854           0 :                         return r;
     855             : 
     856           0 :                 if (!path_is_absolute(tty))
     857           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "TTY device not absolute path");
     858             : 
     859           0 :                 if (mode != UNIT_CHECK) {
     860             :                         char *t;
     861             : 
     862           0 :                         t = strdup(tty);
     863           0 :                         if (!t)
     864           0 :                                 return -ENOMEM;
     865             : 
     866           0 :                         free(c->tty_path);
     867           0 :                         c->tty_path = t;
     868             : 
     869           0 :                         unit_write_drop_in_private_format(u, mode, name, "TTYPath=%s\n", tty);
     870             :                 }
     871             : 
     872           0 :                 return 1;
     873             : 
     874           0 :         } else if (streq(name, "StandardInput")) {
     875             :                 const char *s;
     876             :                 ExecInput p;
     877             : 
     878           0 :                 r = sd_bus_message_read(message, "s", &s);
     879           0 :                 if (r < 0)
     880           0 :                         return r;
     881             : 
     882           0 :                 p = exec_input_from_string(s);
     883           0 :                 if (p < 0)
     884           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid standard input name");
     885             : 
     886           0 :                 if (mode != UNIT_CHECK) {
     887           0 :                         c->std_input = p;
     888             : 
     889           0 :                         unit_write_drop_in_private_format(u, mode, name, "StandardInput=%s\n", exec_input_to_string(p));
     890             :                 }
     891             : 
     892           0 :                 return 1;
     893             : 
     894             : 
     895           0 :         } else if (streq(name, "StandardOutput")) {
     896             :                 const char *s;
     897             :                 ExecOutput p;
     898             : 
     899           0 :                 r = sd_bus_message_read(message, "s", &s);
     900           0 :                 if (r < 0)
     901           0 :                         return r;
     902             : 
     903           0 :                 p = exec_output_from_string(s);
     904           0 :                 if (p < 0)
     905           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid standard output name");
     906             : 
     907           0 :                 if (mode != UNIT_CHECK) {
     908           0 :                         c->std_output = p;
     909             : 
     910           0 :                         unit_write_drop_in_private_format(u, mode, name, "StandardOutput=%s\n", exec_output_to_string(p));
     911             :                 }
     912             : 
     913           0 :                 return 1;
     914             : 
     915           0 :         } else if (streq(name, "StandardError")) {
     916             :                 const char *s;
     917             :                 ExecOutput p;
     918             : 
     919           0 :                 r = sd_bus_message_read(message, "s", &s);
     920           0 :                 if (r < 0)
     921           0 :                         return r;
     922             : 
     923           0 :                 p = exec_output_from_string(s);
     924           0 :                 if (p < 0)
     925           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid standard error name");
     926             : 
     927           0 :                 if (mode != UNIT_CHECK) {
     928           0 :                         c->std_error = p;
     929             : 
     930           0 :                         unit_write_drop_in_private_format(u, mode, name, "StandardError=%s\n", exec_output_to_string(p));
     931             :                 }
     932             : 
     933           0 :                 return 1;
     934             : 
     935           0 :         } else if (streq(name, "Environment")) {
     936             : 
     937           0 :                 _cleanup_strv_free_ char **l = NULL;
     938             : 
     939           0 :                 r = sd_bus_message_read_strv(message, &l);
     940           0 :                 if (r < 0)
     941           0 :                         return r;
     942             : 
     943           0 :                 if (!strv_env_is_valid(l))
     944           0 :                         return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid environment block.");
     945             : 
     946           0 :                 if (mode != UNIT_CHECK) {
     947           0 :                         _cleanup_free_ char *joined = NULL;
     948             :                         char **e;
     949             : 
     950           0 :                         e = strv_env_merge(2, c->environment, l);
     951           0 :                         if (!e)
     952           0 :                                 return -ENOMEM;
     953             : 
     954           0 :                         strv_free(c->environment);
     955           0 :                         c->environment = e;
     956             : 
     957           0 :                         joined = strv_join_quoted(c->environment);
     958           0 :                         if (!joined)
     959           0 :                                 return -ENOMEM;
     960             : 
     961           0 :                         unit_write_drop_in_private_format(u, mode, name, "Environment=%s\n", joined);
     962             :                 }
     963             : 
     964           0 :                 return 1;
     965             : 
     966           0 :         } else if (rlimit_from_string(name) >= 0) {
     967             :                 uint64_t rl;
     968             :                 rlim_t x;
     969             : 
     970           0 :                 r = sd_bus_message_read(message, "t", &rl);
     971           0 :                 if (r < 0)
     972           0 :                         return r;
     973             : 
     974           0 :                 if (rl == (uint64_t) -1)
     975           0 :                         x = RLIM_INFINITY;
     976             :                 else {
     977           0 :                         x = (rlim_t) rl;
     978             : 
     979           0 :                         if ((uint64_t) x != rl)
     980           0 :                                 return -ERANGE;
     981             :                 }
     982             : 
     983           0 :                 if (mode != UNIT_CHECK) {
     984             :                         int z;
     985             : 
     986           0 :                         z = rlimit_from_string(name);
     987             : 
     988           0 :                         if (!c->rlimit[z]) {
     989           0 :                                 c->rlimit[z] = new(struct rlimit, 1);
     990           0 :                                 if (!c->rlimit[z])
     991           0 :                                         return -ENOMEM;
     992             :                         }
     993             : 
     994           0 :                         c->rlimit[z]->rlim_cur = c->rlimit[z]->rlim_max = x;
     995             : 
     996           0 :                         if (x == RLIM_INFINITY)
     997           0 :                                 unit_write_drop_in_private_format(u, mode, name, "%s=infinity\n", name);
     998             :                         else
     999           0 :                                 unit_write_drop_in_private_format(u, mode, name, "%s=%" PRIu64 "\n", name, rl);
    1000             :                 }
    1001             : 
    1002           0 :                 return 1;
    1003             :         }
    1004             : 
    1005           0 :         return 0;
    1006             : }

Generated by: LCOV version 1.11