From 1c1a9da7a4f9c4c1990192e14763ebf423d812a9 Mon Sep 17 00:00:00 2001 From: Alice Frosi Date: Wed, 7 Jun 2023 16:54:53 +0200 Subject: seitan, cooker: refactor op_return Refactor OP_RETURN: - merged OP_BLOCK and OP_CONT into OP_RETURN - add desc field for op_return - updated the demo files --- cooker/emit.c | 36 ++++++++++++++++-------------------- cooker/emit.h | 4 ++-- cooker/parse.c | 34 +++++++++++++++++++++++++++------- 3 files changed, 45 insertions(+), 29 deletions(-) (limited to 'cooker') diff --git a/cooker/emit.c b/cooker/emit.c index 7b1b14d..506a561 100644 --- a/cooker/emit.c +++ b/cooker/emit.c @@ -304,36 +304,32 @@ void emit_cmp_field(struct gluten_ctx *g, enum op_cmp_type cmp, /** * emit_return() - Emit OP_RETURN instruction: return value * @g: gluten context - * @v: Pointer to return value + * @v: offset of the return value + * @error: error value + * @cont if the filtered syscall needs to be executed */ -void emit_return(struct gluten_ctx *g, struct gluten_offset v) +void emit_return(struct gluten_ctx *g, struct gluten_offset v, int32_t error, + bool cont) { struct op *op = (struct op *)gluten_ptr(&g->g, g->ip); struct op_return *ret = &op->op.ret; + struct gluten_offset o; + struct return_desc *desc; op->type = OP_RETURN; - ret->val = v; - - debug(" %i: OP_RETURN:", g->ip.offset); - if (++g->ip.offset > INST_MAX) - die("Too many instructions"); -} + o = gluten_ro_alloc(g, sizeof(struct return_desc)); + desc = (struct return_desc *)gluten_ptr(&g->g, o); -/** - * 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; + desc->val = v; + desc->error = error; + desc->cont = cont; - op->type = OP_BLOCK; - block->error = error; + ret->desc = o; - debug(" %i: OP_BLOCK: %d", g->ip.offset, error); + debug(" %i: OP_RETURN:", g->ip.offset); + debug(" \t val=(%s %d) errno=%d cont=%s", gluten_offset_name[v.type], + v.offset, error, cont ? "true" : "false"); if (++g->ip.offset > INST_MAX) die("Too many instructions"); diff --git a/cooker/emit.h b/cooker/emit.h index 18618ee..81f947e 100644 --- a/cooker/emit.h +++ b/cooker/emit.h @@ -24,8 +24,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); +void emit_return(struct gluten_ctx *g, struct gluten_offset v, int32_t error, + bool cont); void emit_copy(struct gluten_ctx *g, struct gluten_offset dst, struct gluten_offset src, size_t size); void emit_copy_field(struct gluten_ctx *g, struct field *field, diff --git a/cooker/parse.c b/cooker/parse.c index 81ad159..353947e 100644 --- a/cooker/parse.c +++ b/cooker/parse.c @@ -6,6 +6,7 @@ * * Copyright 2023 Red Hat GmbH * Author: Stefano Brivio + * Alice Frosi */ #include "parson.h" @@ -73,14 +74,34 @@ static void handle_limit(struct gluten_ctx *g, JSON_Value *value) static void handle_return(struct gluten_ctx *g, JSON_Value *value) { - union value v = { .v_u64 = json_value_get_number(value) }; + JSON_Object *obj = json_value_get_object(value); + JSON_Value *jvalue; + union value v = { .v_u64 = 0 }; + int32_t error = 0; + bool cont = false; - emit_return(g, emit_data(g, U64, sizeof(v.v_u64), &v)); -} + debug(" Parsing \"return\""); -static void handle_block(struct gluten_ctx *g, JSON_Value *value) -{ - emit_block(g, json_value_get_number(value)); + jvalue = json_object_get_value(obj, "error"); + if (json_value_get_type(jvalue) == JSONNumber) { + error = json_value_get_number(jvalue); + } + + jvalue = json_object_get_value(obj, "value"); + if (json_value_get_type(jvalue) == JSONNumber) { + v.v_u64 = json_value_get_number(jvalue); + } + + jvalue = json_object_get_value(obj, "continue"); + if (json_value_get_type(jvalue) == JSONBoolean) { + cont = json_value_get_boolean(jvalue); + } + if (cont && (v.v_u64 != 0 || error != 0)) + die(" if continue is true, error and value needs to be zero"); + + debug(" emit return: val=%ld errno=%d cont=%s", v.v_u64, error, + cont ? "true" : "false"); + emit_return(g, emit_data(g, U64, sizeof(v.v_u64), &v), error, cont); } static void handle_context(struct gluten_ctx *g, JSON_Value *value) @@ -103,7 +124,6 @@ struct rule_parser { { "fd", handle_fd }, { "limit", handle_limit }, { "return", handle_return }, - { "block", handle_block }, { "context", handle_context }, { NULL, NULL }, }; -- cgit v1.2.3