aboutgitcodelistschat:MatrixIRC
diff options
context:
space:
mode:
authorAlice Frosi <afrosi@redhat.com>2023-09-01 10:16:36 +0200
committerAlice Frosi <afrosi@redhat.com>2023-09-01 10:37:04 +0200
commit59f7f7c241253293c25e001c9340f1deeb138311 (patch)
tree4be7c160cbec552f5d5d3dcd88e85c1b98407749
parentaecd6adbd2f5ce12437215fe2e64e004d28db86b (diff)
downloadseitan-59f7f7c241253293c25e001c9340f1deeb138311.tar
seitan-59f7f7c241253293c25e001c9340f1deeb138311.tar.gz
seitan-59f7f7c241253293c25e001c9340f1deeb138311.tar.bz2
seitan-59f7f7c241253293c25e001c9340f1deeb138311.tar.lz
seitan-59f7f7c241253293c25e001c9340f1deeb138311.tar.xz
seitan-59f7f7c241253293c25e001c9340f1deeb138311.tar.zst
seitan-59f7f7c241253293c25e001c9340f1deeb138311.zip
cooker, seitan: add sched_setscheduler
The sched_setscheduler requires to set the pid of the process we want to change the priority, this adds a new metadata for getting the target pid at runtime. Add a couple of syscalls for the scheduler in the string parsing. Signed-off-by: Alice Frosi <afrosi@redhat.com>
-rw-r--r--common/gluten.h3
-rw-r--r--common/util.c34
-rw-r--r--cooker/Makefile2
-rw-r--r--cooker/call.c19
-rw-r--r--cooker/calls.c3
-rw-r--r--cooker/calls/scheduler.c41
-rw-r--r--cooker/calls/scheduler.h12
-rw-r--r--demo/scheduler.hjson24
-rw-r--r--operations.c3
9 files changed, 122 insertions, 19 deletions
diff --git a/common/gluten.h b/common/gluten.h
index 6414e20..1f06221 100644
--- a/common/gluten.h
+++ b/common/gluten.h
@@ -147,7 +147,8 @@ BUILD_BUG_ON(BITS_PER_NUM(CONTEXT_TYPE_MAX) + \
enum metadata_type {
UID_TARGET = 0,
GID_TARGET = 1,
- METADATA_MAX = GID_TARGET,
+ PID_TARGET = 2,
+ METADATA_MAX = PID_TARGET,
};
extern const char *metadata_type_str[METADATA_MAX + 1];
diff --git a/common/util.c b/common/util.c
index 8815ecb..3e81a1c 100644
--- a/common/util.c
+++ b/common/util.c
@@ -55,17 +55,27 @@ const char *cmp_type_str[CMP_MAX + 1] = {
"EQ", "NE", "GT", "GE", "LT", "LE",
};
-const char *metadata_type_str[METADATA_MAX + 1] = { "uid", "gid" };
+const char *metadata_type_str[METADATA_MAX + 1] = { "uid", "gid", "pid" };
const char *syscall_name_str[N_SYSCALL + 1] = {
- [__NR_chown] = "chown",
- [__NR_connect] = "connect",
- [__NR_ioctl] = "ioctl",
- [__NR_lchown] = "lchown",
- [__NR_mknod] = "mknod",
- [__NR_mknodat] = "mknodat",
- [__NR_read] = "read",
- [__NR_socket] = "socket",
- [__NR_unshare] = "unshare",
- [__NR_open] = "open",
-
+ [__NR_chown] = "chown",
+ [__NR_connect] = "connect",
+ [__NR_ioctl] = "ioctl",
+ [__NR_lchown] = "lchown",
+ [__NR_mknod] = "mknod",
+ [__NR_mknodat] = "mknodat",
+ [__NR_open] = "open",
+ [__NR_read] = "read",
+ [__NR_sched_get_priority_max] = "sched_get_priority_max",
+ [__NR_sched_get_priority_min] = "sched_get_priority_min",
+ [__NR_sched_getaffinity] = "sched_getaffinity",
+ [__NR_sched_getattr] = "sched_getattr",
+ [__NR_sched_getparam] = "sched_getparam",
+ [__NR_sched_getscheduler] = "sched_getscheduler",
+ [__NR_sched_setaffinity] = "sched_setaffinity",
+ [__NR_sched_setattr] = "sched_setattr",
+ [__NR_sched_setparam] = "sched_setparam",
+ [__NR_sched_setscheduler] = "sched_setscheduler",
+ [__NR_sched_yield] = "sched_yield",
+ [__NR_socket] = "socket",
+ [__NR_unshare] = "unshare",
};
diff --git a/cooker/Makefile b/cooker/Makefile
index 8cf8691..12b9c1d 100644
--- a/cooker/Makefile
+++ b/cooker/Makefile
@@ -33,11 +33,13 @@ SRCS := call.c calls.c emit.c gluten.c filter.c main.c match.c \
parse.c parson.c \
$(COMMON)/util.c \
calls/net.c calls/ioctl.c calls/process.c calls/fs.c calls/io.c \
+ calls/scheduler.c \
seccomp_profile.c
HEADERS := call.h calls.h cooker.h emit.h filter.h gluten.h match.h \
parse.h parson.h \
$(COMMON)/gluten.h $(COMMON)/util.h \
calls/net.h calls/ioctl.h calls/process.h calls/fs.h calls/io.h \
+ calls/scheduler.h \
seccomp_profile.h
$(BIN): $(SRCS) $(HEADERS)
diff --git a/cooker/call.c b/cooker/call.c
index 173bdb4..a09194a 100644
--- a/cooker/call.c
+++ b/cooker/call.c
@@ -16,6 +16,15 @@
#include "parse.h"
#include "util.h"
+static bool is_metadata_obj(JSON_Object *metadata)
+{
+ if (!metadata)
+ return false;
+ return ((!json_object_get_string(metadata, "caller")) ||
+ (!json_object_get_string(metadata, "set")) ||
+ (!json_object_get_string(metadata, "get")));
+}
+
/* TODO: refactor and simplify this horrible function */
static union value parse_metadata(struct gluten_ctx *g, struct field *f,
struct gluten_offset **base_offset,
@@ -29,10 +38,12 @@ static union value parse_metadata(struct gluten_ctx *g, struct field *f,
if ((tag = json_object_get_string(metadata, "caller"))) {
debug(" args reference value at runtime '%s' with metadata %s", tag, tag);
(*base_offset)->type = OFFSET_METADATA;
- if (strcmp(tag, "uid") == 0) {
+ if (!strcmp(tag, "uid")) {
(*base_offset)->offset = UID_TARGET;
- } else if (strcmp(tag, "gid") == 0) {
+ } else if (!strcmp(tag, "gid")) {
(*base_offset)->offset = GID_TARGET;
+ } else if (!strcmp(tag, "pid")) {
+ (*base_offset)->offset = PID_TARGET;
} else {
die(" unrecognized metadata tag: %s", tag);
}
@@ -151,9 +162,7 @@ static union value parse_field(struct gluten_ctx *g, struct arg *args,
if (offset.type != OFFSET_NULL)
offset.offset += f->offset;
-
- if (json_value_get_type(jvalue) == JSONObject &&
- (tmp1 = json_value_get_object(jvalue)))
+ if (!(tmp1 = json_value_get_object(jvalue)) && is_metadata_obj(tmp1))
v = parse_metadata(g, f, &base_offset, offset, tmp1, dry_run,
add);
if (v.v_num == 0)
diff --git a/cooker/calls.c b/cooker/calls.c
index f486777..f4e7d49 100644
--- a/cooker/calls.c
+++ b/cooker/calls.c
@@ -16,9 +16,10 @@
#include "calls/process.h"
#include "calls/fs.h"
#include "calls/io.h"
+#include "calls/scheduler.h"
struct call *call_sets[] = {
syscalls_net, syscalls_ioctl, syscalls_process, syscalls_fs,
- syscalls_io,
+ syscalls_io, syscalls_scheduler,
NULL,
};
diff --git a/cooker/calls/scheduler.c b/cooker/calls/scheduler.c
new file mode 100644
index 0000000..436d3c2
--- /dev/null
+++ b/cooker/calls/scheduler.c
@@ -0,0 +1,41 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later
+ * Copyright 2023 Red Hat GmbH
+ * Author: Alice Frosi <afrosi@redhat.com>
+ */
+#define _GNU_SOURCE
+#include <sys/syscall.h>
+#include <sched.h>
+
+#include "../cooker.h"
+#include "../calls.h"
+
+static struct num sched_policy[] = {
+ { "SCHED_OTHER", SCHED_OTHER },
+ { "SCHED_BATCH", SCHED_BATCH },
+ { "SCHED_IDLE", SCHED_IDLE },
+ { "SCHED_FIFO", SCHED_FIFO },
+ { "SCHED_RR", SCHED_RR },
+ { "SCHED_RESET_ON_FORK", SCHED_RESET_ON_FORK }, /* ORed in policy */
+ { 0 },
+};
+
+static struct field sched_param[] = {
+ { "sched_priority",
+ INT,
+ 0,
+ offsetof(struct sched_param, sched_priority),
+ sizeof(int),
+ { 0 } },
+ { 0 },
+};
+
+static struct arg sched_setscheduler_args[] = {
+ { 0, { "pid", PID, 0, 0, 0, { 0 } } },
+ { 1, { "policy", INT, FLAGS, 0, 0, { .d_num = sched_policy } } },
+ { 2, { "param", STRUCT, 0, 0, 0, { .d_struct = sched_param } } }
+};
+
+struct call syscalls_scheduler[] = {
+ { __NR_sched_setscheduler, "sched_setscheduler", sched_setscheduler_args },
+ { 0 },
+};
diff --git a/cooker/calls/scheduler.h b/cooker/calls/scheduler.h
new file mode 100644
index 0000000..751d65b
--- /dev/null
+++ b/cooker/calls/scheduler.h
@@ -0,0 +1,12 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later
+ * Copyright 2023 Red Hat GmbH
+ * Author: Alice Frosi <afrosi@redhat.com>
+ */
+
+#ifndef CALLS_SCHEDULER_H
+#define CALLS_SCHEDULER_H
+
+extern struct call syscalls_scheduler[];
+
+#endif /* CALLS_IO_H */
+
diff --git a/demo/scheduler.hjson b/demo/scheduler.hjson
new file mode 100644
index 0000000..29c7d31
--- /dev/null
+++ b/demo/scheduler.hjson
@@ -0,0 +1,24 @@
+[
+ {
+ "match": [
+ {
+ "sched_setscheduler": {
+ "policy": "SCHED_FIFO",
+ "param": { "priority": 1 }
+ }
+ }
+ ],
+ "call": [
+ {
+ "sched_setscheduler": {
+ "pid": { "caller": "pid" },
+ "policy": "SCHED_FIFO",
+ "param": { "priority": 1 }
+ }
+ }
+ ],
+ "return": {
+ "value": 0
+ }
+ }
+]
diff --git a/operations.c b/operations.c
index 0121023..cfb3a9c 100644
--- a/operations.c
+++ b/operations.c
@@ -130,6 +130,9 @@ static int get_metadata_value(uint32_t offset, pid_t pid)
case GID_TARGET:
return proc_state("Gid", pid);
break;
+ case PID_TARGET:
+ return pid;
+ break;
default:
err("unrecognize metadata type");
}