]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/shared/varlink-io.systemd.service.c
675f949929ee435b541609aa5cd76eaa4c509599
[thirdparty/systemd.git] / src / shared / varlink-io.systemd.service.c
1 /* SPDX-License-Identifier: GPL-2.0-or-later */
2
3 #include <unistd.h>
4
5 #include "varlink-io.systemd.service.h"
6
7 static VARLINK_DEFINE_METHOD(Ping);
8
9 static VARLINK_DEFINE_METHOD(Reload);
10
11 static VARLINK_DEFINE_METHOD(
12 SetLogLevel,
13 VARLINK_DEFINE_INPUT(level, VARLINK_INT, 0));
14
15 VARLINK_DEFINE_INTERFACE(
16 io_systemd_service,
17 "io.systemd.service",
18 &vl_method_Ping,
19 &vl_method_Reload,
20 &vl_method_SetLogLevel);
21
22 int varlink_method_ping(Varlink *link, JsonVariant *parameters, VarlinkMethodFlags flags, void *userdata) {
23 assert(link);
24
25 if (json_variant_elements(parameters) > 0)
26 return varlink_error_invalid_parameter(link, parameters);
27
28 log_debug("Received io.systemd.service.Ping");
29
30 return varlink_reply(link, NULL);
31 }
32
33 int varlink_method_set_log_level(Varlink *link, JsonVariant *parameters, VarlinkMethodFlags flags, void *userdata) {
34 static const JsonDispatch dispatch_table[] = {
35 {"level", JSON_VARIANT_INTEGER, json_dispatch_int64, 0, JSON_MANDATORY},
36 {}
37 };
38
39 int64_t level;
40 uid_t uid;
41 int r;
42
43 assert(link);
44 assert(parameters);
45
46 /* NOTE: The method does have 1 parameter, but we must compare to 2 here, because
47 * json_variant_elements() breaks abstraction and exposes internal structure of JsonObject. */
48 if (json_variant_elements(parameters) != 2)
49 return varlink_error_invalid_parameter(link, parameters);
50
51 r = json_dispatch(parameters, dispatch_table, NULL, 0, &level);
52 if (r < 0)
53 return r;
54
55 if (LOG_PRI(level) != level)
56 return varlink_error_invalid_parameter(link, parameters);
57
58 r = varlink_get_peer_uid(link, &uid);
59 if (r < 0)
60 return r;
61
62 if (uid != getuid() && uid != 0)
63 return varlink_error(link, VARLINK_ERROR_PERMISSION_DENIED, parameters);
64
65 log_debug("Received io.systemd.service.SetLogLevel(%" PRIi64 ")", level);
66
67 log_set_max_level(level);
68
69 return varlink_reply(link, NULL);
70 }