aboutgitcodelistschat:MatrixIRC
diff options
context:
space:
mode:
authorAlice Frosi <afrosi@redhat.com>2023-05-17 15:46:57 +0200
committerAlice Frosi <afrosi@redhat.com>2023-05-17 16:05:51 +0200
commitef403b6687ec5739933f9f215093e1ea5c923666 (patch)
tree1e13e29251c18541b9b6f915e142aca886806e60
parent1e78526693d22abe24c98291a782998573f6b01d (diff)
downloadseitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar.gz
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar.bz2
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar.lz
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar.xz
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.tar.zst
seitan-ef403b6687ec5739933f9f215093e1ea5c923666.zip
cooker, seitan: simple working example
parser: - add OP_BLOCK and OP_RETURN to the parser seitan: - fix op_cmp in seitan, it was jmp when comparison was true Working example: demo.json: [ { "match": [ /* qemu-pr-helper and similar */ { "connect": { "addr": { "family": "unix", "path": "/tmp/test.sock" } } } ], "return": 0 } ] Create gluten and the bpf filter: $ seitan-cooker demo.hjson demo.gluten demo.bpf Launch the seitan eater with the target program: $ seitan-eater -i demo.bpf -- strace -e connect tests-utils/test-syscalls connect Start seitan with gluten: $ seitan -i demo.gluten -p $(pgrep seitan-eater) Seitan mocks the connect syscall and `connect` returns successfully: $ seitan-eater -i demo.bpf -- strace -e connect tests-utils/test-syscalls connect Test syscall: connect connect(4, {sa_family=AF_UNIX, sun_path="/tmp/test.sock"}, 108) = 0
-rw-r--r--cooker/cooker.h1
-rw-r--r--cooker/emit.c48
-rw-r--r--cooker/emit.h2
-rw-r--r--cooker/parse.c8
-rw-r--r--operations.c4
-rw-r--r--operations.h2
6 files changed, 58 insertions, 7 deletions
diff --git a/cooker/cooker.h b/cooker/cooker.h
index 82b24f7..8dcf93e 100644
--- a/cooker/cooker.h
+++ b/cooker/cooker.h
@@ -46,6 +46,7 @@ union desc {
union value {
int v_int;
uint32_t v_u32;
+ uint64_t v_u64;
long long v_num;
const char *v_str;
};
diff --git a/cooker/emit.c b/cooker/emit.c
index c233b0a..3fcddba 100644
--- a/cooker/emit.c
+++ b/cooker/emit.c
@@ -6,6 +6,7 @@
*
* Copyright 2023 Red Hat GmbH
* Author: Stefano Brivio <sbrivio@redhat.com>
+ * Alice Frosi <afrosi@redhat.com>
*/
#include "cooker.h"
@@ -136,6 +137,43 @@ void emit_cmp_field(struct gluten_ctx *g, enum op_cmp_type cmp,
jmp);
}
+/**
+ * emit_return() - Emit OP_RETURN instruction: return value
+ * @g: gluten context
+ * @v: Pointer to return value
+ */
+void emit_return(struct gluten_ctx *g, struct gluten_offset v)
+{
+ struct op *op = (struct op *)gluten_ptr(&g->g, g->ip);
+ struct op_return *ret = &op->op.ret;
+
+ op->type = OP_RETURN;
+ ret->val = v;
+
+ debug(" %i: OP_RETURN:", g->ip.offset);
+
+ if (++g->ip.offset > INST_MAX)
+ die("Too many instructions");
+}
+/**
+ * emit_block() - Emit OP_BLOCK instruction: return error value
+ * @g: gluten context
+ * @error: Error value
+ */
+void emit_block(struct gluten_ctx *g, int32_t error)
+{
+ struct op *op = (struct op *)gluten_ptr(&g->g, g->ip);
+ struct op_block *block = &op->op.block;
+
+ op->type = OP_BLOCK;
+ block->error = error;
+
+ debug(" %i: OP_BLOCK: %d", g->ip.offset, error);
+
+ if (++g->ip.offset > INST_MAX)
+ die("Too many instructions");
+}
+
struct gluten_offset emit_data(struct gluten_ctx *g, enum type type,
size_t str_len, union value *value)
{
@@ -153,6 +191,16 @@ struct gluten_offset emit_data(struct gluten_ctx *g, enum type type,
g->cp.offset += sizeof(int);
break;
+ case U64:
+ if (g->cp.offset + sizeof(uint64_t) > RO_DATA_SIZE)
+ die(" Read-only data section exceeded");
+
+ *(uint64_t *)p = value->v_u64;
+ debug(" C#%i: (%s) %i", g->cp.offset, type_str[type],
+ value->v_u64);
+
+ g->cp.offset += sizeof(uint64_t);
+ break;
case STRING:
if (g->cp.offset + str_len > RO_DATA_SIZE)
die(" Read-only data section exceeded");
diff --git a/cooker/emit.h b/cooker/emit.h
index 2135052..5d15b1b 100644
--- a/cooker/emit.h
+++ b/cooker/emit.h
@@ -16,6 +16,8 @@ void emit_cmp_field(struct gluten_ctx *g, enum op_cmp_type cmp,
struct field *field,
struct gluten_offset base, struct gluten_offset match,
enum jump_type jmp);
+void emit_return(struct gluten_ctx *g, struct gluten_offset v);
+void emit_block(struct gluten_ctx *g, int32_t error);
struct gluten_offset emit_data(struct gluten_ctx *g, enum type type,
size_t str_len, union value *value);
void link_block(struct gluten_ctx *g);
diff --git a/cooker/parse.c b/cooker/parse.c
index 09b1e46..acb6810 100644
--- a/cooker/parse.c
+++ b/cooker/parse.c
@@ -38,14 +38,14 @@ static void handle_limit(struct gluten_ctx *g, JSON_Value *value)
static void handle_return(struct gluten_ctx *g, JSON_Value *value)
{
- (void)g;
- (void)value;
+ union value v = { .v_u64 = json_value_get_number(value) };
+
+ emit_return(g, emit_data(g, U64, sizeof(v.v_u64), &v));
}
static void handle_block(struct gluten_ctx *g, JSON_Value *value)
{
- (void)g;
- (void)value;
+ emit_block(g, json_value_get_number(value));
}
static void handle_context(struct gluten_ctx *g, JSON_Value *value)
diff --git a/operations.c b/operations.c
index f79c41c..60c8410 100644
--- a/operations.c
+++ b/operations.c
@@ -357,9 +357,9 @@ int op_cmp(const struct seccomp_notif *req, int notifier, struct gluten *g,
(res < 0 && (cmp == CMP_LT || cmp == CMP_LE)) ||
(res > 0 && (cmp == CMP_GT || cmp == CMP_GE)) ||
(res != 0 && (cmp == CMP_NE)))
- return op->jmp.offset; /* TODO: check boundaries */
+ return 0;
- return 0;
+ return op->jmp.offset;
}
int op_resolve_fd(const struct seccomp_notif *req, int notifier,
diff --git a/operations.h b/operations.h
index 9d017e0..b1d0ac2 100644
--- a/operations.h
+++ b/operations.h
@@ -21,7 +21,7 @@
if (res == 0) \
(op)++; \
else if (res == -1) \
- return -1; \
+ return -1; \
else \
(op) += res; \
} while (0); \