From 5a9302bab9c9bb3d1577f04678d074fb7af4115f Mon Sep 17 00:00:00 2001 From: Stefano Brivio Date: Wed, 15 May 2024 08:49:56 +0200 Subject: Add fsetxattr(), fremovexattr(), open_by_handle_at(), and "virtiofsd demo" Mostly assorted fixes, a new FDGET operation (get a copy of the target file descriptor via pidfd_getfd()) and a new "FD" flag that means we have to do that on direct tag reference. Signed-off-by: Stefano Brivio --- cooker/emit.c | 49 +++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 45 insertions(+), 4 deletions(-) (limited to 'cooker/emit.c') diff --git a/cooker/emit.c b/cooker/emit.c index 7899fa5..33355b6 100644 --- a/cooker/emit.c +++ b/cooker/emit.c @@ -24,7 +24,8 @@ static const char *type_str[] = { "PID", "PORT", "IPV4", "IPV6", "GNU_DEV_MAJOR", "GNU_DEV_MINOR", - "FDPATH", + "FDPATH", "FDMOUNT", + "UID", "GID", NULL }; @@ -76,6 +77,37 @@ void emit_fd(struct gluten_ctx *g, struct fd_desc *desc) die("Too many instructions"); } +/** + * emit_fdget() - Emit OP_FDGET instruction: copy file descriptor from target + * @g: gluten context + * @src: Pointer to existing file descriptor number in target process + * @dst: Pointer to new descriptor number in seitan, can be OFFSET_NULL + * + * Return: offset to destination operand, allocated here if not given + */ +struct gluten_offset emit_fdget(struct gluten_ctx *g, + struct gluten_offset src, + struct gluten_offset dst) +{ + struct op *op = (struct op *)gluten_ptr(&g->g, g->ip); + struct op_fdget *fdget = &op->op.fdget; + + op->type = OP_FDGET; + + if (dst.type == OFFSET_NULL) + dst = gluten_rw_alloc(g, sizeof(int)); + + fdget->src = src; + fdget->dst = dst; + + debug(" %i: OP_FDGET: ...", g->ip.offset); + + if (++g->ip.offset > INST_MAX) + die("Too many instructions"); + + return dst; +} + /** * emit_call() - Emit OP_CALL instruction: execute a system call * @g: gluten context @@ -218,19 +250,21 @@ struct gluten_offset emit_iovload(struct gluten_ctx *g, /** * emit_resolved() - Emit OP_RESOLVEFD instruction: resolve file descriptor with path * @g: gluten context + * @type: Type of field (FDPATH or FDMOUNT) * @fd: offset of the file descriptor value * @path: offset of the path * @path_size: size of the path */ -void emit_resolvefd(struct gluten_ctx *g, struct gluten_offset fd, - struct gluten_offset path, size_t path_size) +void emit_resolvefd(struct gluten_ctx *g, enum type type, + struct gluten_offset fd, + struct gluten_offset path, size_t path_size) { struct op *op = (struct op *)gluten_ptr(&g->g, g->ip); struct op_resolvefd *resfd = &op->op.resfd; struct gluten_offset o; struct resolvefd_desc *desc; - op->type = OP_RESOLVEDFD; + op->type = OP_RESOLVEFD; o = gluten_ro_alloc(g, sizeof(struct resolvefd_desc)); desc = (struct resolvefd_desc *)gluten_ptr(&g->g, o); @@ -238,6 +272,13 @@ void emit_resolvefd(struct gluten_ctx *g, struct gluten_offset fd, desc->path = path; desc->path_max = path_size; + if (type == FDPATH) + desc->type = RESOLVEFD_PATH; + else if (type == FDMOUNT) + desc->type = RESOLVEFD_MOUNT; + else + die("Invalid field type for resolvefd"); + resfd->desc = o; debug(" %i: OP_RESOLVEDFD:", g->ip.offset); -- cgit v1.2.3