summaryrefslogtreecommitdiff
path: root/lib9p
diff options
context:
space:
mode:
Diffstat (limited to 'lib9p')
-rw-r--r--lib9p/9p.c212
-rw-r--r--lib9p/9p.generated.c9167
-rw-r--r--lib9p/CMakeLists.txt4
-rwxr-xr-xlib9p/idl.gen1439
-rw-r--r--lib9p/idl/0000-README.md63
-rw-r--r--lib9p/idl/0000-TODO.md4
-rw-r--r--lib9p/idl/1992-9P0.9p.wip56
-rw-r--r--lib9p/idl/1995-9P1.9p.wip2
-rw-r--r--lib9p/idl/1996-Styx.9p.wip2
-rw-r--r--lib9p/idl/2002-9P2000.9p83
-rw-r--r--lib9p/idl/2005-9P2000.u.9p14
-rw-r--r--lib9p/idl/2010-9P2000.L.9p186
-rw-r--r--lib9p/idl/__init__.py522
-rw-r--r--lib9p/include/lib9p/9p.generated.h704
-rw-r--r--lib9p/include/lib9p/9p.h17
-rw-r--r--lib9p/include/lib9p/srv.h145
-rw-r--r--lib9p/internal.h129
-rw-r--r--lib9p/map.h2
-rwxr-xr-xlib9p/proto.gen15
-rw-r--r--lib9p/protogen/__init__.py57
-rw-r--r--lib9p/protogen/c.py201
-rw-r--r--lib9p/protogen/c9util.py134
-rw-r--r--lib9p/protogen/c_format.py142
-rw-r--r--lib9p/protogen/c_marshal.py403
-rw-r--r--lib9p/protogen/c_unmarshal.py138
-rw-r--r--lib9p/protogen/c_validate.py299
-rw-r--r--lib9p/protogen/cutil.py84
-rw-r--r--lib9p/protogen/h.py535
-rw-r--r--lib9p/protogen/idlutil.py112
-rw-r--r--lib9p/srv.c167
-rw-r--r--lib9p/tables.c186
-rw-r--r--lib9p/tables.h59
-rw-r--r--lib9p/tests/test_compile.c192
-rw-r--r--lib9p/tests/test_compile_config/config.h28
-rw-r--r--lib9p/tests/test_server/CMakeLists.txt2
-rw-r--r--lib9p/tests/test_server/config/config.h27
-rw-r--r--lib9p/tests/test_server/main.c27
-rw-r--r--lib9p/utf8.h34
38 files changed, 9850 insertions, 5743 deletions
diff --git a/lib9p/9p.c b/lib9p/9p.c
index 74a786c..e7b20b5 100644
--- a/lib9p/9p.c
+++ b/lib9p/9p.c
@@ -6,35 +6,14 @@
#include <inttypes.h> /* for PRIu{n} */
#include <stdarg.h> /* for va_* */
-#include <stdio.h> /* for vsnprintf() */
#include <string.h> /* for strncpy() */
-#define LOG_NAME 9P
-#include <libmisc/log.h> /* for const_byte_str() */
+#include <libfmt/fmt.h> /* for fmt_vsnprintf() */
#include <lib9p/9p.h>
-#include "internal.h"
-
/* strings ********************************************************************/
-const char *lib9p_version_str(enum lib9p_version ver) {
-#pragma GCC diagnostic push
-#pragma GCC diagnostic ignored "-Wtype-limits"
- assert(0 <= ver && ver < LIB9P_VER_NUM);
-#pragma GCC diagnostic pop
- return _lib9p_table_ver_name[ver];
-}
-
-const char *lib9p_msgtype_str(enum lib9p_version ver, enum lib9p_msg_type typ) {
-#pragma GCC diagnostic push
-#pragma GCC diagnostic ignored "-Wtype-limits"
- assert(0 <= ver && ver < LIB9P_VER_NUM);
- assert(0 <= typ && typ <= 0xFF);
-#pragma GCC diagnostic pop
- return _lib9p_table_msg_name[ver][typ] ?: const_byte_str(typ);
-}
-
struct lib9p_s lib9p_str(char *s) {
if (!s)
return (struct lib9p_s){0};
@@ -101,7 +80,7 @@ int lib9p_errorf(struct lib9p_ctx *ctx, lib9p_errno_t linux_errno, char const *f
if (lib9p_ctx_has_error(ctx))
return -1;
va_start(args, fmt);
- n = vsnprintf(ctx->err_msg, sizeof(ctx->err_msg), fmt, args);
+ n = fmt_vsnprintf(ctx->err_msg, sizeof(ctx->err_msg), fmt, args);
va_end(args);
if ((size_t)(n+1) < sizeof(ctx->err_msg))
memset(&ctx->err_msg[n+1], 0, sizeof(ctx->err_msg)-(n+1));
@@ -114,190 +93,3 @@ int lib9p_errorf(struct lib9p_ctx *ctx, lib9p_errno_t linux_errno, char const *f
return -1;
}
-
-/* main message functions *****************************************************/
-
-static
-ssize_t _lib9p_validate(uint8_t xxx_low_typ_bit,
- const char *xxx_errmsg,
- const struct _lib9p_recv_tentry xxx_table[LIB9P_VER_NUM][0x80],
- struct lib9p_ctx *ctx, uint8_t *net_bytes) {
- /* Inspect the first 5 bytes ourselves. */
- struct _validate_ctx subctx = {
- /* input */
- .ctx = ctx,
- .net_size = uint32le_decode(net_bytes),
- .net_bytes = net_bytes,
-
- /* output */
- .net_offset = 0,
- .host_extra = 0,
- };
- if (subctx.net_size < 5)
- return lib9p_error(ctx, LINUX_EBADMSG, "message is impossibly short");
- uint8_t typ = net_bytes[4];
- if (typ % 2 != xxx_low_typ_bit)
- return lib9p_errorf(ctx, LINUX_EOPNOTSUPP, "%s: message_type=%s", xxx_errmsg,
- lib9p_msgtype_str(ctx->version, typ));
- struct _lib9p_recv_tentry tentry = xxx_table[ctx->version][typ/2];
- if (!tentry.validate)
- return lib9p_errorf(ctx, LINUX_EOPNOTSUPP, "unknown message type: %s (protocol_version=%s)",
- lib9p_msgtype_str(ctx->version, typ), lib9p_version_str(ctx->version));
-
- /* Now use the message-type-specific tentry to process the whole thing. */
- if (tentry.validate(&subctx))
- return -1;
- assert(subctx.net_offset <= subctx.net_size);
- if (subctx.net_offset < subctx.net_size)
- return lib9p_errorf(ctx, LINUX_EBADMSG, "message has %"PRIu32" extra bytes",
- subctx.net_size - subctx.net_offset);
-
- /* Return. */
- ssize_t ret;
- if (__builtin_add_overflow(tentry.basesize, subctx.host_extra, &ret))
- return lib9p_error(ctx, LINUX_EMSGSIZE, "unmarshalled payload overflows SSIZE_MAX");
- return ret;
-}
-
-ssize_t lib9p_Tmsg_validate(struct lib9p_ctx *ctx, uint8_t *net_bytes) {
- return _lib9p_validate(0, "expected a T-message but got an R-message", _lib9p_table_Tmsg_recv,
- ctx, net_bytes);
-}
-
-ssize_t lib9p_Rmsg_validate(struct lib9p_ctx *ctx, uint8_t *net_bytes) {
- return _lib9p_validate(1, "expected an R-message but got a T-message", _lib9p_table_Rmsg_recv,
- ctx, net_bytes);
-}
-
-static
-void _lib9p_unmarshal(const struct _lib9p_recv_tentry xxx_table[LIB9P_VER_NUM][0x80],
- struct lib9p_ctx *ctx, uint8_t *net_bytes,
- enum lib9p_msg_type *ret_typ, void *ret_body) {
- enum lib9p_msg_type typ = net_bytes[4];
- *ret_typ = typ;
- struct _lib9p_recv_tentry tentry = xxx_table[ctx->version][typ/2];
-
- struct _unmarshal_ctx subctx = {
- /* input */
- .ctx = ctx,
- .net_bytes = net_bytes,
-
- /* output */
- .net_offset = 0,
- .extra = ret_body + tentry.basesize,
- };
- tentry.unmarshal(&subctx, ret_body);
-}
-
-void lib9p_Tmsg_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
- enum lib9p_msg_type *ret_typ, void *ret_body) {
- _lib9p_unmarshal(_lib9p_table_Tmsg_recv,
- ctx, net_bytes, ret_typ, ret_body);
-}
-
-void lib9p_Rmsg_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
- enum lib9p_msg_type *ret_typ, void *ret_body) {
- _lib9p_unmarshal(_lib9p_table_Rmsg_recv,
- ctx, net_bytes, ret_typ, ret_body);
-}
-
-static
-bool _lib9p_marshal(const struct _lib9p_send_tentry xxx_table[LIB9P_VER_NUM][0x80],
- struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
- size_t *ret_iov_cnt, struct iovec *ret_iov, uint8_t *ret_copied) {
- struct _marshal_ctx subctx = {
- /* input */
- .ctx = ctx,
-
- /* ouptut */
- .net_iov_cnt = 1,
- .net_iov = ret_iov,
- .net_copied_size = 0,
- .net_copied = ret_copied,
- };
-
- struct _lib9p_send_tentry tentry = xxx_table[ctx->version][typ/2];
- bool ret_erred = tentry.marshal(&subctx, body);
- if (ret_iov[subctx.net_iov_cnt-1].iov_len == 0)
- subctx.net_iov_cnt--;
- *ret_iov_cnt = subctx.net_iov_cnt;
- return ret_erred;
-}
-
-bool lib9p_Tmsg_marshal(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
- struct lib9p_Tmsg_send_buf *ret) {
- assert(typ % 2 == 0);
- memset(ret, 0, sizeof(*ret));
- return _lib9p_marshal(_lib9p_table_Tmsg_send,
- ctx, typ, body,
- &ret->iov_cnt, ret->iov, ret->copied);
-}
-
-bool lib9p_Rmsg_marshal(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
- struct lib9p_Rmsg_send_buf *ret) {
- assert(typ % 2 == 1);
- memset(ret, 0, sizeof(*ret));
- return _lib9p_marshal(_lib9p_table_Rmsg_send,
- ctx, typ, body,
- &ret->iov_cnt, ret->iov, ret->copied);
-}
-
-/* `struct lib9p_stat` helpers ************************************************/
-
-bool lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes,
- uint32_t *ret_net_size, ssize_t *ret_host_size) {
- struct _validate_ctx subctx = {
- /* input */
- .ctx = ctx,
- .net_size = net_size,
- .net_bytes = net_bytes,
-
- /* output */
- .net_offset = 0,
- .host_extra = 0,
- };
- if (_lib9p_stat_validate(&subctx))
- return true;
- if (ret_net_size)
- *ret_net_size = subctx.net_offset;
- if (ret_host_size)
- if (__builtin_add_overflow(sizeof(struct lib9p_stat), subctx.host_extra, ret_host_size))
- return lib9p_error(ctx, LINUX_EMSGSIZE, "unmarshalled stat object overflows SSIZE_MAX");
- return false;
-}
-
-uint32_t lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
- struct lib9p_stat *ret_obj, void *ret_extra) {
- struct _unmarshal_ctx subctx = {
- /* input */
- .ctx = ctx,
- .net_bytes = net_bytes,
-
- /* output */
- .net_offset = 0,
- .extra = ret_extra,
- };
- _lib9p_stat_unmarshal(&subctx, ret_obj);
- return subctx.net_offset;
-}
-
-uint32_t lib9p_stat_marshal(struct lib9p_ctx *ctx, uint32_t max_net_size, struct lib9p_stat *obj,
- uint8_t *ret_bytes) {
- struct lib9p_ctx _ctx = *ctx;
- _ctx.max_msg_size = max_net_size;
-
- struct iovec iov = {0};
- struct _marshal_ctx subctx = {
- /* input */
- .ctx = &_ctx,
-
- /* output */
- .net_iov_cnt = 1,
- .net_iov = &iov,
- .net_copied_size = 0,
- .net_copied = ret_bytes,
- };
- if (_lib9p_stat_marshal(&subctx, obj))
- return 0;
- return subctx.net_iov[0].iov_len;
-}
diff --git a/lib9p/9p.generated.c b/lib9p/9p.generated.c
index 8d6c82f..b58a485 100644
--- a/lib9p/9p.generated.c
+++ b/lib9p/9p.generated.c
@@ -1,4 +1,4 @@
-/* Generated by `lib9p/idl.gen lib9p/idl/2002-9P2000.9p lib9p/idl/2003-9P2000.p9p.9p lib9p/idl/2005-9P2000.u.9p lib9p/idl/2010-9P2000.L.9p lib9p/idl/2012-9P2000.e.9p`. DO NOT EDIT! */
+/* Generated by `lib9p/proto.gen lib9p/idl/2002-9P2000.9p lib9p/idl/2003-9P2000.p9p.9p lib9p/idl/2005-9P2000.u.9p lib9p/idl/2010-9P2000.L.9p lib9p/idl/2012-9P2000.e.9p`. DO NOT EDIT! */
#include <stdbool.h>
#include <stddef.h> /* for size_t */
@@ -6,10 +6,132 @@
#include <string.h> /* for memset() */
#include <libmisc/assert.h>
+#include <libmisc/endian.h>
#include <lib9p/9p.h>
-#include "internal.h"
+#include "tables.h"
+#include "utf8.h"
+
+/* libobj vtables *************************************************************/
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_tag_t, lib9p_tag, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_fid_t, lib9p_fid, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_s, lib9p_s, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_dm_t, lib9p_dm, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_qt_t, lib9p_qt, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_qid, lib9p_qid, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_stat, lib9p_stat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_o_t, lib9p_o, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tversion, lib9p_msg_Tversion, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rversion, lib9p_msg_Rversion, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tauth, lib9p_msg_Tauth, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rauth, lib9p_msg_Rauth, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tattach, lib9p_msg_Tattach, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rattach, lib9p_msg_Rattach, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rerror, lib9p_msg_Rerror, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tflush, lib9p_msg_Tflush, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rflush, lib9p_msg_Rflush, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Twalk, lib9p_msg_Twalk, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rwalk, lib9p_msg_Rwalk, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Topen, lib9p_msg_Topen, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Ropen, lib9p_msg_Ropen, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tcreate, lib9p_msg_Tcreate, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rcreate, lib9p_msg_Rcreate, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tread, lib9p_msg_Tread, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rread, lib9p_msg_Rread, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Twrite, lib9p_msg_Twrite, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rwrite, lib9p_msg_Rwrite, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tclunk, lib9p_msg_Tclunk, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rclunk, lib9p_msg_Rclunk, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tremove, lib9p_msg_Tremove, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rremove, lib9p_msg_Rremove, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tstat, lib9p_msg_Tstat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rstat, lib9p_msg_Rstat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Twstat, lib9p_msg_Twstat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rwstat, lib9p_msg_Rwstat, static);
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000_p9p
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Topenfd, lib9p_msg_Topenfd, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Ropenfd, lib9p_msg_Ropenfd, static);
+#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
+#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_nuid_t, lib9p_nuid, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_errno_t, lib9p_errno, static);
+#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000_L
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_super_magic_t, lib9p_super_magic, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_lo_t, lib9p_lo, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_dt_t, lib9p_dt, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_mode_t, lib9p_mode, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_b4_t, lib9p_b4, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_getattr_t, lib9p_getattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_setattr_t, lib9p_setattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_lock_type_t, lib9p_lock_type, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_lock_flags_t, lib9p_lock_flags, static);
+LO_IMPLEMENTATION_C(fmt_formatter, lib9p_lock_status_t, lib9p_lock_status, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rlerror, lib9p_msg_Rlerror, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tstatfs, lib9p_msg_Tstatfs, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rstatfs, lib9p_msg_Rstatfs, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tlopen, lib9p_msg_Tlopen, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rlopen, lib9p_msg_Rlopen, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tlcreate, lib9p_msg_Tlcreate, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rlcreate, lib9p_msg_Rlcreate, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tsymlink, lib9p_msg_Tsymlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rsymlink, lib9p_msg_Rsymlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tmknod, lib9p_msg_Tmknod, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rmknod, lib9p_msg_Rmknod, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Trename, lib9p_msg_Trename, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rrename, lib9p_msg_Rrename, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Treadlink, lib9p_msg_Treadlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rreadlink, lib9p_msg_Rreadlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tgetattr, lib9p_msg_Tgetattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rgetattr, lib9p_msg_Rgetattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tsetattr, lib9p_msg_Tsetattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rsetattr, lib9p_msg_Rsetattr, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Txattrwalk, lib9p_msg_Txattrwalk, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rxattrwalk, lib9p_msg_Rxattrwalk, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Txattrcreate, lib9p_msg_Txattrcreate, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rxattrcreate, lib9p_msg_Rxattrcreate, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Treaddir, lib9p_msg_Treaddir, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rreaddir, lib9p_msg_Rreaddir, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tfsync, lib9p_msg_Tfsync, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rfsync, lib9p_msg_Rfsync, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tlock, lib9p_msg_Tlock, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rlock, lib9p_msg_Rlock, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tgetlock, lib9p_msg_Tgetlock, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rgetlock, lib9p_msg_Rgetlock, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tlink, lib9p_msg_Tlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rlink, lib9p_msg_Rlink, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tmkdir, lib9p_msg_Tmkdir, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rmkdir, lib9p_msg_Rmkdir, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Trenameat, lib9p_msg_Trenameat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rrenameat, lib9p_msg_Rrenameat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tunlinkat, lib9p_msg_Tunlinkat, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Runlinkat, lib9p_msg_Runlinkat, static);
+#endif /* CONFIG_9P_ENABLE_9P2000_L */
+#if CONFIG_9P_ENABLE_9P2000_e
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tsession, lib9p_msg_Tsession, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rsession, lib9p_msg_Rsession, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tsread, lib9p_msg_Tsread, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rsread, lib9p_msg_Rsread, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Tswrite, lib9p_msg_Tswrite, static);
+LO_IMPLEMENTATION_C(fmt_formatter, struct lib9p_msg_Rswrite, lib9p_msg_Rswrite, static);
+#endif /* CONFIG_9P_ENABLE_9P2000_e */
/* utilities ******************************************************************/
#if CONFIG_9P_ENABLE_9P2000
@@ -39,255 +161,31 @@
#endif
/**
- * is_ver(ctx, ver) is essentially `(ctx->ctx->version == LIB9P_VER_##ver)`,
- * but compiles correctly (to `false`) even if `LIB9P_VER_##ver` isn't defined
+ * is_ver(ctx, ver) is essentially `(ctx->version == LIB9P_VER_##ver)`, but
+ * compiles correctly (to `false`) even if `LIB9P_VER_##ver` isn't defined
* (because `!CONFIG_9P_ENABLE_##ver`). This is useful when `||`ing
* several version checks together.
*/
-#define is_ver(CTX, ver) _is_ver_##ver(CTX->ctx->version)
-
-/* strings ********************************************************************/
-
-const char *const _lib9p_table_ver_name[LIB9P_VER_NUM] = {
- [LIB9P_VER_unknown] = "unknown",
-#if CONFIG_9P_ENABLE_9P2000
- [LIB9P_VER_9P2000] = "9P2000",
-#endif /* CONFIG_9P_ENABLE_9P2000 */
-#if CONFIG_9P_ENABLE_9P2000_L
- [LIB9P_VER_9P2000_L] = "9P2000.L",
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
- [LIB9P_VER_9P2000_e] = "9P2000.e",
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
-#if CONFIG_9P_ENABLE_9P2000_p9p
- [LIB9P_VER_9P2000_p9p] = "9P2000.p9p",
-#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
-#if CONFIG_9P_ENABLE_9P2000_u
- [LIB9P_VER_9P2000_u] = "9P2000.u",
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-};
-
-#define _MSG_NAME(typ) [LIB9P_TYP_##typ] = #typ
-const char *const _lib9p_table_msg_name[LIB9P_VER_NUM][0x100] = {
- [LIB9P_VER_unknown] = {
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Rerror),
- },
-#if CONFIG_9P_ENABLE_9P2000
- [LIB9P_VER_9P2000] = {
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Tauth),
- _MSG_NAME(Rauth),
- _MSG_NAME(Tattach),
- _MSG_NAME(Rattach),
- _MSG_NAME(Rerror),
- _MSG_NAME(Tflush),
- _MSG_NAME(Rflush),
- _MSG_NAME(Twalk),
- _MSG_NAME(Rwalk),
- _MSG_NAME(Topen),
- _MSG_NAME(Ropen),
- _MSG_NAME(Tcreate),
- _MSG_NAME(Rcreate),
- _MSG_NAME(Tread),
- _MSG_NAME(Rread),
- _MSG_NAME(Twrite),
- _MSG_NAME(Rwrite),
- _MSG_NAME(Tclunk),
- _MSG_NAME(Rclunk),
- _MSG_NAME(Tremove),
- _MSG_NAME(Rremove),
- _MSG_NAME(Tstat),
- _MSG_NAME(Rstat),
- _MSG_NAME(Twstat),
- _MSG_NAME(Rwstat),
- },
-#endif /* CONFIG_9P_ENABLE_9P2000 */
-#if CONFIG_9P_ENABLE_9P2000_L
- [LIB9P_VER_9P2000_L] = {
- _MSG_NAME(Rlerror),
- _MSG_NAME(Tstatfs),
- _MSG_NAME(Rstatfs),
- _MSG_NAME(Tlopen),
- _MSG_NAME(Rlopen),
- _MSG_NAME(Tlcreate),
- _MSG_NAME(Rlcreate),
- _MSG_NAME(Tsymlink),
- _MSG_NAME(Rsymlink),
- _MSG_NAME(Tmknod),
- _MSG_NAME(Rmknod),
- _MSG_NAME(Trename),
- _MSG_NAME(Rrename),
- _MSG_NAME(Treadlink),
- _MSG_NAME(Rreadlink),
- _MSG_NAME(Tgetattr),
- _MSG_NAME(Rgetattr),
- _MSG_NAME(Tsetattr),
- _MSG_NAME(Rsetattr),
- _MSG_NAME(Txattrwalk),
- _MSG_NAME(Rxattrwalk),
- _MSG_NAME(Txattrcreate),
- _MSG_NAME(Rxattrcreate),
- _MSG_NAME(Treaddir),
- _MSG_NAME(Rreaddir),
- _MSG_NAME(Tfsync),
- _MSG_NAME(Rfsync),
- _MSG_NAME(Tlock),
- _MSG_NAME(Rlock),
- _MSG_NAME(Tgetlock),
- _MSG_NAME(Rgetlock),
- _MSG_NAME(Tlink),
- _MSG_NAME(Rlink),
- _MSG_NAME(Tmkdir),
- _MSG_NAME(Rmkdir),
- _MSG_NAME(Trenameat),
- _MSG_NAME(Rrenameat),
- _MSG_NAME(Tunlinkat),
- _MSG_NAME(Runlinkat),
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Tauth),
- _MSG_NAME(Rauth),
- _MSG_NAME(Tattach),
- _MSG_NAME(Rattach),
- _MSG_NAME(Rerror),
- _MSG_NAME(Tflush),
- _MSG_NAME(Rflush),
- _MSG_NAME(Twalk),
- _MSG_NAME(Rwalk),
- _MSG_NAME(Tread),
- _MSG_NAME(Rread),
- _MSG_NAME(Twrite),
- _MSG_NAME(Rwrite),
- _MSG_NAME(Tclunk),
- _MSG_NAME(Rclunk),
- _MSG_NAME(Tremove),
- _MSG_NAME(Rremove),
- },
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
- [LIB9P_VER_9P2000_e] = {
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Tauth),
- _MSG_NAME(Rauth),
- _MSG_NAME(Tattach),
- _MSG_NAME(Rattach),
- _MSG_NAME(Rerror),
- _MSG_NAME(Tflush),
- _MSG_NAME(Rflush),
- _MSG_NAME(Twalk),
- _MSG_NAME(Rwalk),
- _MSG_NAME(Topen),
- _MSG_NAME(Ropen),
- _MSG_NAME(Tcreate),
- _MSG_NAME(Rcreate),
- _MSG_NAME(Tread),
- _MSG_NAME(Rread),
- _MSG_NAME(Twrite),
- _MSG_NAME(Rwrite),
- _MSG_NAME(Tclunk),
- _MSG_NAME(Rclunk),
- _MSG_NAME(Tremove),
- _MSG_NAME(Rremove),
- _MSG_NAME(Tstat),
- _MSG_NAME(Rstat),
- _MSG_NAME(Twstat),
- _MSG_NAME(Rwstat),
- _MSG_NAME(Tsession),
- _MSG_NAME(Rsession),
- _MSG_NAME(Tsread),
- _MSG_NAME(Rsread),
- _MSG_NAME(Tswrite),
- _MSG_NAME(Rswrite),
- },
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
-#if CONFIG_9P_ENABLE_9P2000_p9p
- [LIB9P_VER_9P2000_p9p] = {
- _MSG_NAME(Topenfd),
- _MSG_NAME(Ropenfd),
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Tauth),
- _MSG_NAME(Rauth),
- _MSG_NAME(Tattach),
- _MSG_NAME(Rattach),
- _MSG_NAME(Rerror),
- _MSG_NAME(Tflush),
- _MSG_NAME(Rflush),
- _MSG_NAME(Twalk),
- _MSG_NAME(Rwalk),
- _MSG_NAME(Topen),
- _MSG_NAME(Ropen),
- _MSG_NAME(Tcreate),
- _MSG_NAME(Rcreate),
- _MSG_NAME(Tread),
- _MSG_NAME(Rread),
- _MSG_NAME(Twrite),
- _MSG_NAME(Rwrite),
- _MSG_NAME(Tclunk),
- _MSG_NAME(Rclunk),
- _MSG_NAME(Tremove),
- _MSG_NAME(Rremove),
- _MSG_NAME(Tstat),
- _MSG_NAME(Rstat),
- _MSG_NAME(Twstat),
- _MSG_NAME(Rwstat),
- },
-#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
-#if CONFIG_9P_ENABLE_9P2000_u
- [LIB9P_VER_9P2000_u] = {
- _MSG_NAME(Tversion),
- _MSG_NAME(Rversion),
- _MSG_NAME(Tauth),
- _MSG_NAME(Rauth),
- _MSG_NAME(Tattach),
- _MSG_NAME(Rattach),
- _MSG_NAME(Rerror),
- _MSG_NAME(Tflush),
- _MSG_NAME(Rflush),
- _MSG_NAME(Twalk),
- _MSG_NAME(Rwalk),
- _MSG_NAME(Topen),
- _MSG_NAME(Ropen),
- _MSG_NAME(Tcreate),
- _MSG_NAME(Rcreate),
- _MSG_NAME(Tread),
- _MSG_NAME(Rread),
- _MSG_NAME(Twrite),
- _MSG_NAME(Rwrite),
- _MSG_NAME(Tclunk),
- _MSG_NAME(Rclunk),
- _MSG_NAME(Tremove),
- _MSG_NAME(Rremove),
- _MSG_NAME(Tstat),
- _MSG_NAME(Rstat),
- _MSG_NAME(Twstat),
- _MSG_NAME(Rwstat),
- },
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-};
+#define is_ver(ctx, ver) _is_ver_##ver((ctx)->version)
/* bitmasks *******************************************************************/
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
static const lib9p_dm_t dm_masks[LIB9P_VER_NUM] = {
#if CONFIG_9P_ENABLE_9P2000
- [LIB9P_VER_9P2000] = 0b11101100000000000000000111111111,
+ [LIB9P_VER_9P2000] = 0b11111100000000000000000111111111,
#endif /* CONFIG_9P_ENABLE_9P2000 */
#if CONFIG_9P_ENABLE_9P2000_L
[LIB9P_VER_9P2000_L] = 0b00000000000000000000000000000000,
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
- [LIB9P_VER_9P2000_e] = 0b11101100000000000000000111111111,
+ [LIB9P_VER_9P2000_e] = 0b11111100000000000000000111111111,
#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000_p9p
- [LIB9P_VER_9P2000_p9p] = 0b11101100000000000000000111111111,
+ [LIB9P_VER_9P2000_p9p] = 0b11111100000000000000000111111111,
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_u
- [LIB9P_VER_9P2000_u] = 0b11101100101111000000000111111111,
+ [LIB9P_VER_9P2000_u] = 0b11111100101111000000000111111111,
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
@@ -295,19 +193,19 @@ static const lib9p_dm_t dm_masks[LIB9P_VER_NUM] = {
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
static const lib9p_qt_t qt_masks[LIB9P_VER_NUM] = {
#if CONFIG_9P_ENABLE_9P2000
- [LIB9P_VER_9P2000] = 0b11101100,
+ [LIB9P_VER_9P2000] = 0b11111100,
#endif /* CONFIG_9P_ENABLE_9P2000 */
#if CONFIG_9P_ENABLE_9P2000_L
- [LIB9P_VER_9P2000_L] = 0b11101100,
+ [LIB9P_VER_9P2000_L] = 0b11111100,
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
- [LIB9P_VER_9P2000_e] = 0b11101100,
+ [LIB9P_VER_9P2000_e] = 0b11111100,
#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000_p9p
- [LIB9P_VER_9P2000_p9p] = 0b11101100,
+ [LIB9P_VER_9P2000_p9p] = 0b11111100,
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_u
- [LIB9P_VER_9P2000_u] = 0b11101110,
+ [LIB9P_VER_9P2000_u] = 0b11111110,
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
@@ -416,2562 +314,2664 @@ static const lib9p_lock_flags_t lock_flags_masks[LIB9P_VER_NUM] = {
/* validate_* *****************************************************************/
-LM_ALWAYS_INLINE static bool _validate_size_net(struct _validate_ctx *ctx, uint32_t n) {
- if (__builtin_add_overflow(ctx->net_offset, n, &ctx->net_offset))
- /* If needed-net-size overflowed uint32_t, then
- * there's no way that actual-net-size will live up to
- * that. */
- return lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
- if (ctx->net_offset > ctx->net_size)
- return lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
- return false;
-}
-
-LM_ALWAYS_INLINE static bool _validate_size_host(struct _validate_ctx *ctx, size_t n) {
- if (__builtin_add_overflow(ctx->host_extra, n, &ctx->host_extra))
- /* If needed-host-size overflowed size_t, then there's
- * no way that actual-net-size will live up to
- * that. */
- return lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
- return false;
-}
-
-LM_ALWAYS_INLINE static bool _validate_list(struct _validate_ctx *ctx,
- size_t cnt,
- _validate_fn_t item_fn, size_t item_host_size) {
- for (size_t i = 0; i < cnt; i++)
- if (_validate_size_host(ctx, item_host_size) || item_fn(ctx))
- return true;
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_1(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 1); }
-LM_ALWAYS_INLINE static bool validate_2(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 2); }
-LM_ALWAYS_INLINE static bool validate_4(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 4); }
-LM_ALWAYS_INLINE static bool validate_8(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 8); }
-
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_tag(struct _validate_ctx *ctx) {
- return validate_2(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_fid(struct _validate_ctx *ctx) {
- return validate_4(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_s(struct _validate_ctx *ctx) {
- uint16_t len;
- return false
- || (validate_2(ctx) || ({ len = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || _validate_size_net(ctx, len)
- || ({ (!is_valid_utf8_without_nul(&ctx->net_bytes[ctx->net_offset-len], len)) && lib9p_error(ctx->ctx, LINUX_EBADMSG, "message contains invalid UTF-8"); })
- ;
-}
+#define VALIDATE_NET_BYTES(n) \
+ if (__builtin_add_overflow(net_offset, n, &net_offset)) \
+ /* If needed-net-size overflowed uint32_t, then \
+ * there's no way that actual-net-size will live up to \
+ * that. */ \
+ return lib9p_error(ctx, LINUX_EBADMSG, "message is too short for content"); \
+ if (net_offset > net_size) \
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "message is too short for content (%"PRIu32" > %"PRIu32") @ %d", net_offset, net_size, __LINE__);
+#define VALIDATE_NET_UTF8(n) \
+ { \
+ size_t len = n; \
+ VALIDATE_NET_BYTES(len); \
+ if (!is_valid_utf8_without_nul(&net_bytes[net_offset-len], len)) \
+ return lib9p_error(ctx, LINUX_EBADMSG, "message contains invalid UTF-8"); \
+ }
+#define RESERVE_HOST_BYTES(n) \
+ if (__builtin_add_overflow(host_size, n, &host_size)) \
+ /* If needed-host-size overflowed ssize_t, then there's \
+ * no way that actual-net-size will live up to \
+ * that. */ \
+ return lib9p_error(ctx, LINUX_EBADMSG, "message is too short for content");
+#define GET_U8LE(off) (net_bytes[off])
+#define GET_U16LE(off) uint16le_decode(&net_bytes[off])
+#define GET_U32LE(off) uint32le_decode(&net_bytes[off])
+#define GET_U64LE(off) uint64le_decode(&net_bytes[off])
+#define LAST_U8LE() GET_U8LE(net_offset-1)
+#define LAST_U16LE() GET_U16LE(net_offset-2)
+#define LAST_U32LE() GET_U32LE(net_offset-4)
+#define LAST_U64LE() GET_U64LE(net_offset-8)
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_dm(struct _validate_ctx *ctx) {
- if (validate_4(ctx))
- return true;
- lib9p_dm_t mask = dm_masks[ctx->ctx->version];
- lib9p_dm_t val = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in dm bitfield: %#04"PRIx32, val & ~mask);
- return false;
+static ssize_t validate_stat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes, uint32_t *ret_net_size) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_stat);
+ uint32_t offsetof_stat_size = net_offset + 0;
+ uint32_t offsetof_kern_type = net_offset + 2;
+ uint32_t offsetof_file_qid_type = net_offset + 8;
+ VALIDATE_NET_BYTES(21);
+ if (GET_U8LE(offsetof_file_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_file_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_file_mode = net_offset + 0;
+ VALIDATE_NET_BYTES(22);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+#if CONFIG_9P_ENABLE_9P2000_u
+ if (is_ver(ctx, 9P2000_u)) {
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(12);
+ }
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_stat_size) != (uint32_t)(offsetof_end - offsetof_kern_type))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "stat->stat_size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_stat_size), (uint32_t)(offsetof_end - offsetof_kern_type));
+ if (GET_U32LE(offsetof_file_mode) & ~dm_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in dm bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_file_mode) & ~dm_masks[ctx->version]);
+ if (ret_net_size)
+ *ret_net_size = net_offset;
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_qt(struct _validate_ctx *ctx) {
- if (validate_1(ctx))
- return true;
- lib9p_qt_t mask = qt_masks[ctx->ctx->version];
- lib9p_qt_t val = ctx->net_bytes[ctx->net_offset-1];
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#01"PRIx8, val & ~mask);
- return false;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+static ssize_t validate_Tversion(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tversion);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tversion->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(100))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tversion->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(100));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rversion(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rversion);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rversion->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(101))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rversion->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(101));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tauth(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tauth);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_nuid(struct _validate_ctx *ctx) {
- return validate_4(ctx);
-}
-
+ if (( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) )) {
+ VALIDATE_NET_BYTES(4);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_o(struct _validate_ctx *ctx) {
- if (validate_1(ctx))
- return true;
- lib9p_o_t mask = o_masks[ctx->ctx->version];
- lib9p_o_t val = ctx->net_bytes[ctx->net_offset-1];
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in o bitfield: %#01"PRIx8, val & ~mask);
- return false;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tauth->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(102))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tauth->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(102));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rauth(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rauth);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_aqid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_aqid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_aqid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rauth->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(103))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rauth->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(103));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tattach(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tattach);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(17);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_errno(struct _validate_ctx *ctx) {
- return validate_4(ctx);
-}
-
+ if (( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) )) {
+ VALIDATE_NET_BYTES(4);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_ALWAYS_INLINE static bool validate_super_magic(struct _validate_ctx *ctx) {
- return validate_4(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_lo(struct _validate_ctx *ctx) {
- if (validate_4(ctx))
- return true;
- lib9p_lo_t mask = lo_masks[ctx->ctx->version];
- lib9p_lo_t val = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in lo bitfield: %#04"PRIx32, val & ~mask);
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_dt(struct _validate_ctx *ctx) {
- return validate_1(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_mode(struct _validate_ctx *ctx) {
- if (validate_4(ctx))
- return true;
- lib9p_mode_t mask = mode_masks[ctx->ctx->version];
- lib9p_mode_t val = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#04"PRIx32, val & ~mask);
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_b4(struct _validate_ctx *ctx) {
- return validate_4(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_getattr(struct _validate_ctx *ctx) {
- if (validate_8(ctx))
- return true;
- lib9p_getattr_t mask = getattr_masks[ctx->ctx->version];
- lib9p_getattr_t val = uint64le_decode(&ctx->net_bytes[ctx->net_offset-8]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in getattr bitfield: %#08"PRIx64, val & ~mask);
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_setattr(struct _validate_ctx *ctx) {
- if (validate_4(ctx))
- return true;
- lib9p_setattr_t mask = setattr_masks[ctx->ctx->version];
- lib9p_setattr_t val = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in setattr bitfield: %#04"PRIx32, val & ~mask);
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_lock_type(struct _validate_ctx *ctx) {
- return validate_1(ctx);
-}
-
-LM_ALWAYS_INLINE static bool validate_lock_flags(struct _validate_ctx *ctx) {
- if (validate_4(ctx))
- return true;
- lib9p_lock_flags_t mask = lock_flags_masks[ctx->ctx->version];
- lib9p_lock_flags_t val = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]);
- if (val & ~mask)
- return lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in lock_flags bitfield: %#04"PRIx32, val & ~mask);
- return false;
-}
-
-LM_ALWAYS_INLINE static bool validate_lock_status(struct _validate_ctx *ctx) {
- return validate_1(ctx);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Tflush(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_2(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 108; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rflush(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 109; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rread(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || _validate_size_net(ctx, count)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 117; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint32_t max = INT32_MAX; (((uint32_t)count) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "count value is too large (%"PRIu32" > %"PRIu32")", count, max); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rwrite(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 119; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint32_t max = INT32_MAX; (((uint32_t)count) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "count value is too large (%"PRIu32" > %"PRIu32")", count, max); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rclunk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 121; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rremove(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 123; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Rwstat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 127; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Rrename(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 21; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rsetattr(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 27; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rxattrwalk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_8(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 31; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rxattrcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 33; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rreaddir(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || _validate_size_net(ctx, count)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 41; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rfsync(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 51; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 71; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rrenameat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 75; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Runlinkat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 77; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
-LM_FLATTEN static bool validate_Tsession(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_8(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 150; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rsession(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 151; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rsread(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || _validate_size_net(ctx, count)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 153; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rswrite(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 155; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Tread(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint64_t offset;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || (validate_8(ctx) || ({ offset = uint64le_decode(&ctx->net_bytes[ctx->net_offset-8]); false; }))
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 116; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint64_t max = INT64_MAX; (((uint64_t)offset) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "offset value is too large (%"PRIu64" > %"PRIu64")", offset, max); })
- || ({ uint32_t max = INT32_MAX; (((uint32_t)count) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "count value is too large (%"PRIu32" > %"PRIu32")", count, max); })
- ;
-}
-
-LM_FLATTEN static bool validate_Twrite(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint64_t offset;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || (validate_8(ctx) || ({ offset = uint64le_decode(&ctx->net_bytes[ctx->net_offset-8]); false; }))
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || _validate_size_net(ctx, count)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 118; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint64_t max = INT64_MAX; (((uint64_t)offset) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "offset value is too large (%"PRIu64" > %"PRIu64")", offset, max); })
- || ({ uint32_t max = INT32_MAX; (((uint32_t)count) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "count value is too large (%"PRIu32" > %"PRIu32")", count, max); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tclunk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 120; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tremove(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 122; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tattach->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(104))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tattach->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(104));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rattach(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rattach);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rattach->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(105))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rattach->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(105));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rerror(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rerror);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(9);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+#if CONFIG_9P_ENABLE_9P2000_u
+ if (is_ver(ctx, 9P2000_u)) {
+ VALIDATE_NET_BYTES(4);
+ }
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rerror->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(107))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rerror->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(107));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tflush(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tflush);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 9;
+ VALIDATE_NET_BYTES(9);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tflush->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(108))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tflush->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(108));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rflush(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rflush);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rflush->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(109))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rflush->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(109));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Twalk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Twalk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_nwname = net_offset + 15;
+ VALIDATE_NET_BYTES(17);
+ for (uint16_t i = 0, cnt = LAST_U16LE(); i < cnt; i++) {
+ RESERVE_HOST_BYTES(sizeof(struct lib9p_s));
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ }
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twalk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(110))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twalk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(110));
+ if ((uint16_t)GET_U16LE(offsetof_nwname) > (uint16_t)(16))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twalk->nwname value is too large: %"PRIu16" > %"PRIu16,
+ (uint16_t)GET_U16LE(offsetof_nwname), (uint16_t)(16));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rwalk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rwalk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_nwqid = net_offset + 7;
+ VALIDATE_NET_BYTES(9);
+ for (uint16_t i = 0, cnt = LAST_U16LE(); i < cnt; i++) {
+ RESERVE_HOST_BYTES(sizeof(struct lib9p_qid));
+ uint32_t offsetof_wqid_type = net_offset + 0;
+ VALIDATE_NET_BYTES(13);
+ if (GET_U8LE(offsetof_wqid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_wqid_type) & ~qt_masks[ctx->version]);
+ }
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwalk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(111))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwalk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(111));
+ if ((uint16_t)GET_U16LE(offsetof_nwqid) > (uint16_t)(16))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwalk->nwqid value is too large: %"PRIu16" > %"PRIu16,
+ (uint16_t)GET_U16LE(offsetof_nwqid), (uint16_t)(16));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Tstat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 124; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+static ssize_t validate_Topen(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Topen);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_mode = net_offset + 11;
+ uint32_t offsetof_end = net_offset + 12;
+ VALIDATE_NET_BYTES(12);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Topen->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(112))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Topen->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(112));
+ if (GET_U8LE(offsetof_mode) & ~o_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in o bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_mode) & ~o_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Ropen(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Ropen);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Ropen->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(113))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Ropen->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(113));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_perm = net_offset + 0;
+ uint32_t offsetof_mode = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 5;
+ VALIDATE_NET_BYTES(5);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(114))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(114));
+ if (GET_U32LE(offsetof_perm) & ~dm_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in dm bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_perm) & ~dm_masks[ctx->version]);
+ if (GET_U8LE(offsetof_mode) & ~o_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in o bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_mode) & ~o_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(115))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(115));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Tstatfs(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 8; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Treadlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 22; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Treaddir(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 40; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Tversion(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_4(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 100; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rversion(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_4(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 101; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Twalk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nwname;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_fid(ctx)
- || (validate_2(ctx) || ({ nwname = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || _validate_list(ctx, nwname, validate_s, sizeof(struct lib9p_s))
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 110; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint16_t max = 16; (((uint16_t)nwname) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "nwname value is too large (%"PRIu16" > %"PRIu16")", nwname, max); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Trename(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 20; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rreadlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 23; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Txattrwalk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 30; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Txattrcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 32; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 70; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Trenameat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 74; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tunlinkat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 76; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
-LM_FLATTEN static bool validate_Tsread(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nwname;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_4(ctx)
- || (validate_2(ctx) || ({ nwname = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || _validate_list(ctx, nwname, validate_s, sizeof(struct lib9p_s))
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 152; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tswrite(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nwname;
- uint32_t count;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_4(ctx)
- || (validate_2(ctx) || ({ nwname = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || _validate_list(ctx, nwname, validate_s, sizeof(struct lib9p_s))
- || (validate_4(ctx) || ({ count = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || _validate_size_net(ctx, count)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 154; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_qid(struct _validate_ctx *ctx) {
- return false
- || validate_qt(ctx)
- || validate_4(ctx)
- || validate_8(ctx)
- ;
-}
-
-LM_FLATTEN static bool validate_Tauth(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
-#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
- || ( ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) && validate_nuid(ctx) )
-#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 102; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tattach(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
-#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
- || ( ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) && validate_nuid(ctx) )
-#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 104; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+static ssize_t validate_Tread(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tread);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_offset = net_offset + 11;
+ uint32_t offsetof_count = net_offset + 19;
+ uint32_t offsetof_end = net_offset + 23;
+ VALIDATE_NET_BYTES(23);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tread->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(116))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tread->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(116));
+ if ((uint64_t)GET_U64LE(offsetof_offset) > (uint64_t)(INT64_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tread->offset value is too large: %"PRIu64" > %"PRIu64,
+ (uint64_t)GET_U64LE(offsetof_offset), (uint64_t)(INT64_MAX));
+ if ((uint32_t)GET_U32LE(offsetof_count) > (uint32_t)(INT32_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tread->count value is too large: %"PRIu32" > %"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_count), (uint32_t)(INT32_MAX));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rread(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rread);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_count = net_offset + 7;
+ VALIDATE_NET_BYTES(11);
+ VALIDATE_NET_BYTES(LAST_U32LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rread->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(117))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rread->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(117));
+ if ((uint32_t)GET_U32LE(offsetof_count) > (uint32_t)(INT32_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rread->count value is too large: %"PRIu32" > %"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_count), (uint32_t)(INT32_MAX));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Twrite(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Twrite);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_offset = net_offset + 11;
+ uint32_t offsetof_count = net_offset + 19;
+ VALIDATE_NET_BYTES(23);
+ VALIDATE_NET_BYTES(LAST_U32LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twrite->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(118))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twrite->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(118));
+ if ((uint64_t)GET_U64LE(offsetof_offset) > (uint64_t)(INT64_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twrite->offset value is too large: %"PRIu64" > %"PRIu64,
+ (uint64_t)GET_U64LE(offsetof_offset), (uint64_t)(INT64_MAX));
+ if ((uint32_t)GET_U32LE(offsetof_count) > (uint32_t)(INT32_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twrite->count value is too large: %"PRIu32" > %"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_count), (uint32_t)(INT32_MAX));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rwrite(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rwrite);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_count = net_offset + 7;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwrite->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(119))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwrite->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(119));
+ if ((uint32_t)GET_U32LE(offsetof_count) > (uint32_t)(INT32_MAX))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwrite->count value is too large: %"PRIu32" > %"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_count), (uint32_t)(INT32_MAX));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tclunk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tclunk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tclunk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(120))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tclunk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(120));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rclunk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rclunk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rclunk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(121))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rclunk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(121));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tremove(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tremove);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tremove->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(122))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tremove->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(122));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rremove(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rremove);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rremove->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(123))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rremove->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(123));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Tsymlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
- || validate_nuid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 16; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Topen(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_o(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 112; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_dm(ctx)
- || validate_o(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 114; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_p9p
-LM_FLATTEN static bool validate_Topenfd(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_o(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 98; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Rerror(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_s(ctx)
+static ssize_t validate_Tstat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tstat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tstat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(124))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tstat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(124));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rstat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rstat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_nstat = net_offset + 7;
+ uint32_t offsetof_stat = net_offset + 9;
+ uint32_t offsetof_stat_stat_size = net_offset + 9;
+ uint32_t offsetof_stat_kern_type = net_offset + 11;
+ uint32_t offsetof_stat_file_qid_type = net_offset + 17;
+ VALIDATE_NET_BYTES(30);
+ if (GET_U8LE(offsetof_stat_file_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_stat_file_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_stat_file_mode = net_offset + 0;
+ VALIDATE_NET_BYTES(22);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
#if CONFIG_9P_ENABLE_9P2000_u
- || ( is_ver(ctx, 9P2000_u) && validate_errno(ctx) )
+ if (is_ver(ctx, 9P2000_u)) {
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(12);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 107; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Rlerror(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_errno(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 7; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rstatfs(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_super_magic(ctx)
- || validate_4(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 9; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tlopen(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_lo(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 12; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tlcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_lo(ctx)
- || validate_mode(ctx)
- || validate_nuid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 14; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tmknod(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_mode(ctx)
- || validate_4(ctx)
- || validate_4(ctx)
- || validate_nuid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 18; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tmkdir(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_s(ctx)
- || validate_mode(ctx)
- || validate_nuid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 72; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tfsync(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_b4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 50; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tgetattr(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_getattr(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 24; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tsetattr(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_setattr(ctx)
- || validate_mode(ctx)
- || validate_nuid(ctx)
- || validate_nuid(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 26; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tgetlock(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_lock_type(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 54; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rgetlock(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_lock_type(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 55; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Tlock(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || validate_lock_type(ctx)
- || validate_lock_flags(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_4(ctx)
- || validate_s(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 52; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rlock(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_lock_status(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 53; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static bool validate_stat(struct _validate_ctx *ctx) {
- uint16_t stat_size;
- uint32_t _kern_type_offset;
- return false
- || (validate_2(ctx) || ({ stat_size = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || ({ _kern_type_offset = ctx->net_offset; validate_2(ctx); })
- || validate_4(ctx)
- || validate_qid(ctx)
- || validate_dm(ctx)
- || validate_4(ctx)
- || validate_4(ctx)
- || validate_8(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
- || validate_s(ctx)
+ uint32_t offsetof_stat_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_stat_stat_size) != (uint32_t)(offsetof_stat_end - offsetof_stat_kern_type))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstat->stat.stat_size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_stat_stat_size), (uint32_t)(offsetof_stat_end - offsetof_stat_kern_type));
+ if (GET_U32LE(offsetof_stat_file_mode) & ~dm_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in dm bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_stat_file_mode) & ~dm_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(125))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(125));
+ if ((uint32_t)GET_U32LE(offsetof_nstat) != (uint32_t)(offsetof_end - offsetof_stat))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstat->nstat value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_nstat), (uint32_t)(offsetof_end - offsetof_stat));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Twstat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Twstat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_nstat = net_offset + 11;
+ uint32_t offsetof_stat = net_offset + 13;
+ uint32_t offsetof_stat_stat_size = net_offset + 13;
+ uint32_t offsetof_stat_kern_type = net_offset + 15;
+ uint32_t offsetof_stat_file_qid_type = net_offset + 21;
+ VALIDATE_NET_BYTES(34);
+ if (GET_U8LE(offsetof_stat_file_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_stat_file_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_stat_file_mode = net_offset + 0;
+ VALIDATE_NET_BYTES(22);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
#if CONFIG_9P_ENABLE_9P2000_u
- || ( is_ver(ctx, 9P2000_u) && validate_s(ctx) )
- || ( is_ver(ctx, 9P2000_u) && validate_nuid(ctx) )
- || ( is_ver(ctx, 9P2000_u) && validate_nuid(ctx) )
- || ( is_ver(ctx, 9P2000_u) && validate_nuid(ctx) )
+ if (is_ver(ctx, 9P2000_u)) {
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(12);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- || ({ uint16_t exp = ctx->net_offset - _kern_type_offset; (((uint16_t)stat_size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "stat_size value is wrong (actual:%"PRIu16" != correct:%"PRIu16")", (uint16_t)stat_size, exp); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Rauth(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 103; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rattach(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 105; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rwalk(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nwqid;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_2(ctx) || ({ nwqid = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || _validate_list(ctx, nwqid, validate_qid, sizeof(struct lib9p_qid))
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 111; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint16_t max = 16; (((uint16_t)nwqid) > max) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "nwqid value is too large (%"PRIu16" > %"PRIu16")", nwqid, max); })
- ;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Ropen(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 113; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 115; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+ uint32_t offsetof_stat_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_stat_stat_size) != (uint32_t)(offsetof_stat_end - offsetof_stat_kern_type))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twstat->stat.stat_size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_stat_stat_size), (uint32_t)(offsetof_stat_end - offsetof_stat_kern_type));
+ if (GET_U32LE(offsetof_stat_file_mode) & ~dm_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in dm bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_stat_file_mode) & ~dm_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twstat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(126))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twstat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(126));
+ if ((uint32_t)GET_U32LE(offsetof_nstat) != (uint32_t)(offsetof_end - offsetof_stat))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Twstat->nstat value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_nstat), (uint32_t)(offsetof_end - offsetof_stat));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rwstat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rwstat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwstat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(127))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rwstat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(127));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_p9p
-LM_FLATTEN static bool validate_Ropenfd(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || validate_4(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 99; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+static ssize_t validate_Topenfd(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Topenfd);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_mode = net_offset + 11;
+ uint32_t offsetof_end = net_offset + 12;
+ VALIDATE_NET_BYTES(12);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Topenfd->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(98))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Topenfd->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(98));
+ if (GET_U8LE(offsetof_mode) & ~o_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in o bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_mode) & ~o_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Ropenfd(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Ropenfd);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 8;
+ VALIDATE_NET_BYTES(8);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Ropenfd->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(99))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Ropenfd->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(99));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static bool validate_Rlopen(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 13; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rlcreate(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || validate_4(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 15; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rsymlink(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 17; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rmknod(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 19; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rgetattr(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_getattr(ctx)
- || validate_qid(ctx)
- || validate_mode(ctx)
- || validate_nuid(ctx)
- || validate_nuid(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || validate_8(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 25; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Rmkdir(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint32_t _size_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_qid(ctx)
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 73; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- ;
+static ssize_t validate_Rlerror(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rlerror);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlerror->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(7))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlerror->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(7));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tstatfs(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tstatfs);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tstatfs->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(8))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tstatfs->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(8));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rstatfs(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rstatfs);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 67;
+ VALIDATE_NET_BYTES(67);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstatfs->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(9))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rstatfs->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(9));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tlopen(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tlopen);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_flags = net_offset + 11;
+ uint32_t offsetof_end = net_offset + 15;
+ VALIDATE_NET_BYTES(15);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlopen->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(12))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlopen->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(12));
+ if (GET_U32LE(offsetof_flags) & ~lo_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in lo bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_flags) & ~lo_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rlopen(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rlopen);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlopen->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(13))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlopen->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(13));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tlcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tlcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_flags = net_offset + 0;
+ uint32_t offsetof_mode = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 12;
+ VALIDATE_NET_BYTES(12);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(14))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(14));
+ if (GET_U32LE(offsetof_flags) & ~lo_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in lo bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_flags) & ~lo_masks[ctx->version]);
+ if (GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rlcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rlcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(15))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(15));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tsymlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tsymlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsymlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(16))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsymlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(16));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rsymlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rsymlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsymlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(17))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsymlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(17));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tmknod(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tmknod);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_mode = net_offset + 0;
+ uint32_t offsetof_end = net_offset + 16;
+ VALIDATE_NET_BYTES(16);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tmknod->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(18))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tmknod->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(18));
+ if (GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rmknod(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rmknod);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rmknod->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(19))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rmknod->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(19));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Trename(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Trename);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(17);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Trename->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(20))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Trename->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(20));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rrename(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rrename);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rrename->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(21))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rrename->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(21));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Treadlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Treadlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Treadlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(22))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Treadlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(22));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rreadlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rreadlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(9);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rreadlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(23))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rreadlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(23));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tgetattr(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tgetattr);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_request_mask = net_offset + 11;
+ uint32_t offsetof_end = net_offset + 19;
+ VALIDATE_NET_BYTES(19);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tgetattr->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(24))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tgetattr->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(24));
+ if (GET_U64LE(offsetof_request_mask) & ~getattr_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in getattr bitfield: %#016"PRIx64,
+ GET_U64LE(offsetof_request_mask) & ~getattr_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rgetattr(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rgetattr);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_valid = net_offset + 7;
+ uint32_t offsetof_qid_type = net_offset + 15;
+ VALIDATE_NET_BYTES(28);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_mode = net_offset + 0;
+ uint32_t offsetof_end = net_offset + 132;
+ VALIDATE_NET_BYTES(132);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rgetattr->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(25))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rgetattr->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(25));
+ if (GET_U64LE(offsetof_valid) & ~getattr_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in getattr bitfield: %#016"PRIx64,
+ GET_U64LE(offsetof_valid) & ~getattr_masks[ctx->version]);
+ if (GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tsetattr(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tsetattr);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_valid = net_offset + 11;
+ uint32_t offsetof_mode = net_offset + 15;
+ uint32_t offsetof_end = net_offset + 67;
+ VALIDATE_NET_BYTES(67);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsetattr->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(26))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsetattr->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(26));
+ if (GET_U32LE(offsetof_valid) & ~setattr_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in setattr bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_valid) & ~setattr_masks[ctx->version]);
+ if (GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rsetattr(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rsetattr);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsetattr->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(27))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsetattr->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(27));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Txattrwalk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Txattrwalk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(17);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Txattrwalk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(30))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Txattrwalk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(30));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rxattrwalk(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rxattrwalk);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 15;
+ VALIDATE_NET_BYTES(15);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rxattrwalk->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(31))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rxattrwalk->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(31));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Txattrcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Txattrcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 12;
+ VALIDATE_NET_BYTES(12);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Txattrcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(32))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Txattrcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(32));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rxattrcreate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rxattrcreate);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rxattrcreate->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(33))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rxattrcreate->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(33));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Treaddir(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Treaddir);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 23;
+ VALIDATE_NET_BYTES(23);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Treaddir->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(40))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Treaddir->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(40));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rreaddir(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rreaddir);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(11);
+ VALIDATE_NET_BYTES(LAST_U32LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rreaddir->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(41))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rreaddir->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(41));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tfsync(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tfsync);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 15;
+ VALIDATE_NET_BYTES(15);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tfsync->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(50))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tfsync->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(50));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rfsync(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rfsync);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rfsync->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(51))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rfsync->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(51));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tlock(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tlock);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_flags = net_offset + 12;
+ VALIDATE_NET_BYTES(38);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlock->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(52))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlock->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(52));
+ if (GET_U32LE(offsetof_flags) & ~lock_flags_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in lock_flags bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_flags) & ~lock_flags_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rlock(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rlock);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 8;
+ VALIDATE_NET_BYTES(8);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlock->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(53))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlock->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(53));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tgetlock(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tgetlock);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(34);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tgetlock->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(54))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tgetlock->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(54));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rgetlock(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rgetlock);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(30);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rgetlock->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(55))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rgetlock->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(55));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(17);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(70))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(70));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rlink(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rlink);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlink->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(71))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rlink->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(71));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tmkdir(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tmkdir);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_mode = net_offset + 0;
+ uint32_t offsetof_end = net_offset + 8;
+ VALIDATE_NET_BYTES(8);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tmkdir->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(72))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tmkdir->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(72));
+ if (GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in mode bitfield: %#08"PRIx32,
+ GET_U32LE(offsetof_mode) & ~mode_masks[ctx->version]);
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rmkdir(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rmkdir);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_qid_type = net_offset + 7;
+ VALIDATE_NET_BYTES(20);
+ if (GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version])
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in qt bitfield: %#02"PRIx8,
+ GET_U8LE(offsetof_qid_type) & ~qt_masks[ctx->version]);
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rmkdir->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(73))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rmkdir->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(73));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Trenameat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Trenameat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ VALIDATE_NET_BYTES(6);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Trenameat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(74))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Trenameat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(74));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rrenameat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rrenameat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rrenameat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(75))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rrenameat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(75));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tunlinkat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tunlinkat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ uint32_t offsetof_end = net_offset + 4;
+ VALIDATE_NET_BYTES(4);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tunlinkat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(76))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tunlinkat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(76));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Runlinkat(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Runlinkat);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Runlinkat->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(77))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Runlinkat->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(77));
+ return (ssize_t)host_size;
}
#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static bool validate_Rstat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nstat;
- uint32_t _size_offset;
- uint32_t _stat_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || (validate_2(ctx) || ({ nstat = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || ({ _stat_offset = ctx->net_offset; validate_stat(ctx); })
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 125; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint16_t exp = ctx->net_offset - _stat_offset; (((uint16_t)nstat) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "nstat value is wrong (actual:%"PRIu16" != correct:%"PRIu16")", (uint16_t)nstat, exp); })
- ;
-}
-
-LM_FLATTEN static bool validate_Twstat(struct _validate_ctx *ctx) {
- uint32_t size;
- uint8_t typ;
- uint16_t nstat;
- uint32_t _size_offset;
- uint32_t _stat_offset;
- return false
- || (({ _size_offset = ctx->net_offset; validate_4(ctx); }) || ({ size = uint32le_decode(&ctx->net_bytes[ctx->net_offset-4]); false; }))
- || (validate_1(ctx) || ({ typ = ctx->net_bytes[ctx->net_offset-1]; false; }))
- || validate_tag(ctx)
- || validate_fid(ctx)
- || (validate_2(ctx) || ({ nstat = uint16le_decode(&ctx->net_bytes[ctx->net_offset-2]); false; }))
- || ({ _stat_offset = ctx->net_offset; validate_stat(ctx); })
- || ({ uint32_t exp = ctx->net_offset - _size_offset; (((uint32_t)size) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "size value is wrong (actual:%"PRIu32" != correct:%"PRIu32")", (uint32_t)size, exp); })
- || ({ uint8_t exp = 126; (((uint8_t)typ) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "typ value is wrong (actual:%"PRIu8" != correct:%"PRIu8")", (uint8_t)typ, exp); })
- || ({ uint16_t exp = ctx->net_offset - _stat_offset; (((uint16_t)nstat) != exp) &&
- lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "nstat value is wrong (actual:%"PRIu16" != correct:%"PRIu16")", (uint16_t)nstat, exp); })
- ;
+#if CONFIG_9P_ENABLE_9P2000_e
+static ssize_t validate_Tsession(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tsession);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 15;
+ VALIDATE_NET_BYTES(15);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsession->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(150))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsession->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(150));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rsession(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rsession);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 7;
+ VALIDATE_NET_BYTES(7);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsession->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(151))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsession->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(151));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tsread(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tsread);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ for (uint16_t i = 0, cnt = LAST_U16LE(); i < cnt; i++) {
+ RESERVE_HOST_BYTES(sizeof(struct lib9p_s));
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ }
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsread->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(152))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tsread->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(152));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rsread(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rsread);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(11);
+ VALIDATE_NET_BYTES(LAST_U32LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsread->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(153))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rsread->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(153));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Tswrite(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Tswrite);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ VALIDATE_NET_BYTES(13);
+ for (uint16_t i = 0, cnt = LAST_U16LE(); i < cnt; i++) {
+ RESERVE_HOST_BYTES(sizeof(struct lib9p_s));
+ VALIDATE_NET_BYTES(2);
+ VALIDATE_NET_UTF8(LAST_U16LE());
+ }
+ VALIDATE_NET_BYTES(4);
+ VALIDATE_NET_BYTES(LAST_U32LE());
+ uint32_t offsetof_end = net_offset + 0;
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tswrite->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(154))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Tswrite->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(154));
+ return (ssize_t)host_size;
+}
+
+static ssize_t validate_Rswrite(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {
+ uint32_t net_offset = 0;
+ ssize_t host_size = sizeof(struct lib9p_msg_Rswrite);
+ uint32_t offsetof_size = net_offset + 0;
+ uint32_t offsetof_typ = net_offset + 4;
+ uint32_t offsetof_end = net_offset + 11;
+ VALIDATE_NET_BYTES(11);
+ if ((uint32_t)GET_U32LE(offsetof_size) != (uint32_t)(offsetof_end - offsetof_size))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rswrite->size value is wrong: actual: %"PRIu32" != correct:%"PRIu32,
+ (uint32_t)GET_U32LE(offsetof_size), (uint32_t)(offsetof_end - offsetof_size));
+ if ((uint8_t)GET_U8LE(offsetof_typ) != (uint8_t)(155))
+ return lib9p_errorf(ctx, LINUX_EBADMSG, "Rswrite->typ value is wrong: actual: %"PRIu8" != correct:%"PRIu8,
+ (uint8_t)GET_U8LE(offsetof_typ), (uint8_t)(155));
+ return (ssize_t)host_size;
}
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#endif /* CONFIG_9P_ENABLE_9P2000_e */
/* unmarshal_* ****************************************************************/
-LM_ALWAYS_INLINE static void unmarshal_1(struct _unmarshal_ctx *ctx, uint8_t *out) {
- *out = ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += 1;
-}
+#define UNMARSHAL_BYTES(ctx, data_lvalue, len) \
+ data_lvalue = (char *)&net_bytes[net_offset]; \
+ net_offset += len;
+#define UNMARSHAL_U8LE(ctx, val_lvalue) \
+ val_lvalue = net_bytes[net_offset]; \
+ net_offset += 1;
+#define UNMARSHAL_U16LE(ctx, val_lvalue) \
+ val_lvalue = uint16le_decode(&net_bytes[net_offset]); \
+ net_offset += 2;
+#define UNMARSHAL_U32LE(ctx, val_lvalue) \
+ val_lvalue = uint32le_decode(&net_bytes[net_offset]); \
+ net_offset += 4;
+#define UNMARSHAL_U64LE(ctx, val_lvalue) \
+ val_lvalue = uint64le_decode(&net_bytes[net_offset]); \
+ net_offset += 8;
-LM_ALWAYS_INLINE static void unmarshal_2(struct _unmarshal_ctx *ctx, uint16_t *out) {
- *out = uint16le_decode(&ctx->net_bytes[ctx->net_offset]);
- ctx->net_offset += 2;
-}
-
-LM_ALWAYS_INLINE static void unmarshal_4(struct _unmarshal_ctx *ctx, uint32_t *out) {
- *out = uint32le_decode(&ctx->net_bytes[ctx->net_offset]);
- ctx->net_offset += 4;
-}
-
-LM_ALWAYS_INLINE static void unmarshal_8(struct _unmarshal_ctx *ctx, uint64_t *out) {
- *out = uint64le_decode(&ctx->net_bytes[ctx->net_offset]);
- ctx->net_offset += 8;
-}
-
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_tag(struct _unmarshal_ctx *ctx, lib9p_tag_t *out) {
- unmarshal_2(ctx, (uint16_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_fid(struct _unmarshal_ctx *ctx, lib9p_fid_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_s(struct _unmarshal_ctx *ctx, struct lib9p_s *out) {
- memset(out, 0, sizeof(*out));
- unmarshal_2(ctx, &out->len);
- out->utf8 = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->len;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_dm(struct _unmarshal_ctx *ctx, lib9p_dm_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
+static void unmarshal_stat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_stat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 2;
+ UNMARSHAL_U16LE(ctx, out->kern_type);
+ UNMARSHAL_U32LE(ctx, out->kern_dev);
+ UNMARSHAL_U8LE(ctx, out->file_qid.type);
+ UNMARSHAL_U32LE(ctx, out->file_qid.vers);
+ UNMARSHAL_U64LE(ctx, out->file_qid.path);
+ UNMARSHAL_U32LE(ctx, out->file_mode);
+ UNMARSHAL_U32LE(ctx, out->file_atime);
+ UNMARSHAL_U32LE(ctx, out->file_mtime);
+ UNMARSHAL_U64LE(ctx, out->file_size);
+ UNMARSHAL_U16LE(ctx, out->file_name.len);
+ UNMARSHAL_BYTES(ctx, out->file_name.utf8, out->file_name.len);
+ UNMARSHAL_U16LE(ctx, out->file_owner_uid.len);
+ UNMARSHAL_BYTES(ctx, out->file_owner_uid.utf8, out->file_owner_uid.len);
+ UNMARSHAL_U16LE(ctx, out->file_owner_gid.len);
+ UNMARSHAL_BYTES(ctx, out->file_owner_gid.utf8, out->file_owner_gid.len);
+ UNMARSHAL_U16LE(ctx, out->file_last_modified_uid.len);
+ UNMARSHAL_BYTES(ctx, out->file_last_modified_uid.utf8, out->file_last_modified_uid.len);
+#if CONFIG_9P_ENABLE_9P2000_u
+ if (is_ver(ctx, 9P2000_u)) {
+ UNMARSHAL_U16LE(ctx, out->file_extension.len);
+ UNMARSHAL_BYTES(ctx, out->file_extension.utf8, out->file_extension.len);
+ UNMARSHAL_U32LE(ctx, out->file_owner_n_uid);
+ UNMARSHAL_U32LE(ctx, out->file_owner_n_gid);
+ UNMARSHAL_U32LE(ctx, out->file_last_modified_n_uid);
+ }
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_qt(struct _unmarshal_ctx *ctx, lib9p_qt_t *out) {
- unmarshal_1(ctx, (uint8_t *)out);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+static void unmarshal_Tversion([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tversion *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->max_msg_size);
+ UNMARSHAL_U16LE(ctx, out->version.len);
+ UNMARSHAL_BYTES(ctx, out->version.utf8, out->version.len);
+}
+
+static void unmarshal_Rversion([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rversion *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->max_msg_size);
+ UNMARSHAL_U16LE(ctx, out->version.len);
+ UNMARSHAL_BYTES(ctx, out->version.utf8, out->version.len);
+}
+
+static void unmarshal_Tauth([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tauth *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->afid);
+ UNMARSHAL_U16LE(ctx, out->uname.len);
+ UNMARSHAL_BYTES(ctx, out->uname.utf8, out->uname.len);
+ UNMARSHAL_U16LE(ctx, out->aname.len);
+ UNMARSHAL_BYTES(ctx, out->aname.utf8, out->aname.len);
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_nuid(struct _unmarshal_ctx *ctx, lib9p_nuid_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
+ if (( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) )) {
+ UNMARSHAL_U32LE(ctx, out->n_uid);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_o(struct _unmarshal_ctx *ctx, lib9p_o_t *out) {
- unmarshal_1(ctx, (uint8_t *)out);
}
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+static void unmarshal_Rauth([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rauth *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->aqid.type);
+ UNMARSHAL_U32LE(ctx, out->aqid.vers);
+ UNMARSHAL_U64LE(ctx, out->aqid.path);
+}
+
+static void unmarshal_Tattach([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tattach *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->afid);
+ UNMARSHAL_U16LE(ctx, out->uname.len);
+ UNMARSHAL_BYTES(ctx, out->uname.utf8, out->uname.len);
+ UNMARSHAL_U16LE(ctx, out->aname.len);
+ UNMARSHAL_BYTES(ctx, out->aname.utf8, out->aname.len);
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_errno(struct _unmarshal_ctx *ctx, lib9p_errno_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
+ if (( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) )) {
+ UNMARSHAL_U32LE(ctx, out->n_uid);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_ALWAYS_INLINE static void unmarshal_super_magic(struct _unmarshal_ctx *ctx, lib9p_super_magic_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_lo(struct _unmarshal_ctx *ctx, lib9p_lo_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_dt(struct _unmarshal_ctx *ctx, lib9p_dt_t *out) {
- unmarshal_1(ctx, (uint8_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_mode(struct _unmarshal_ctx *ctx, lib9p_mode_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_b4(struct _unmarshal_ctx *ctx, lib9p_b4_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_getattr(struct _unmarshal_ctx *ctx, lib9p_getattr_t *out) {
- unmarshal_8(ctx, (uint64_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_setattr(struct _unmarshal_ctx *ctx, lib9p_setattr_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_lock_type(struct _unmarshal_ctx *ctx, lib9p_lock_type_t *out) {
- unmarshal_1(ctx, (uint8_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_lock_flags(struct _unmarshal_ctx *ctx, lib9p_lock_flags_t *out) {
- unmarshal_4(ctx, (uint32_t *)out);
-}
-
-LM_ALWAYS_INLINE static void unmarshal_lock_status(struct _unmarshal_ctx *ctx, lib9p_lock_status_t *out) {
- unmarshal_1(ctx, (uint8_t *)out);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Tflush(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tflush *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_2(ctx, &out->oldtag);
-}
-
-LM_FLATTEN static void unmarshal_Rflush(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rflush *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rread(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rread *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->count);
- out->data = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->count;
-}
-
-LM_FLATTEN static void unmarshal_Rwrite(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rwrite *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->count);
-}
-
-LM_FLATTEN static void unmarshal_Rclunk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rclunk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rremove(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rremove *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Rwstat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rwstat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Rrename(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rrename *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rsetattr(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rsetattr *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
}
-LM_FLATTEN static void unmarshal_Rxattrwalk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rxattrwalk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_8(ctx, &out->attr_size);
-}
-
-LM_FLATTEN static void unmarshal_Rxattrcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rxattrcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rreaddir(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rreaddir *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->count);
- out->data = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->count;
-}
-
-LM_FLATTEN static void unmarshal_Rfsync(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rfsync *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rrenameat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rrenameat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Runlinkat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Runlinkat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
-LM_FLATTEN static void unmarshal_Tsession(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tsession *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_8(ctx, &out->key);
-}
-
-LM_FLATTEN static void unmarshal_Rsession(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rsession *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
-}
-
-LM_FLATTEN static void unmarshal_Rsread(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rsread *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->count);
- out->data = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->count;
+static void unmarshal_Rattach([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rattach *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+}
+
+static void unmarshal_Rerror([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rerror *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U16LE(ctx, out->ename.len);
+ UNMARSHAL_BYTES(ctx, out->ename.utf8, out->ename.len);
+#if CONFIG_9P_ENABLE_9P2000_u
+ if (is_ver(ctx, 9P2000_u)) {
+ UNMARSHAL_U32LE(ctx, out->errno);
+ }
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
}
-LM_FLATTEN static void unmarshal_Rswrite(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rswrite *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->count);
+static void unmarshal_Tflush([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tflush *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U16LE(ctx, out->oldtag);
+}
+
+static void unmarshal_Rflush([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rflush *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Twalk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Twalk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->newfid);
+ UNMARSHAL_U16LE(ctx, out->nwname);
+ out->wname = extra;
+ extra += sizeof(out->wname[0]) * out->nwname;
+ for (uint16_t i = 0; i < out->nwname; i++) {
+ UNMARSHAL_U16LE(ctx, out->wname[i].len);
+ UNMARSHAL_BYTES(ctx, out->wname[i].utf8, out->wname[i].len);
+ }
}
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Tread(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tread *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_8(ctx, &out->offset);
- unmarshal_4(ctx, &out->count);
-}
-
-LM_FLATTEN static void unmarshal_Twrite(struct _unmarshal_ctx *ctx, struct lib9p_msg_Twrite *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_8(ctx, &out->offset);
- unmarshal_4(ctx, &out->count);
- out->data = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->count;
-}
-
-LM_FLATTEN static void unmarshal_Tclunk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tclunk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
-}
-
-LM_FLATTEN static void unmarshal_Tremove(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tremove *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
+static void unmarshal_Rwalk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rwalk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U16LE(ctx, out->nwqid);
+ out->wqid = extra;
+ extra += sizeof(out->wqid[0]) * out->nwqid;
+ for (uint16_t i = 0; i < out->nwqid; i++) {
+ UNMARSHAL_U8LE(ctx, out->wqid[i].type);
+ UNMARSHAL_U32LE(ctx, out->wqid[i].vers);
+ UNMARSHAL_U64LE(ctx, out->wqid[i].path);
+ }
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Tstat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tstat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
+static void unmarshal_Topen([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Topen *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U8LE(ctx, out->mode);
+}
+
+static void unmarshal_Ropen([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Ropen *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->iounit);
+}
+
+static void unmarshal_Tcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U32LE(ctx, out->perm);
+ UNMARSHAL_U8LE(ctx, out->mode);
+}
+
+static void unmarshal_Rcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->iounit);
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Tstatfs(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tstatfs *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
-}
-
-LM_FLATTEN static void unmarshal_Treadlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Treadlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
-}
-
-LM_FLATTEN static void unmarshal_Treaddir(struct _unmarshal_ctx *ctx, struct lib9p_msg_Treaddir *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_8(ctx, &out->offset);
- unmarshal_4(ctx, &out->count);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Tversion(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tversion *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->max_msg_size);
- unmarshal_s(ctx, &out->version);
-}
-
-LM_FLATTEN static void unmarshal_Rversion(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rversion *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->max_msg_size);
- unmarshal_s(ctx, &out->version);
-}
-
-LM_FLATTEN static void unmarshal_Twalk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Twalk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_fid(ctx, &out->newfid);
- unmarshal_2(ctx, &out->nwname);
- out->wname = ctx->extra;
- ctx->extra += sizeof(out->wname[0]) * out->nwname;
- for (typeof(out->nwname) i = 0; i < out->nwname; i++)
- unmarshal_s(ctx, &out->wname[i]);
+static void unmarshal_Tread([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tread *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U64LE(ctx, out->offset);
+ UNMARSHAL_U32LE(ctx, out->count);
+}
+
+static void unmarshal_Rread([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rread *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->count);
+ UNMARSHAL_BYTES(ctx, out->data, out->count);
+}
+
+static void unmarshal_Twrite([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Twrite *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U64LE(ctx, out->offset);
+ UNMARSHAL_U32LE(ctx, out->count);
+ UNMARSHAL_BYTES(ctx, out->data, out->count);
+}
+
+static void unmarshal_Rwrite([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rwrite *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->count);
+}
+
+static void unmarshal_Tclunk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tclunk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+}
+
+static void unmarshal_Rclunk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rclunk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Tremove([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tremove *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+}
+
+static void unmarshal_Rremove([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rremove *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Trename(struct _unmarshal_ctx *ctx, struct lib9p_msg_Trename *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_fid(ctx, &out->dfid);
- unmarshal_s(ctx, &out->name);
-}
-
-LM_FLATTEN static void unmarshal_Rreadlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rreadlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_s(ctx, &out->target);
-}
-
-LM_FLATTEN static void unmarshal_Txattrwalk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Txattrwalk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_fid(ctx, &out->newfid);
- unmarshal_s(ctx, &out->name);
-}
-
-LM_FLATTEN static void unmarshal_Txattrcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Txattrcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_s(ctx, &out->name);
- unmarshal_8(ctx, &out->attr_size);
- unmarshal_4(ctx, &out->flags);
-}
-
-LM_FLATTEN static void unmarshal_Tlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->dfid);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_s(ctx, &out->name);
-}
-
-LM_FLATTEN static void unmarshal_Trenameat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Trenameat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->olddirfid);
- unmarshal_s(ctx, &out->oldname);
- unmarshal_fid(ctx, &out->newdirfid);
- unmarshal_s(ctx, &out->newname);
-}
-
-LM_FLATTEN static void unmarshal_Tunlinkat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tunlinkat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->dirfd);
- unmarshal_s(ctx, &out->name);
- unmarshal_4(ctx, &out->flags);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000_e
-LM_FLATTEN static void unmarshal_Tsread(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tsread *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->fid);
- unmarshal_2(ctx, &out->nwname);
- out->wname = ctx->extra;
- ctx->extra += sizeof(out->wname[0]) * out->nwname;
- for (typeof(out->nwname) i = 0; i < out->nwname; i++)
- unmarshal_s(ctx, &out->wname[i]);
-}
-
-LM_FLATTEN static void unmarshal_Tswrite(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tswrite *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_4(ctx, &out->fid);
- unmarshal_2(ctx, &out->nwname);
- out->wname = ctx->extra;
- ctx->extra += sizeof(out->wname[0]) * out->nwname;
- for (typeof(out->nwname) i = 0; i < out->nwname; i++)
- unmarshal_s(ctx, &out->wname[i]);
- unmarshal_4(ctx, &out->count);
- out->data = (char *)&ctx->net_bytes[ctx->net_offset];
- ctx->net_offset += out->count;
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_e */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_qid(struct _unmarshal_ctx *ctx, struct lib9p_qid *out) {
- memset(out, 0, sizeof(*out));
- unmarshal_qt(ctx, &out->type);
- unmarshal_4(ctx, &out->vers);
- unmarshal_8(ctx, &out->path);
-}
-
-LM_FLATTEN static void unmarshal_Tauth(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tauth *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->afid);
- unmarshal_s(ctx, &out->uname);
- unmarshal_s(ctx, &out->aname);
-#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
- if ( ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) ) unmarshal_nuid(ctx, &out->n_uid);
-#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-}
-
-LM_FLATTEN static void unmarshal_Tattach(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tattach *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_fid(ctx, &out->afid);
- unmarshal_s(ctx, &out->uname);
- unmarshal_s(ctx, &out->aname);
-#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
- if ( ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) ) unmarshal_nuid(ctx, &out->n_uid);
-#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Tsymlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tsymlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_s(ctx, &out->name);
- unmarshal_s(ctx, &out->symtgt);
- unmarshal_nuid(ctx, &out->gid);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Topen(struct _unmarshal_ctx *ctx, struct lib9p_msg_Topen *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_o(ctx, &out->mode);
-}
-
-LM_FLATTEN static void unmarshal_Tcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_s(ctx, &out->name);
- unmarshal_dm(ctx, &out->perm);
- unmarshal_o(ctx, &out->mode);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_p9p
-LM_FLATTEN static void unmarshal_Topenfd(struct _unmarshal_ctx *ctx, struct lib9p_msg_Topenfd *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_o(ctx, &out->mode);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Rerror(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rerror *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_s(ctx, &out->ename);
+static void unmarshal_Tstat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tstat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+}
+
+static void unmarshal_Rstat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rstat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ net_offset += 2;
+ net_offset += 2;
+ UNMARSHAL_U16LE(ctx, out->stat.kern_type);
+ UNMARSHAL_U32LE(ctx, out->stat.kern_dev);
+ UNMARSHAL_U8LE(ctx, out->stat.file_qid.type);
+ UNMARSHAL_U32LE(ctx, out->stat.file_qid.vers);
+ UNMARSHAL_U64LE(ctx, out->stat.file_qid.path);
+ UNMARSHAL_U32LE(ctx, out->stat.file_mode);
+ UNMARSHAL_U32LE(ctx, out->stat.file_atime);
+ UNMARSHAL_U32LE(ctx, out->stat.file_mtime);
+ UNMARSHAL_U64LE(ctx, out->stat.file_size);
+ UNMARSHAL_U16LE(ctx, out->stat.file_name.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_name.utf8, out->stat.file_name.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_owner_uid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_owner_uid.utf8, out->stat.file_owner_uid.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_owner_gid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_owner_gid.utf8, out->stat.file_owner_gid.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_last_modified_uid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_last_modified_uid.utf8, out->stat.file_last_modified_uid.len);
#if CONFIG_9P_ENABLE_9P2000_u
- if ( is_ver(ctx, 9P2000_u) ) unmarshal_errno(ctx, &out->errno);
+ if (is_ver(ctx, 9P2000_u)) {
+ UNMARSHAL_U16LE(ctx, out->stat.file_extension.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_extension.utf8, out->stat.file_extension.len);
+ UNMARSHAL_U32LE(ctx, out->stat.file_owner_n_uid);
+ UNMARSHAL_U32LE(ctx, out->stat.file_owner_n_gid);
+ UNMARSHAL_U32LE(ctx, out->stat.file_last_modified_n_uid);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_u */
}
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Rlerror(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rlerror *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_errno(ctx, &out->ecode);
-}
-
-LM_FLATTEN static void unmarshal_Rstatfs(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rstatfs *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_super_magic(ctx, &out->type);
- unmarshal_4(ctx, &out->bsize);
- unmarshal_8(ctx, &out->blocks);
- unmarshal_8(ctx, &out->bfree);
- unmarshal_8(ctx, &out->bavail);
- unmarshal_8(ctx, &out->files);
- unmarshal_8(ctx, &out->ffree);
- unmarshal_8(ctx, &out->fsid);
- unmarshal_4(ctx, &out->namelen);
-}
-
-LM_FLATTEN static void unmarshal_Tlopen(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tlopen *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_lo(ctx, &out->flags);
-}
-
-LM_FLATTEN static void unmarshal_Tlcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tlcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_s(ctx, &out->name);
- unmarshal_lo(ctx, &out->flags);
- unmarshal_mode(ctx, &out->mode);
- unmarshal_nuid(ctx, &out->gid);
-}
-
-LM_FLATTEN static void unmarshal_Tmknod(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tmknod *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->dfid);
- unmarshal_s(ctx, &out->name);
- unmarshal_mode(ctx, &out->mode);
- unmarshal_4(ctx, &out->major);
- unmarshal_4(ctx, &out->minor);
- unmarshal_nuid(ctx, &out->gid);
-}
-
-LM_FLATTEN static void unmarshal_Tmkdir(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tmkdir *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->dfid);
- unmarshal_s(ctx, &out->name);
- unmarshal_mode(ctx, &out->mode);
- unmarshal_nuid(ctx, &out->gid);
-}
-
-LM_FLATTEN static void unmarshal_Tfsync(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tfsync *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_b4(ctx, &out->datasync);
-}
-
-LM_FLATTEN static void unmarshal_Tgetattr(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tgetattr *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_getattr(ctx, &out->request_mask);
-}
-
-LM_FLATTEN static void unmarshal_Tsetattr(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tsetattr *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_setattr(ctx, &out->valid);
- unmarshal_mode(ctx, &out->mode);
- unmarshal_nuid(ctx, &out->uid);
- unmarshal_nuid(ctx, &out->gid);
- unmarshal_8(ctx, &out->filesize);
- unmarshal_8(ctx, &out->atime_sec);
- unmarshal_8(ctx, &out->atime_nsec);
- unmarshal_8(ctx, &out->mtime_sec);
- unmarshal_8(ctx, &out->mtime_nsec);
-}
-
-LM_FLATTEN static void unmarshal_Tgetlock(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tgetlock *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_lock_type(ctx, &out->type);
- unmarshal_8(ctx, &out->start);
- unmarshal_8(ctx, &out->length);
- unmarshal_4(ctx, &out->proc_id);
- unmarshal_s(ctx, &out->client_id);
-}
-
-LM_FLATTEN static void unmarshal_Rgetlock(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rgetlock *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_lock_type(ctx, &out->type);
- unmarshal_8(ctx, &out->start);
- unmarshal_8(ctx, &out->length);
- unmarshal_4(ctx, &out->proc_id);
- unmarshal_s(ctx, &out->client_id);
-}
-
-LM_FLATTEN static void unmarshal_Tlock(struct _unmarshal_ctx *ctx, struct lib9p_msg_Tlock *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- unmarshal_lock_type(ctx, &out->type);
- unmarshal_lock_flags(ctx, &out->flags);
- unmarshal_8(ctx, &out->start);
- unmarshal_8(ctx, &out->length);
- unmarshal_4(ctx, &out->proc_id);
- unmarshal_s(ctx, &out->client_id);
-}
-
-LM_FLATTEN static void unmarshal_Rlock(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rlock *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_lock_status(ctx, &out->status);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_ALWAYS_INLINE static void unmarshal_stat(struct _unmarshal_ctx *ctx, struct lib9p_stat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 2;
- unmarshal_2(ctx, &out->kern_type);
- unmarshal_4(ctx, &out->kern_dev);
- unmarshal_qid(ctx, &out->file_qid);
- unmarshal_dm(ctx, &out->file_mode);
- unmarshal_4(ctx, &out->file_atime);
- unmarshal_4(ctx, &out->file_mtime);
- unmarshal_8(ctx, &out->file_size);
- unmarshal_s(ctx, &out->file_name);
- unmarshal_s(ctx, &out->file_owner_uid);
- unmarshal_s(ctx, &out->file_owner_gid);
- unmarshal_s(ctx, &out->file_last_modified_uid);
+static void unmarshal_Twstat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Twstat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ net_offset += 2;
+ net_offset += 2;
+ UNMARSHAL_U16LE(ctx, out->stat.kern_type);
+ UNMARSHAL_U32LE(ctx, out->stat.kern_dev);
+ UNMARSHAL_U8LE(ctx, out->stat.file_qid.type);
+ UNMARSHAL_U32LE(ctx, out->stat.file_qid.vers);
+ UNMARSHAL_U64LE(ctx, out->stat.file_qid.path);
+ UNMARSHAL_U32LE(ctx, out->stat.file_mode);
+ UNMARSHAL_U32LE(ctx, out->stat.file_atime);
+ UNMARSHAL_U32LE(ctx, out->stat.file_mtime);
+ UNMARSHAL_U64LE(ctx, out->stat.file_size);
+ UNMARSHAL_U16LE(ctx, out->stat.file_name.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_name.utf8, out->stat.file_name.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_owner_uid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_owner_uid.utf8, out->stat.file_owner_uid.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_owner_gid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_owner_gid.utf8, out->stat.file_owner_gid.len);
+ UNMARSHAL_U16LE(ctx, out->stat.file_last_modified_uid.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_last_modified_uid.utf8, out->stat.file_last_modified_uid.len);
#if CONFIG_9P_ENABLE_9P2000_u
- if ( is_ver(ctx, 9P2000_u) ) unmarshal_s(ctx, &out->file_extension);
- if ( is_ver(ctx, 9P2000_u) ) unmarshal_nuid(ctx, &out->file_owner_n_uid);
- if ( is_ver(ctx, 9P2000_u) ) unmarshal_nuid(ctx, &out->file_owner_n_gid);
- if ( is_ver(ctx, 9P2000_u) ) unmarshal_nuid(ctx, &out->file_last_modified_n_uid);
+ if (is_ver(ctx, 9P2000_u)) {
+ UNMARSHAL_U16LE(ctx, out->stat.file_extension.len);
+ UNMARSHAL_BYTES(ctx, out->stat.file_extension.utf8, out->stat.file_extension.len);
+ UNMARSHAL_U32LE(ctx, out->stat.file_owner_n_uid);
+ UNMARSHAL_U32LE(ctx, out->stat.file_owner_n_gid);
+ UNMARSHAL_U32LE(ctx, out->stat.file_last_modified_n_uid);
+ }
#endif /* CONFIG_9P_ENABLE_9P2000_u */
}
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Rauth(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rauth *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->aqid);
-}
-
-LM_FLATTEN static void unmarshal_Rattach(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rattach *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
-}
-
-LM_FLATTEN static void unmarshal_Rwalk(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rwalk *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_2(ctx, &out->nwqid);
- out->wqid = ctx->extra;
- ctx->extra += sizeof(out->wqid[0]) * out->nwqid;
- for (typeof(out->nwqid) i = 0; i < out->nwqid; i++)
- unmarshal_qid(ctx, &out->wqid[i]);
-}
-
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Ropen(struct _unmarshal_ctx *ctx, struct lib9p_msg_Ropen *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_4(ctx, &out->iounit);
-}
-
-LM_FLATTEN static void unmarshal_Rcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_4(ctx, &out->iounit);
+static void unmarshal_Rwstat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rwstat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
}
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_p9p
-LM_FLATTEN static void unmarshal_Ropenfd(struct _unmarshal_ctx *ctx, struct lib9p_msg_Ropenfd *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_4(ctx, &out->iounit);
- unmarshal_4(ctx, &out->unixfd);
+static void unmarshal_Topenfd([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Topenfd *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U8LE(ctx, out->mode);
+}
+
+static void unmarshal_Ropenfd([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Ropenfd *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->iounit);
+ UNMARSHAL_U32LE(ctx, out->unixfd);
}
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_L
-LM_FLATTEN static void unmarshal_Rlopen(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rlopen *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_4(ctx, &out->iounit);
-}
-
-LM_FLATTEN static void unmarshal_Rlcreate(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rlcreate *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_4(ctx, &out->iounit);
-}
-
-LM_FLATTEN static void unmarshal_Rsymlink(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rsymlink *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
-}
-
-LM_FLATTEN static void unmarshal_Rmknod(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rmknod *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
-}
-
-LM_FLATTEN static void unmarshal_Rgetattr(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rgetattr *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_getattr(ctx, &out->valid);
- unmarshal_qid(ctx, &out->qid);
- unmarshal_mode(ctx, &out->mode);
- unmarshal_nuid(ctx, &out->uid);
- unmarshal_nuid(ctx, &out->gid);
- unmarshal_8(ctx, &out->nlink);
- unmarshal_8(ctx, &out->rdev);
- unmarshal_8(ctx, &out->filesize);
- unmarshal_8(ctx, &out->blksize);
- unmarshal_8(ctx, &out->blocks);
- unmarshal_8(ctx, &out->atime_sec);
- unmarshal_8(ctx, &out->atime_nsec);
- unmarshal_8(ctx, &out->mtime_sec);
- unmarshal_8(ctx, &out->mtime_nsec);
- unmarshal_8(ctx, &out->ctime_sec);
- unmarshal_8(ctx, &out->ctime_nsec);
- unmarshal_8(ctx, &out->btime_sec);
- unmarshal_8(ctx, &out->btime_nsec);
- unmarshal_8(ctx, &out->gen);
- unmarshal_8(ctx, &out->data_version);
-}
-
-LM_FLATTEN static void unmarshal_Rmkdir(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rmkdir *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_qid(ctx, &out->qid);
+static void unmarshal_Rlerror([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rlerror *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->ecode);
+}
+
+static void unmarshal_Tstatfs([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tstatfs *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+}
+
+static void unmarshal_Rstatfs([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rstatfs *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->type);
+ UNMARSHAL_U32LE(ctx, out->bsize);
+ UNMARSHAL_U64LE(ctx, out->blocks);
+ UNMARSHAL_U64LE(ctx, out->bfree);
+ UNMARSHAL_U64LE(ctx, out->bavail);
+ UNMARSHAL_U64LE(ctx, out->files);
+ UNMARSHAL_U64LE(ctx, out->ffree);
+ UNMARSHAL_U64LE(ctx, out->fsid);
+ UNMARSHAL_U32LE(ctx, out->namelen);
+}
+
+static void unmarshal_Tlopen([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tlopen *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->flags);
+}
+
+static void unmarshal_Rlopen([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rlopen *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->iounit);
+}
+
+static void unmarshal_Tlcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tlcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U32LE(ctx, out->flags);
+ UNMARSHAL_U32LE(ctx, out->mode);
+ UNMARSHAL_U32LE(ctx, out->gid);
+}
+
+static void unmarshal_Rlcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rlcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->iounit);
+}
+
+static void unmarshal_Tsymlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tsymlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U16LE(ctx, out->symtgt.len);
+ UNMARSHAL_BYTES(ctx, out->symtgt.utf8, out->symtgt.len);
+ UNMARSHAL_U32LE(ctx, out->gid);
+}
+
+static void unmarshal_Rsymlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rsymlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+}
+
+static void unmarshal_Tmknod([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tmknod *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->dfid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U32LE(ctx, out->mode);
+ UNMARSHAL_U32LE(ctx, out->major);
+ UNMARSHAL_U32LE(ctx, out->minor);
+ UNMARSHAL_U32LE(ctx, out->gid);
+}
+
+static void unmarshal_Rmknod([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rmknod *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+}
+
+static void unmarshal_Trename([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Trename *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->dfid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+}
+
+static void unmarshal_Rrename([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rrename *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Treadlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Treadlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+}
+
+static void unmarshal_Rreadlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rreadlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U16LE(ctx, out->target.len);
+ UNMARSHAL_BYTES(ctx, out->target.utf8, out->target.len);
+}
+
+static void unmarshal_Tgetattr([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tgetattr *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U64LE(ctx, out->request_mask);
+}
+
+static void unmarshal_Rgetattr([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rgetattr *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U64LE(ctx, out->valid);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+ UNMARSHAL_U32LE(ctx, out->mode);
+ UNMARSHAL_U32LE(ctx, out->uid);
+ UNMARSHAL_U32LE(ctx, out->gid);
+ UNMARSHAL_U64LE(ctx, out->nlink);
+ UNMARSHAL_U64LE(ctx, out->rdev);
+ UNMARSHAL_U64LE(ctx, out->filesize);
+ UNMARSHAL_U64LE(ctx, out->blksize);
+ UNMARSHAL_U64LE(ctx, out->blocks);
+ UNMARSHAL_U64LE(ctx, out->atime_sec);
+ UNMARSHAL_U64LE(ctx, out->atime_nsec);
+ UNMARSHAL_U64LE(ctx, out->mtime_sec);
+ UNMARSHAL_U64LE(ctx, out->mtime_nsec);
+ UNMARSHAL_U64LE(ctx, out->ctime_sec);
+ UNMARSHAL_U64LE(ctx, out->ctime_nsec);
+ UNMARSHAL_U64LE(ctx, out->btime_sec);
+ UNMARSHAL_U64LE(ctx, out->btime_nsec);
+ UNMARSHAL_U64LE(ctx, out->gen);
+ UNMARSHAL_U64LE(ctx, out->data_version);
+}
+
+static void unmarshal_Tsetattr([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tsetattr *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->valid);
+ UNMARSHAL_U32LE(ctx, out->mode);
+ UNMARSHAL_U32LE(ctx, out->uid);
+ UNMARSHAL_U32LE(ctx, out->gid);
+ UNMARSHAL_U64LE(ctx, out->filesize);
+ UNMARSHAL_U64LE(ctx, out->atime_sec);
+ UNMARSHAL_U64LE(ctx, out->atime_nsec);
+ UNMARSHAL_U64LE(ctx, out->mtime_sec);
+ UNMARSHAL_U64LE(ctx, out->mtime_nsec);
+}
+
+static void unmarshal_Rsetattr([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rsetattr *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Txattrwalk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Txattrwalk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->newfid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+}
+
+static void unmarshal_Rxattrwalk([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rxattrwalk *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U64LE(ctx, out->attr_size);
+}
+
+static void unmarshal_Txattrcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Txattrcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U64LE(ctx, out->attr_size);
+ UNMARSHAL_U32LE(ctx, out->flags);
+}
+
+static void unmarshal_Rxattrcreate([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rxattrcreate *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Treaddir([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Treaddir *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U64LE(ctx, out->offset);
+ UNMARSHAL_U32LE(ctx, out->count);
+}
+
+static void unmarshal_Rreaddir([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rreaddir *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->count);
+ UNMARSHAL_BYTES(ctx, out->data, out->count);
+}
+
+static void unmarshal_Tfsync([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tfsync *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U32LE(ctx, out->datasync);
+}
+
+static void unmarshal_Rfsync([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rfsync *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Tlock([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tlock *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U8LE(ctx, out->type);
+ UNMARSHAL_U32LE(ctx, out->flags);
+ UNMARSHAL_U64LE(ctx, out->start);
+ UNMARSHAL_U64LE(ctx, out->length);
+ UNMARSHAL_U32LE(ctx, out->proc_id);
+ UNMARSHAL_U16LE(ctx, out->client_id.len);
+ UNMARSHAL_BYTES(ctx, out->client_id.utf8, out->client_id.len);
+}
+
+static void unmarshal_Rlock([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rlock *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->status);
+}
+
+static void unmarshal_Tgetlock([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tgetlock *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U8LE(ctx, out->type);
+ UNMARSHAL_U64LE(ctx, out->start);
+ UNMARSHAL_U64LE(ctx, out->length);
+ UNMARSHAL_U32LE(ctx, out->proc_id);
+ UNMARSHAL_U16LE(ctx, out->client_id.len);
+ UNMARSHAL_BYTES(ctx, out->client_id.utf8, out->client_id.len);
+}
+
+static void unmarshal_Rgetlock([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rgetlock *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->type);
+ UNMARSHAL_U64LE(ctx, out->start);
+ UNMARSHAL_U64LE(ctx, out->length);
+ UNMARSHAL_U32LE(ctx, out->proc_id);
+ UNMARSHAL_U16LE(ctx, out->client_id.len);
+ UNMARSHAL_BYTES(ctx, out->client_id.utf8, out->client_id.len);
+}
+
+static void unmarshal_Tlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->dfid);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+}
+
+static void unmarshal_Rlink([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rlink *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Tmkdir([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tmkdir *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->dfid);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U32LE(ctx, out->mode);
+ UNMARSHAL_U32LE(ctx, out->gid);
+}
+
+static void unmarshal_Rmkdir([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rmkdir *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U8LE(ctx, out->qid.type);
+ UNMARSHAL_U32LE(ctx, out->qid.vers);
+ UNMARSHAL_U64LE(ctx, out->qid.path);
+}
+
+static void unmarshal_Trenameat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Trenameat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->olddirfid);
+ UNMARSHAL_U16LE(ctx, out->oldname.len);
+ UNMARSHAL_BYTES(ctx, out->oldname.utf8, out->oldname.len);
+ UNMARSHAL_U32LE(ctx, out->newdirfid);
+ UNMARSHAL_U16LE(ctx, out->newname.len);
+ UNMARSHAL_BYTES(ctx, out->newname.utf8, out->newname.len);
+}
+
+static void unmarshal_Rrenameat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rrenameat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Tunlinkat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tunlinkat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->dirfd);
+ UNMARSHAL_U16LE(ctx, out->name.len);
+ UNMARSHAL_BYTES(ctx, out->name.utf8, out->name.len);
+ UNMARSHAL_U32LE(ctx, out->flags);
+}
+
+static void unmarshal_Runlinkat([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Runlinkat *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
}
#endif /* CONFIG_9P_ENABLE_9P2000_L */
-#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-LM_FLATTEN static void unmarshal_Rstat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Rstat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- ctx->net_offset += 2;
- unmarshal_stat(ctx, &out->stat);
-}
-
-LM_FLATTEN static void unmarshal_Twstat(struct _unmarshal_ctx *ctx, struct lib9p_msg_Twstat *out) {
- memset(out, 0, sizeof(*out));
- ctx->net_offset += 4;
- ctx->net_offset += 1;
- unmarshal_tag(ctx, &out->tag);
- unmarshal_fid(ctx, &out->fid);
- ctx->net_offset += 2;
- unmarshal_stat(ctx, &out->stat);
+#if CONFIG_9P_ENABLE_9P2000_e
+static void unmarshal_Tsession([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tsession *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U64LE(ctx, out->key);
+}
+
+static void unmarshal_Rsession([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rsession *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+}
+
+static void unmarshal_Tsread([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tsread *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->nwname);
+ out->wname = extra;
+ extra += sizeof(out->wname[0]) * out->nwname;
+ for (uint16_t i = 0; i < out->nwname; i++) {
+ UNMARSHAL_U16LE(ctx, out->wname[i].len);
+ UNMARSHAL_BYTES(ctx, out->wname[i].utf8, out->wname[i].len);
+ }
+}
+
+static void unmarshal_Rsread([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rsread *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->count);
+ UNMARSHAL_BYTES(ctx, out->data, out->count);
+}
+
+static void unmarshal_Tswrite([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Tswrite *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->fid);
+ UNMARSHAL_U16LE(ctx, out->nwname);
+ out->wname = extra;
+ extra += sizeof(out->wname[0]) * out->nwname;
+ for (uint16_t i = 0; i < out->nwname; i++) {
+ UNMARSHAL_U16LE(ctx, out->wname[i].len);
+ UNMARSHAL_BYTES(ctx, out->wname[i].utf8, out->wname[i].len);
+ }
+ UNMARSHAL_U32LE(ctx, out->count);
+ UNMARSHAL_BYTES(ctx, out->data, out->count);
}
-#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+
+static void unmarshal_Rswrite([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {
+ struct lib9p_msg_Rswrite *out = out_buf;
+ [[gnu::unused]] void *extra = &out[1];
+ uint32_t net_offset = 0;
+ net_offset += 4;
+ net_offset += 1;
+ UNMARSHAL_U16LE(ctx, out->tag);
+ UNMARSHAL_U32LE(ctx, out->count);
+}
+#endif /* CONFIG_9P_ENABLE_9P2000_e */
/* marshal_* ******************************************************************/
-#define MARSHAL_BYTES_ZEROCOPY(ctx, data, len) \
- if (ctx->net_iov[ctx->net_iov_cnt-1].iov_len) \
- ctx->net_iov_cnt++; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = data; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len = len; \
- ctx->net_iov_cnt++;
-#define MARSHAL_BYTES(ctx, data, len) \
- if (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base) \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size]; \
- memcpy(&ctx->net_copied[ctx->net_copied_size], data, len); \
- ctx->net_copied_size += len; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len += len;
-#define MARSHAL_U8LE(ctx, val) \
- if (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base) \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size]; \
- ctx->net_copied[ctx->net_copied_size] = val; \
- ctx->net_copied_size += 1; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len += 1;
-#define MARSHAL_U16LE(ctx, val) \
- if (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base) \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size]; \
- uint16le_encode(&ctx->net_copied[ctx->net_copied_size], val); \
- ctx->net_copied_size += 2; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len += 2;
-#define MARSHAL_U32LE(ctx, val) \
- if (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base) \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size]; \
- uint32le_encode(&ctx->net_copied[ctx->net_copied_size], val); \
- ctx->net_copied_size += 4; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len += 4;
-#define MARSHAL_U64LE(ctx, val) \
- if (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base) \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size]; \
- uint64le_encode(&ctx->net_copied[ctx->net_copied_size], val); \
- ctx->net_copied_size += 8; \
- ctx->net_iov[ctx->net_iov_cnt-1].iov_len += 8;
+#define MARSHAL_BYTES_ZEROCOPY(ctx, data, len) \
+ if (ret->net_iov[ret->net_iov_cnt-1].iov_len) \
+ ret->net_iov_cnt++; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = data; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len = len; \
+ ret->net_iov_cnt++;
+#define MARSHAL_BYTES(ctx, data, len) \
+ if (!ret->net_iov[ret->net_iov_cnt-1].iov_base) \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size]; \
+ memcpy(&ret->net_copied[ret->net_copied_size], data, len); \
+ ret->net_copied_size += len; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len += len;
+#define MARSHAL_U8LE(ctx, val) \
+ if (!ret->net_iov[ret->net_iov_cnt-1].iov_base) \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size]; \
+ ret->net_copied[ret->net_copied_size] = val; \
+ ret->net_copied_size += 1; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len += 1;
+#define MARSHAL_U16LE(ctx, val) \
+ if (!ret->net_iov[ret->net_iov_cnt-1].iov_base) \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size]; \
+ uint16le_encode(&ret->net_copied[ret->net_copied_size], val); \
+ ret->net_copied_size += 2; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len += 2;
+#define MARSHAL_U32LE(ctx, val) \
+ if (!ret->net_iov[ret->net_iov_cnt-1].iov_base) \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size]; \
+ uint32le_encode(&ret->net_copied[ret->net_copied_size], val); \
+ ret->net_copied_size += 4; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len += 4;
+#define MARSHAL_U64LE(ctx, val) \
+ if (!ret->net_iov[ret->net_iov_cnt-1].iov_base) \
+ ret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size]; \
+ uint64le_encode(&ret->net_copied[ret->net_copied_size], val); \
+ ret->net_copied_size += 8; \
+ ret->net_iov[ret->net_iov_cnt-1].iov_len += 8;
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-static bool marshal_stat(struct _marshal_ctx *ctx, struct lib9p_stat *val) {
+static bool marshal_stat(struct lib9p_ctx *ctx, struct lib9p_stat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 49 + val->file_name.len + val->file_owner_uid.len + val->file_owner_gid.len + val->file_last_modified_uid.len;
#if CONFIG_9P_ENABLE_9P2000_u
if is_ver(ctx, 9P2000_u) {
needed_size += 14 + val->file_extension.len;
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
+ if (needed_size > ctx->max_msg_size) {
return true;
}
uint32_t offsetof_end = needed_size;
@@ -2979,10 +2979,10 @@ static bool marshal_stat(struct _marshal_ctx *ctx, struct lib9p_stat *val) {
MARSHAL_U16LE(ctx, offsetof_end - offsetof_kern_type);
MARSHAL_U16LE(ctx, val->kern_type);
MARSHAL_U32LE(ctx, val->kern_dev);
- MARSHAL_U8LE(ctx, val->file_qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->file_qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->file_qid.vers);
MARSHAL_U64LE(ctx, val->file_qid.path);
- MARSHAL_U32LE(ctx, val->file_mode & dm_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->file_mode & dm_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->file_atime);
MARSHAL_U32LE(ctx, val->file_mtime);
MARSHAL_U64LE(ctx, val->file_size);
@@ -2998,20 +2998,8 @@ static bool marshal_stat(struct _marshal_ctx *ctx, struct lib9p_stat *val) {
if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U16LE(ctx, val->file_extension.len);
MARSHAL_BYTES(ctx, val->file_extension.utf8, val->file_extension.len);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->file_owner_n_uid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->file_owner_n_gid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->file_last_modified_n_uid);
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
@@ -3020,13 +3008,13 @@ static bool marshal_stat(struct _marshal_ctx *ctx, struct lib9p_stat *val) {
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-static bool marshal_Tversion(struct _marshal_ctx *ctx, struct lib9p_msg_Tversion *val) {
+static bool marshal_Tversion(struct lib9p_ctx *ctx, struct lib9p_msg_Tversion *val, struct _marshal_ret *ret) {
uint32_t needed_size = 13 + val->version.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tversion",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3040,13 +3028,13 @@ static bool marshal_Tversion(struct _marshal_ctx *ctx, struct lib9p_msg_Tversion
return false;
}
-static bool marshal_Rversion(struct _marshal_ctx *ctx, struct lib9p_msg_Rversion *val) {
+static bool marshal_Rversion(struct lib9p_ctx *ctx, struct lib9p_msg_Rversion *val, struct _marshal_ret *ret) {
uint32_t needed_size = 13 + val->version.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rversion",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3060,18 +3048,18 @@ static bool marshal_Rversion(struct _marshal_ctx *ctx, struct lib9p_msg_Rversion
return false;
}
-static bool marshal_Tauth(struct _marshal_ctx *ctx, struct lib9p_msg_Tauth *val) {
+static bool marshal_Tauth(struct lib9p_ctx *ctx, struct lib9p_msg_Tauth *val, struct _marshal_ret *ret) {
uint32_t needed_size = 15 + val->uname.len + val->aname.len;
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
if ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) {
needed_size += 4;
}
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tauth",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3092,13 +3080,13 @@ static bool marshal_Tauth(struct _marshal_ctx *ctx, struct lib9p_msg_Tauth *val)
return false;
}
-static bool marshal_Rauth(struct _marshal_ctx *ctx, struct lib9p_msg_Rauth *val) {
+static bool marshal_Rauth(struct lib9p_ctx *ctx, struct lib9p_msg_Rauth *val, struct _marshal_ret *ret) {
uint32_t needed_size = 20;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rauth",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3106,24 +3094,24 @@ static bool marshal_Rauth(struct _marshal_ctx *ctx, struct lib9p_msg_Rauth *val)
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 103);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->aqid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->aqid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->aqid.vers);
MARSHAL_U64LE(ctx, val->aqid.path);
return false;
}
-static bool marshal_Tattach(struct _marshal_ctx *ctx, struct lib9p_msg_Tattach *val) {
+static bool marshal_Tattach(struct lib9p_ctx *ctx, struct lib9p_msg_Tattach *val, struct _marshal_ret *ret) {
uint32_t needed_size = 19 + val->uname.len + val->aname.len;
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
if ( is_ver(ctx, 9P2000_L) || is_ver(ctx, 9P2000_u) ) {
needed_size += 4;
}
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tattach",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3145,13 +3133,13 @@ static bool marshal_Tattach(struct _marshal_ctx *ctx, struct lib9p_msg_Tattach *
return false;
}
-static bool marshal_Rattach(struct _marshal_ctx *ctx, struct lib9p_msg_Rattach *val) {
+static bool marshal_Rattach(struct lib9p_ctx *ctx, struct lib9p_msg_Rattach *val, struct _marshal_ret *ret) {
uint32_t needed_size = 20;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rattach",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3159,24 +3147,24 @@ static bool marshal_Rattach(struct _marshal_ctx *ctx, struct lib9p_msg_Rattach *
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 105);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
return false;
}
-static bool marshal_Rerror(struct _marshal_ctx *ctx, struct lib9p_msg_Rerror *val) {
+static bool marshal_Rerror(struct lib9p_ctx *ctx, struct lib9p_msg_Rerror *val, struct _marshal_ret *ret) {
uint32_t needed_size = 9 + val->ename.len;
#if CONFIG_9P_ENABLE_9P2000_u
if is_ver(ctx, 9P2000_u) {
needed_size += 4;
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rerror",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3194,13 +3182,13 @@ static bool marshal_Rerror(struct _marshal_ctx *ctx, struct lib9p_msg_Rerror *va
return false;
}
-static bool marshal_Tflush(struct _marshal_ctx *ctx, struct lib9p_msg_Tflush *val) {
+static bool marshal_Tflush(struct lib9p_ctx *ctx, struct lib9p_msg_Tflush *val, struct _marshal_ret *ret) {
uint32_t needed_size = 9;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tflush",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3212,13 +3200,13 @@ static bool marshal_Tflush(struct _marshal_ctx *ctx, struct lib9p_msg_Tflush *va
return false;
}
-static bool marshal_Rflush(struct _marshal_ctx *ctx, struct lib9p_msg_Rflush *val) {
+static bool marshal_Rflush(struct lib9p_ctx *ctx, struct lib9p_msg_Rflush *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rflush",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3229,16 +3217,16 @@ static bool marshal_Rflush(struct _marshal_ctx *ctx, struct lib9p_msg_Rflush *va
return false;
}
-static bool marshal_Twalk(struct _marshal_ctx *ctx, struct lib9p_msg_Twalk *val) {
+static bool marshal_Twalk(struct lib9p_ctx *ctx, struct lib9p_msg_Twalk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 17;
for (uint16_t i = 0; i < val->nwname; i++) {
needed_size += 2 + val->wname[i].len;
}
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Twalk",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3256,13 +3244,13 @@ static bool marshal_Twalk(struct _marshal_ctx *ctx, struct lib9p_msg_Twalk *val)
return false;
}
-static bool marshal_Rwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Rwalk *val) {
+static bool marshal_Rwalk(struct lib9p_ctx *ctx, struct lib9p_msg_Rwalk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 9 + (val->nwqid)*13;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rwalk",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3272,7 +3260,7 @@ static bool marshal_Rwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Rwalk *val)
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U16LE(ctx, val->nwqid);
for (uint16_t i = 0; i < val->nwqid; i++) {
- MARSHAL_U8LE(ctx, val->wqid[i].type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->wqid[i].type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->wqid[i].vers);
MARSHAL_U64LE(ctx, val->wqid[i].path);
}
@@ -3281,13 +3269,13 @@ static bool marshal_Rwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Rwalk *val)
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-static bool marshal_Topen(struct _marshal_ctx *ctx, struct lib9p_msg_Topen *val) {
+static bool marshal_Topen(struct lib9p_ctx *ctx, struct lib9p_msg_Topen *val, struct _marshal_ret *ret) {
uint32_t needed_size = 12;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Topen",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3296,17 +3284,17 @@ static bool marshal_Topen(struct _marshal_ctx *ctx, struct lib9p_msg_Topen *val)
MARSHAL_U8LE(ctx, 112);
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
- MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->version]);
return false;
}
-static bool marshal_Ropen(struct _marshal_ctx *ctx, struct lib9p_msg_Ropen *val) {
+static bool marshal_Ropen(struct lib9p_ctx *ctx, struct lib9p_msg_Ropen *val, struct _marshal_ret *ret) {
uint32_t needed_size = 24;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Ropen",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3314,20 +3302,20 @@ static bool marshal_Ropen(struct _marshal_ctx *ctx, struct lib9p_msg_Ropen *val)
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 113);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
MARSHAL_U32LE(ctx, val->iounit);
return false;
}
-static bool marshal_Tcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Tcreate *val) {
+static bool marshal_Tcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Tcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 18 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tcreate",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3338,18 +3326,18 @@ static bool marshal_Tcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Tcreate *
MARSHAL_U32LE(ctx, val->fid);
MARSHAL_U16LE(ctx, val->name.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->name.utf8, val->name.len);
- MARSHAL_U32LE(ctx, val->perm & dm_masks[ctx->ctx->version]);
- MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->perm & dm_masks[ctx->version]);
+ MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->version]);
return false;
}
-static bool marshal_Rcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rcreate *val) {
+static bool marshal_Rcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Rcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 24;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rcreate",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3357,7 +3345,7 @@ static bool marshal_Rcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rcreate *
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 115);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
MARSHAL_U32LE(ctx, val->iounit);
@@ -3366,13 +3354,13 @@ static bool marshal_Rcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rcreate *
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-static bool marshal_Tread(struct _marshal_ctx *ctx, struct lib9p_msg_Tread *val) {
+static bool marshal_Tread(struct lib9p_ctx *ctx, struct lib9p_msg_Tread *val, struct _marshal_ret *ret) {
uint32_t needed_size = 23;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tread",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3386,13 +3374,13 @@ static bool marshal_Tread(struct _marshal_ctx *ctx, struct lib9p_msg_Tread *val)
return false;
}
-static bool marshal_Rread(struct _marshal_ctx *ctx, struct lib9p_msg_Rread *val) {
+static bool marshal_Rread(struct lib9p_ctx *ctx, struct lib9p_msg_Rread *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11 + val->count;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rread",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3405,13 +3393,13 @@ static bool marshal_Rread(struct _marshal_ctx *ctx, struct lib9p_msg_Rread *val)
return false;
}
-static bool marshal_Twrite(struct _marshal_ctx *ctx, struct lib9p_msg_Twrite *val) {
+static bool marshal_Twrite(struct lib9p_ctx *ctx, struct lib9p_msg_Twrite *val, struct _marshal_ret *ret) {
uint32_t needed_size = 23 + val->count;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Twrite",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3426,13 +3414,13 @@ static bool marshal_Twrite(struct _marshal_ctx *ctx, struct lib9p_msg_Twrite *va
return false;
}
-static bool marshal_Rwrite(struct _marshal_ctx *ctx, struct lib9p_msg_Rwrite *val) {
+static bool marshal_Rwrite(struct lib9p_ctx *ctx, struct lib9p_msg_Rwrite *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rwrite",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3444,13 +3432,13 @@ static bool marshal_Rwrite(struct _marshal_ctx *ctx, struct lib9p_msg_Rwrite *va
return false;
}
-static bool marshal_Tclunk(struct _marshal_ctx *ctx, struct lib9p_msg_Tclunk *val) {
+static bool marshal_Tclunk(struct lib9p_ctx *ctx, struct lib9p_msg_Tclunk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tclunk",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3462,13 +3450,13 @@ static bool marshal_Tclunk(struct _marshal_ctx *ctx, struct lib9p_msg_Tclunk *va
return false;
}
-static bool marshal_Rclunk(struct _marshal_ctx *ctx, struct lib9p_msg_Rclunk *val) {
+static bool marshal_Rclunk(struct lib9p_ctx *ctx, struct lib9p_msg_Rclunk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rclunk",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3479,13 +3467,13 @@ static bool marshal_Rclunk(struct _marshal_ctx *ctx, struct lib9p_msg_Rclunk *va
return false;
}
-static bool marshal_Tremove(struct _marshal_ctx *ctx, struct lib9p_msg_Tremove *val) {
+static bool marshal_Tremove(struct lib9p_ctx *ctx, struct lib9p_msg_Tremove *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tremove",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3497,13 +3485,13 @@ static bool marshal_Tremove(struct _marshal_ctx *ctx, struct lib9p_msg_Tremove *
return false;
}
-static bool marshal_Rremove(struct _marshal_ctx *ctx, struct lib9p_msg_Rremove *val) {
+static bool marshal_Rremove(struct lib9p_ctx *ctx, struct lib9p_msg_Rremove *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rremove",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3516,13 +3504,13 @@ static bool marshal_Rremove(struct _marshal_ctx *ctx, struct lib9p_msg_Rremove *
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
-static bool marshal_Tstat(struct _marshal_ctx *ctx, struct lib9p_msg_Tstat *val) {
+static bool marshal_Tstat(struct lib9p_ctx *ctx, struct lib9p_msg_Tstat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tstat",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3534,18 +3522,18 @@ static bool marshal_Tstat(struct _marshal_ctx *ctx, struct lib9p_msg_Tstat *val)
return false;
}
-static bool marshal_Rstat(struct _marshal_ctx *ctx, struct lib9p_msg_Rstat *val) {
+static bool marshal_Rstat(struct lib9p_ctx *ctx, struct lib9p_msg_Rstat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 58 + val->stat.file_name.len + val->stat.file_owner_uid.len + val->stat.file_owner_gid.len + val->stat.file_last_modified_uid.len;
#if CONFIG_9P_ENABLE_9P2000_u
if is_ver(ctx, 9P2000_u) {
needed_size += 14 + val->stat.file_extension.len;
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rstat",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3565,10 +3553,10 @@ static bool marshal_Rstat(struct _marshal_ctx *ctx, struct lib9p_msg_Rstat *val)
MARSHAL_U16LE(ctx, offsetof_stat_end - offsetof_stat_kern_type);
MARSHAL_U16LE(ctx, val->stat.kern_type);
MARSHAL_U32LE(ctx, val->stat.kern_dev);
- MARSHAL_U8LE(ctx, val->stat.file_qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->stat.file_qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->stat.file_qid.vers);
MARSHAL_U64LE(ctx, val->stat.file_qid.path);
- MARSHAL_U32LE(ctx, val->stat.file_mode & dm_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->stat.file_mode & dm_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->stat.file_atime);
MARSHAL_U32LE(ctx, val->stat.file_mtime);
MARSHAL_U64LE(ctx, val->stat.file_size);
@@ -3584,38 +3572,26 @@ static bool marshal_Rstat(struct _marshal_ctx *ctx, struct lib9p_msg_Rstat *val)
if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U16LE(ctx, val->stat.file_extension.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->stat.file_extension.utf8, val->stat.file_extension.len);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_owner_n_uid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_owner_n_gid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_last_modified_n_uid);
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
return false;
}
-static bool marshal_Twstat(struct _marshal_ctx *ctx, struct lib9p_msg_Twstat *val) {
+static bool marshal_Twstat(struct lib9p_ctx *ctx, struct lib9p_msg_Twstat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 62 + val->stat.file_name.len + val->stat.file_owner_uid.len + val->stat.file_owner_gid.len + val->stat.file_last_modified_uid.len;
#if CONFIG_9P_ENABLE_9P2000_u
if is_ver(ctx, 9P2000_u) {
needed_size += 14 + val->stat.file_extension.len;
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Twstat",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3636,10 +3612,10 @@ static bool marshal_Twstat(struct _marshal_ctx *ctx, struct lib9p_msg_Twstat *va
MARSHAL_U16LE(ctx, offsetof_stat_end - offsetof_stat_kern_type);
MARSHAL_U16LE(ctx, val->stat.kern_type);
MARSHAL_U32LE(ctx, val->stat.kern_dev);
- MARSHAL_U8LE(ctx, val->stat.file_qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->stat.file_qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->stat.file_qid.vers);
MARSHAL_U64LE(ctx, val->stat.file_qid.path);
- MARSHAL_U32LE(ctx, val->stat.file_mode & dm_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->stat.file_mode & dm_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->stat.file_atime);
MARSHAL_U32LE(ctx, val->stat.file_mtime);
MARSHAL_U64LE(ctx, val->stat.file_size);
@@ -3655,33 +3631,21 @@ static bool marshal_Twstat(struct _marshal_ctx *ctx, struct lib9p_msg_Twstat *va
if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U16LE(ctx, val->stat.file_extension.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->stat.file_extension.utf8, val->stat.file_extension.len);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_owner_n_uid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_owner_n_gid);
- }
-#endif /* CONFIG_9P_ENABLE_9P2000_u */
-#if CONFIG_9P_ENABLE_9P2000_u
- if (is_ver(ctx, 9P2000_u)) {
MARSHAL_U32LE(ctx, val->stat.file_last_modified_n_uid);
}
#endif /* CONFIG_9P_ENABLE_9P2000_u */
return false;
}
-static bool marshal_Rwstat(struct _marshal_ctx *ctx, struct lib9p_msg_Rwstat *val) {
+static bool marshal_Rwstat(struct lib9p_ctx *ctx, struct lib9p_msg_Rwstat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rwstat",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3694,13 +3658,13 @@ static bool marshal_Rwstat(struct _marshal_ctx *ctx, struct lib9p_msg_Rwstat *va
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_p9p
-static bool marshal_Topenfd(struct _marshal_ctx *ctx, struct lib9p_msg_Topenfd *val) {
+static bool marshal_Topenfd(struct lib9p_ctx *ctx, struct lib9p_msg_Topenfd *val, struct _marshal_ret *ret) {
uint32_t needed_size = 12;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Topenfd",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3709,17 +3673,17 @@ static bool marshal_Topenfd(struct _marshal_ctx *ctx, struct lib9p_msg_Topenfd *
MARSHAL_U8LE(ctx, 98);
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
- MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->mode & o_masks[ctx->version]);
return false;
}
-static bool marshal_Ropenfd(struct _marshal_ctx *ctx, struct lib9p_msg_Ropenfd *val) {
+static bool marshal_Ropenfd(struct lib9p_ctx *ctx, struct lib9p_msg_Ropenfd *val, struct _marshal_ret *ret) {
uint32_t needed_size = 28;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Ropenfd",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3727,7 +3691,7 @@ static bool marshal_Ropenfd(struct _marshal_ctx *ctx, struct lib9p_msg_Ropenfd *
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 99);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
MARSHAL_U32LE(ctx, val->iounit);
@@ -3737,13 +3701,13 @@ static bool marshal_Ropenfd(struct _marshal_ctx *ctx, struct lib9p_msg_Ropenfd *
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_L
-static bool marshal_Rlerror(struct _marshal_ctx *ctx, struct lib9p_msg_Rlerror *val) {
+static bool marshal_Rlerror(struct lib9p_ctx *ctx, struct lib9p_msg_Rlerror *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rlerror",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3755,13 +3719,13 @@ static bool marshal_Rlerror(struct _marshal_ctx *ctx, struct lib9p_msg_Rlerror *
return false;
}
-static bool marshal_Tstatfs(struct _marshal_ctx *ctx, struct lib9p_msg_Tstatfs *val) {
+static bool marshal_Tstatfs(struct lib9p_ctx *ctx, struct lib9p_msg_Tstatfs *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tstatfs",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3773,13 +3737,13 @@ static bool marshal_Tstatfs(struct _marshal_ctx *ctx, struct lib9p_msg_Tstatfs *
return false;
}
-static bool marshal_Rstatfs(struct _marshal_ctx *ctx, struct lib9p_msg_Rstatfs *val) {
+static bool marshal_Rstatfs(struct lib9p_ctx *ctx, struct lib9p_msg_Rstatfs *val, struct _marshal_ret *ret) {
uint32_t needed_size = 67;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rstatfs",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3799,13 +3763,13 @@ static bool marshal_Rstatfs(struct _marshal_ctx *ctx, struct lib9p_msg_Rstatfs *
return false;
}
-static bool marshal_Tlopen(struct _marshal_ctx *ctx, struct lib9p_msg_Tlopen *val) {
+static bool marshal_Tlopen(struct lib9p_ctx *ctx, struct lib9p_msg_Tlopen *val, struct _marshal_ret *ret) {
uint32_t needed_size = 15;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tlopen",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3814,17 +3778,17 @@ static bool marshal_Tlopen(struct _marshal_ctx *ctx, struct lib9p_msg_Tlopen *va
MARSHAL_U8LE(ctx, 12);
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
- MARSHAL_U32LE(ctx, val->flags & lo_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->flags & lo_masks[ctx->version]);
return false;
}
-static bool marshal_Rlopen(struct _marshal_ctx *ctx, struct lib9p_msg_Rlopen *val) {
+static bool marshal_Rlopen(struct lib9p_ctx *ctx, struct lib9p_msg_Rlopen *val, struct _marshal_ret *ret) {
uint32_t needed_size = 24;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rlopen",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3832,20 +3796,20 @@ static bool marshal_Rlopen(struct _marshal_ctx *ctx, struct lib9p_msg_Rlopen *va
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 13);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
MARSHAL_U32LE(ctx, val->iounit);
return false;
}
-static bool marshal_Tlcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Tlcreate *val) {
+static bool marshal_Tlcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Tlcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 25 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tlcreate",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3856,19 +3820,19 @@ static bool marshal_Tlcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Tlcreate
MARSHAL_U32LE(ctx, val->fid);
MARSHAL_U16LE(ctx, val->name.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->name.utf8, val->name.len);
- MARSHAL_U32LE(ctx, val->flags & lo_masks[ctx->ctx->version]);
- MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->flags & lo_masks[ctx->version]);
+ MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->gid);
return false;
}
-static bool marshal_Rlcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rlcreate *val) {
+static bool marshal_Rlcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Rlcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 24;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rlcreate",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3876,20 +3840,20 @@ static bool marshal_Rlcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rlcreate
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 15);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
MARSHAL_U32LE(ctx, val->iounit);
return false;
}
-static bool marshal_Tsymlink(struct _marshal_ctx *ctx, struct lib9p_msg_Tsymlink *val) {
+static bool marshal_Tsymlink(struct lib9p_ctx *ctx, struct lib9p_msg_Tsymlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 19 + val->name.len + val->symtgt.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tsymlink",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3906,13 +3870,13 @@ static bool marshal_Tsymlink(struct _marshal_ctx *ctx, struct lib9p_msg_Tsymlink
return false;
}
-static bool marshal_Rsymlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rsymlink *val) {
+static bool marshal_Rsymlink(struct lib9p_ctx *ctx, struct lib9p_msg_Rsymlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 20;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rsymlink",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3920,19 +3884,19 @@ static bool marshal_Rsymlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rsymlink
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 17);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
return false;
}
-static bool marshal_Tmknod(struct _marshal_ctx *ctx, struct lib9p_msg_Tmknod *val) {
+static bool marshal_Tmknod(struct lib9p_ctx *ctx, struct lib9p_msg_Tmknod *val, struct _marshal_ret *ret) {
uint32_t needed_size = 29 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tmknod",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3943,20 +3907,20 @@ static bool marshal_Tmknod(struct _marshal_ctx *ctx, struct lib9p_msg_Tmknod *va
MARSHAL_U32LE(ctx, val->dfid);
MARSHAL_U16LE(ctx, val->name.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->name.utf8, val->name.len);
- MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->major);
MARSHAL_U32LE(ctx, val->minor);
MARSHAL_U32LE(ctx, val->gid);
return false;
}
-static bool marshal_Rmknod(struct _marshal_ctx *ctx, struct lib9p_msg_Rmknod *val) {
+static bool marshal_Rmknod(struct lib9p_ctx *ctx, struct lib9p_msg_Rmknod *val, struct _marshal_ret *ret) {
uint32_t needed_size = 20;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rmknod",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3964,19 +3928,19 @@ static bool marshal_Rmknod(struct _marshal_ctx *ctx, struct lib9p_msg_Rmknod *va
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 19);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
return false;
}
-static bool marshal_Trename(struct _marshal_ctx *ctx, struct lib9p_msg_Trename *val) {
+static bool marshal_Trename(struct lib9p_ctx *ctx, struct lib9p_msg_Trename *val, struct _marshal_ret *ret) {
uint32_t needed_size = 17 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Trename",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -3991,13 +3955,13 @@ static bool marshal_Trename(struct _marshal_ctx *ctx, struct lib9p_msg_Trename *
return false;
}
-static bool marshal_Rrename(struct _marshal_ctx *ctx, struct lib9p_msg_Rrename *val) {
+static bool marshal_Rrename(struct lib9p_ctx *ctx, struct lib9p_msg_Rrename *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rrename",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4008,13 +3972,13 @@ static bool marshal_Rrename(struct _marshal_ctx *ctx, struct lib9p_msg_Rrename *
return false;
}
-static bool marshal_Treadlink(struct _marshal_ctx *ctx, struct lib9p_msg_Treadlink *val) {
+static bool marshal_Treadlink(struct lib9p_ctx *ctx, struct lib9p_msg_Treadlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Treadlink",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4026,13 +3990,13 @@ static bool marshal_Treadlink(struct _marshal_ctx *ctx, struct lib9p_msg_Treadli
return false;
}
-static bool marshal_Rreadlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rreadlink *val) {
+static bool marshal_Rreadlink(struct lib9p_ctx *ctx, struct lib9p_msg_Rreadlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 9 + val->target.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rreadlink",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4045,13 +4009,13 @@ static bool marshal_Rreadlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rreadli
return false;
}
-static bool marshal_Tgetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Tgetattr *val) {
+static bool marshal_Tgetattr(struct lib9p_ctx *ctx, struct lib9p_msg_Tgetattr *val, struct _marshal_ret *ret) {
uint32_t needed_size = 19;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tgetattr",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4060,17 +4024,17 @@ static bool marshal_Tgetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Tgetattr
MARSHAL_U8LE(ctx, 24);
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
- MARSHAL_U64LE(ctx, val->request_mask & getattr_masks[ctx->ctx->version]);
+ MARSHAL_U64LE(ctx, val->request_mask & getattr_masks[ctx->version]);
return false;
}
-static bool marshal_Rgetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Rgetattr *val) {
+static bool marshal_Rgetattr(struct lib9p_ctx *ctx, struct lib9p_msg_Rgetattr *val, struct _marshal_ret *ret) {
uint32_t needed_size = 160;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rgetattr",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4078,11 +4042,11 @@ static bool marshal_Rgetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Rgetattr
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 25);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U64LE(ctx, val->valid & getattr_masks[ctx->ctx->version]);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U64LE(ctx, val->valid & getattr_masks[ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
- MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->uid);
MARSHAL_U32LE(ctx, val->gid);
MARSHAL_U64LE(ctx, val->nlink);
@@ -4103,13 +4067,13 @@ static bool marshal_Rgetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Rgetattr
return false;
}
-static bool marshal_Tsetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Tsetattr *val) {
+static bool marshal_Tsetattr(struct lib9p_ctx *ctx, struct lib9p_msg_Tsetattr *val, struct _marshal_ret *ret) {
uint32_t needed_size = 67;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tsetattr",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4118,8 +4082,8 @@ static bool marshal_Tsetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Tsetattr
MARSHAL_U8LE(ctx, 26);
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
- MARSHAL_U32LE(ctx, val->valid & setattr_masks[ctx->ctx->version]);
- MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->valid & setattr_masks[ctx->version]);
+ MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->uid);
MARSHAL_U32LE(ctx, val->gid);
MARSHAL_U64LE(ctx, val->filesize);
@@ -4130,13 +4094,13 @@ static bool marshal_Tsetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Tsetattr
return false;
}
-static bool marshal_Rsetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Rsetattr *val) {
+static bool marshal_Rsetattr(struct lib9p_ctx *ctx, struct lib9p_msg_Rsetattr *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rsetattr",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4147,13 +4111,13 @@ static bool marshal_Rsetattr(struct _marshal_ctx *ctx, struct lib9p_msg_Rsetattr
return false;
}
-static bool marshal_Txattrwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Txattrwalk *val) {
+static bool marshal_Txattrwalk(struct lib9p_ctx *ctx, struct lib9p_msg_Txattrwalk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 17 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Txattrwalk",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4168,13 +4132,13 @@ static bool marshal_Txattrwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Txattr
return false;
}
-static bool marshal_Rxattrwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Rxattrwalk *val) {
+static bool marshal_Rxattrwalk(struct lib9p_ctx *ctx, struct lib9p_msg_Rxattrwalk *val, struct _marshal_ret *ret) {
uint32_t needed_size = 15;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rxattrwalk",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4186,13 +4150,13 @@ static bool marshal_Rxattrwalk(struct _marshal_ctx *ctx, struct lib9p_msg_Rxattr
return false;
}
-static bool marshal_Txattrcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Txattrcreate *val) {
+static bool marshal_Txattrcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Txattrcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 25 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Txattrcreate",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4208,13 +4172,13 @@ static bool marshal_Txattrcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Txat
return false;
}
-static bool marshal_Rxattrcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rxattrcreate *val) {
+static bool marshal_Rxattrcreate(struct lib9p_ctx *ctx, struct lib9p_msg_Rxattrcreate *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rxattrcreate",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4225,13 +4189,13 @@ static bool marshal_Rxattrcreate(struct _marshal_ctx *ctx, struct lib9p_msg_Rxat
return false;
}
-static bool marshal_Treaddir(struct _marshal_ctx *ctx, struct lib9p_msg_Treaddir *val) {
+static bool marshal_Treaddir(struct lib9p_ctx *ctx, struct lib9p_msg_Treaddir *val, struct _marshal_ret *ret) {
uint32_t needed_size = 23;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Treaddir",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4245,13 +4209,13 @@ static bool marshal_Treaddir(struct _marshal_ctx *ctx, struct lib9p_msg_Treaddir
return false;
}
-static bool marshal_Rreaddir(struct _marshal_ctx *ctx, struct lib9p_msg_Rreaddir *val) {
+static bool marshal_Rreaddir(struct lib9p_ctx *ctx, struct lib9p_msg_Rreaddir *val, struct _marshal_ret *ret) {
uint64_t needed_size = 11 + val->count;
- if (needed_size > (uint64_t)(ctx->ctx->max_msg_size)) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > (uint64_t)(ctx->max_msg_size)) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rreaddir",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = (uint32_t)needed_size;
@@ -4264,13 +4228,13 @@ static bool marshal_Rreaddir(struct _marshal_ctx *ctx, struct lib9p_msg_Rreaddir
return false;
}
-static bool marshal_Tfsync(struct _marshal_ctx *ctx, struct lib9p_msg_Tfsync *val) {
+static bool marshal_Tfsync(struct lib9p_ctx *ctx, struct lib9p_msg_Tfsync *val, struct _marshal_ret *ret) {
uint32_t needed_size = 15;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tfsync",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4283,13 +4247,13 @@ static bool marshal_Tfsync(struct _marshal_ctx *ctx, struct lib9p_msg_Tfsync *va
return false;
}
-static bool marshal_Rfsync(struct _marshal_ctx *ctx, struct lib9p_msg_Rfsync *val) {
+static bool marshal_Rfsync(struct lib9p_ctx *ctx, struct lib9p_msg_Rfsync *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rfsync",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4300,13 +4264,13 @@ static bool marshal_Rfsync(struct _marshal_ctx *ctx, struct lib9p_msg_Rfsync *va
return false;
}
-static bool marshal_Tlock(struct _marshal_ctx *ctx, struct lib9p_msg_Tlock *val) {
+static bool marshal_Tlock(struct lib9p_ctx *ctx, struct lib9p_msg_Tlock *val, struct _marshal_ret *ret) {
uint32_t needed_size = 38 + val->client_id.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tlock",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4316,7 +4280,7 @@ static bool marshal_Tlock(struct _marshal_ctx *ctx, struct lib9p_msg_Tlock *val)
MARSHAL_U16LE(ctx, val->tag);
MARSHAL_U32LE(ctx, val->fid);
MARSHAL_U8LE(ctx, val->type);
- MARSHAL_U32LE(ctx, val->flags & lock_flags_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->flags & lock_flags_masks[ctx->version]);
MARSHAL_U64LE(ctx, val->start);
MARSHAL_U64LE(ctx, val->length);
MARSHAL_U32LE(ctx, val->proc_id);
@@ -4325,13 +4289,13 @@ static bool marshal_Tlock(struct _marshal_ctx *ctx, struct lib9p_msg_Tlock *val)
return false;
}
-static bool marshal_Rlock(struct _marshal_ctx *ctx, struct lib9p_msg_Rlock *val) {
+static bool marshal_Rlock(struct lib9p_ctx *ctx, struct lib9p_msg_Rlock *val, struct _marshal_ret *ret) {
uint32_t needed_size = 8;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rlock",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4343,13 +4307,13 @@ static bool marshal_Rlock(struct _marshal_ctx *ctx, struct lib9p_msg_Rlock *val)
return false;
}
-static bool marshal_Tgetlock(struct _marshal_ctx *ctx, struct lib9p_msg_Tgetlock *val) {
+static bool marshal_Tgetlock(struct lib9p_ctx *ctx, struct lib9p_msg_Tgetlock *val, struct _marshal_ret *ret) {
uint32_t needed_size = 34 + val->client_id.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tgetlock",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4367,13 +4331,13 @@ static bool marshal_Tgetlock(struct _marshal_ctx *ctx, struct lib9p_msg_Tgetlock
return false;
}
-static bool marshal_Rgetlock(struct _marshal_ctx *ctx, struct lib9p_msg_Rgetlock *val) {
+static bool marshal_Rgetlock(struct lib9p_ctx *ctx, struct lib9p_msg_Rgetlock *val, struct _marshal_ret *ret) {
uint32_t needed_size = 30 + val->client_id.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rgetlock",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4390,13 +4354,13 @@ static bool marshal_Rgetlock(struct _marshal_ctx *ctx, struct lib9p_msg_Rgetlock
return false;
}
-static bool marshal_Tlink(struct _marshal_ctx *ctx, struct lib9p_msg_Tlink *val) {
+static bool marshal_Tlink(struct lib9p_ctx *ctx, struct lib9p_msg_Tlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 17 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tlink",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4411,13 +4375,13 @@ static bool marshal_Tlink(struct _marshal_ctx *ctx, struct lib9p_msg_Tlink *val)
return false;
}
-static bool marshal_Rlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rlink *val) {
+static bool marshal_Rlink(struct lib9p_ctx *ctx, struct lib9p_msg_Rlink *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rlink",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4428,13 +4392,13 @@ static bool marshal_Rlink(struct _marshal_ctx *ctx, struct lib9p_msg_Rlink *val)
return false;
}
-static bool marshal_Tmkdir(struct _marshal_ctx *ctx, struct lib9p_msg_Tmkdir *val) {
+static bool marshal_Tmkdir(struct lib9p_ctx *ctx, struct lib9p_msg_Tmkdir *val, struct _marshal_ret *ret) {
uint32_t needed_size = 21 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tmkdir",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4445,18 +4409,18 @@ static bool marshal_Tmkdir(struct _marshal_ctx *ctx, struct lib9p_msg_Tmkdir *va
MARSHAL_U32LE(ctx, val->dfid);
MARSHAL_U16LE(ctx, val->name.len);
MARSHAL_BYTES_ZEROCOPY(ctx, val->name.utf8, val->name.len);
- MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->ctx->version]);
+ MARSHAL_U32LE(ctx, val->mode & mode_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->gid);
return false;
}
-static bool marshal_Rmkdir(struct _marshal_ctx *ctx, struct lib9p_msg_Rmkdir *val) {
+static bool marshal_Rmkdir(struct lib9p_ctx *ctx, struct lib9p_msg_Rmkdir *val, struct _marshal_ret *ret) {
uint32_t needed_size = 20;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rmkdir",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4464,19 +4428,19 @@ static bool marshal_Rmkdir(struct _marshal_ctx *ctx, struct lib9p_msg_Rmkdir *va
MARSHAL_U32LE(ctx, offsetof_end - offsetof_size);
MARSHAL_U8LE(ctx, 73);
MARSHAL_U16LE(ctx, val->tag);
- MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->ctx->version]);
+ MARSHAL_U8LE(ctx, val->qid.type & qt_masks[ctx->version]);
MARSHAL_U32LE(ctx, val->qid.vers);
MARSHAL_U64LE(ctx, val->qid.path);
return false;
}
-static bool marshal_Trenameat(struct _marshal_ctx *ctx, struct lib9p_msg_Trenameat *val) {
+static bool marshal_Trenameat(struct lib9p_ctx *ctx, struct lib9p_msg_Trenameat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 19 + val->oldname.len + val->newname.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Trenameat",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4493,13 +4457,13 @@ static bool marshal_Trenameat(struct _marshal_ctx *ctx, struct lib9p_msg_Trename
return false;
}
-static bool marshal_Rrenameat(struct _marshal_ctx *ctx, struct lib9p_msg_Rrenameat *val) {
+static bool marshal_Rrenameat(struct lib9p_ctx *ctx, struct lib9p_msg_Rrenameat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rrenameat",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4510,13 +4474,13 @@ static bool marshal_Rrenameat(struct _marshal_ctx *ctx, struct lib9p_msg_Rrename
return false;
}
-static bool marshal_Tunlinkat(struct _marshal_ctx *ctx, struct lib9p_msg_Tunlinkat *val) {
+static bool marshal_Tunlinkat(struct lib9p_ctx *ctx, struct lib9p_msg_Tunlinkat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 17 + val->name.len;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tunlinkat",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4531,13 +4495,13 @@ static bool marshal_Tunlinkat(struct _marshal_ctx *ctx, struct lib9p_msg_Tunlink
return false;
}
-static bool marshal_Runlinkat(struct _marshal_ctx *ctx, struct lib9p_msg_Runlinkat *val) {
+static bool marshal_Runlinkat(struct lib9p_ctx *ctx, struct lib9p_msg_Runlinkat *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Runlinkat",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4550,13 +4514,13 @@ static bool marshal_Runlinkat(struct _marshal_ctx *ctx, struct lib9p_msg_Runlink
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
-static bool marshal_Tsession(struct _marshal_ctx *ctx, struct lib9p_msg_Tsession *val) {
+static bool marshal_Tsession(struct lib9p_ctx *ctx, struct lib9p_msg_Tsession *val, struct _marshal_ret *ret) {
uint32_t needed_size = 15;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tsession",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4568,13 +4532,13 @@ static bool marshal_Tsession(struct _marshal_ctx *ctx, struct lib9p_msg_Tsession
return false;
}
-static bool marshal_Rsession(struct _marshal_ctx *ctx, struct lib9p_msg_Rsession *val) {
+static bool marshal_Rsession(struct lib9p_ctx *ctx, struct lib9p_msg_Rsession *val, struct _marshal_ret *ret) {
uint32_t needed_size = 7;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rsession",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4585,16 +4549,16 @@ static bool marshal_Rsession(struct _marshal_ctx *ctx, struct lib9p_msg_Rsession
return false;
}
-static bool marshal_Tsread(struct _marshal_ctx *ctx, struct lib9p_msg_Tsread *val) {
+static bool marshal_Tsread(struct lib9p_ctx *ctx, struct lib9p_msg_Tsread *val, struct _marshal_ret *ret) {
uint64_t needed_size = 13;
for (uint16_t i = 0; i < val->nwname; i++) {
needed_size += 2 + val->wname[i].len;
}
- if (needed_size > (uint64_t)(ctx->ctx->max_msg_size)) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > (uint64_t)(ctx->max_msg_size)) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tsread",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = (uint32_t)needed_size;
@@ -4611,13 +4575,13 @@ static bool marshal_Tsread(struct _marshal_ctx *ctx, struct lib9p_msg_Tsread *va
return false;
}
-static bool marshal_Rsread(struct _marshal_ctx *ctx, struct lib9p_msg_Rsread *val) {
+static bool marshal_Rsread(struct lib9p_ctx *ctx, struct lib9p_msg_Rsread *val, struct _marshal_ret *ret) {
uint64_t needed_size = 11 + val->count;
- if (needed_size > (uint64_t)(ctx->ctx->max_msg_size)) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > (uint64_t)(ctx->max_msg_size)) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rsread",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = (uint32_t)needed_size;
@@ -4630,16 +4594,16 @@ static bool marshal_Rsread(struct _marshal_ctx *ctx, struct lib9p_msg_Rsread *va
return false;
}
-static bool marshal_Tswrite(struct _marshal_ctx *ctx, struct lib9p_msg_Tswrite *val) {
+static bool marshal_Tswrite(struct lib9p_ctx *ctx, struct lib9p_msg_Tswrite *val, struct _marshal_ret *ret) {
uint64_t needed_size = 17 + val->count;
for (uint16_t i = 0; i < val->nwname; i++) {
needed_size += 2 + val->wname[i].len;
}
- if (needed_size > (uint64_t)(ctx->ctx->max_msg_size)) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > (uint64_t)(ctx->max_msg_size)) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Tswrite",
- ctx->ctx->version ? "negotiated" : "client",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "client",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = (uint32_t)needed_size;
@@ -4658,13 +4622,13 @@ static bool marshal_Tswrite(struct _marshal_ctx *ctx, struct lib9p_msg_Tswrite *
return false;
}
-static bool marshal_Rswrite(struct _marshal_ctx *ctx, struct lib9p_msg_Rswrite *val) {
+static bool marshal_Rswrite(struct lib9p_ctx *ctx, struct lib9p_msg_Rswrite *val, struct _marshal_ret *ret) {
uint32_t needed_size = 11;
- if (needed_size > ctx->ctx->max_msg_size) {
- lib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
+ if (needed_size > ctx->max_msg_size) {
+ lib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",
"Rswrite",
- ctx->ctx->version ? "negotiated" : "server",
- ctx->ctx->max_msg_size);
+ ctx->version ? "negotiated" : "server",
+ ctx->max_msg_size);
return true;
}
uint32_t offsetof_end = needed_size;
@@ -4677,34 +4641,2935 @@ static bool marshal_Rswrite(struct _marshal_ctx *ctx, struct lib9p_msg_Rswrite *
}
#endif /* CONFIG_9P_ENABLE_9P2000_e */
-/* function tables ************************************************************/
+/* *_format *******************************************************************/
+
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_tag_format(lib9p_tag_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_TAG_NOTAG:
+ fmt_state_puts(state, "NOTAG");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu16, *self);
+ }
+}
+
+static void lib9p_fid_format(lib9p_fid_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_FID_NOFID:
+ fmt_state_puts(state, "NOFID");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu32, *self);
+ }
+}
+
+static void lib9p_s_format(struct lib9p_s *self, struct fmt_state *state) {
+ /* https://gcc.gnu.org/bugzilla/show_bug.cgi?id=47781 */
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wformat"
+#pragma GCC diagnostic ignored "-Wformat-extra-args"
+ fmt_state_printf(state, "%.*q", self->len, self->utf8);
+#pragma GCC diagnostic pop
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_dm_format(lib9p_dm_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DIR");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "APPEND");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "EXCL");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "_PLAN9_MOUNT");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "AUTH");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "TMP");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DEVICE");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PIPE");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SOCKET");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SETUID");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SETGID");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<17");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<16");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<15)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<15");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<14)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<14");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<13)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<13");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<12)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<12");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<11");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<10");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<9");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OWNER_R");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OWNER_W");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OWNER_X");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GROUP_R");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GROUP_W");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GROUP_X");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OTHER_R");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OTHER_W");
+ empty = false;
+ }
+ if ((*self & ~((lib9p_dm_t)0777)) & (UINT32_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "OTHER_X");
+ empty = false;
+ }
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_printf(state, "%#04"PRIo32, *self & 0777);
+ fmt_state_putchar(state, ')');
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_qt_format(lib9p_qt_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT8_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DIR");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "APPEND");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "EXCL");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "_PLAN9_MOUNT");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "AUTH");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "TMP");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SYMLINK");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<0");
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_qid_format(struct lib9p_qid *self, struct fmt_state *state) {
+ fmt_state_putchar(state, '{');
+ fmt_state_puts(state, " type=");
+ lib9p_qt_format(&self->type, state);
+ fmt_state_puts(state, " vers=");
+ fmt_state_printf(state, "%"PRIu32, self->vers);
+ fmt_state_puts(state, " path=");
+ fmt_state_printf(state, "%"PRIu64, self->path);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_stat_format(struct lib9p_stat *self, struct fmt_state *state) {
+ fmt_state_putchar(state, '{');
+ fmt_state_puts(state, " kern_type=");
+ fmt_state_printf(state, "%"PRIu16, self->kern_type);
+ fmt_state_puts(state, " kern_dev=");
+ fmt_state_printf(state, "%"PRIu32, self->kern_dev);
+ fmt_state_puts(state, " file_qid=");
+ lib9p_qid_format(&self->file_qid, state);
+ fmt_state_puts(state, " file_mode=");
+ lib9p_dm_format(&self->file_mode, state);
+ fmt_state_puts(state, " file_atime=");
+ fmt_state_printf(state, "%"PRIu32, self->file_atime);
+ fmt_state_puts(state, " file_mtime=");
+ fmt_state_printf(state, "%"PRIu32, self->file_mtime);
+ fmt_state_puts(state, " file_size=");
+ fmt_state_printf(state, "%"PRIu64, self->file_size);
+ fmt_state_puts(state, " file_name=");
+ lib9p_s_format(&self->file_name, state);
+ fmt_state_puts(state, " file_owner_uid=");
+ lib9p_s_format(&self->file_owner_uid, state);
+ fmt_state_puts(state, " file_owner_gid=");
+ lib9p_s_format(&self->file_owner_gid, state);
+ fmt_state_puts(state, " file_last_modified_uid=");
+ lib9p_s_format(&self->file_last_modified_uid, state);
+#if CONFIG_9P_ENABLE_9P2000_u
+ fmt_state_puts(state, " file_extension=");
+ lib9p_s_format(&self->file_extension, state);
+ fmt_state_puts(state, " file_owner_n_uid=");
+ lib9p_nuid_format(&self->file_owner_n_uid, state);
+ fmt_state_puts(state, " file_owner_n_gid=");
+ lib9p_nuid_format(&self->file_owner_n_gid, state);
+ fmt_state_puts(state, " file_last_modified_n_uid=");
+ lib9p_nuid_format(&self->file_last_modified_n_uid, state);
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
+ fmt_state_puts(state, " }");
+}
-const uint32_t _lib9p_table_msg_min_size[LIB9P_VER_NUM] = {
- [LIB9P_VER_unknown] = 9,
+static void lib9p_o_format(lib9p_o_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT8_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<7");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "RCLOSE");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "CEXEC");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "TRUNC");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<3");
+ empty = false;
+ }
+ if (*self & (UINT8_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<2");
+ empty = false;
+ }
+ switch (*self & LIB9P_O_MODE_MASK) {
+ case LIB9P_O_MODE_READ:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_READ");
+ empty = false;
+ break;
+ case LIB9P_O_MODE_WRITE:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_WRITE");
+ empty = false;
+ break;
+ case LIB9P_O_MODE_RDWR:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_RDWR");
+ empty = false;
+ break;
+ case LIB9P_O_MODE_EXEC:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_EXEC");
+ empty = false;
+ break;
+ default:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_printf(state, "%"PRIu8, *self & LIB9P_O_MODE_MASK);
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_msg_Tversion_format(struct lib9p_msg_Tversion *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tversion {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " max_msg_size=");
+ fmt_state_printf(state, "%"PRIu32, self->max_msg_size);
+ fmt_state_puts(state, " version=");
+ lib9p_s_format(&self->version, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rversion_format(struct lib9p_msg_Rversion *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rversion {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " max_msg_size=");
+ fmt_state_printf(state, "%"PRIu32, self->max_msg_size);
+ fmt_state_puts(state, " version=");
+ lib9p_s_format(&self->version, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tauth_format(struct lib9p_msg_Tauth *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tauth {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " afid=");
+ lib9p_fid_format(&self->afid, state);
+ fmt_state_puts(state, " uname=");
+ lib9p_s_format(&self->uname, state);
+ fmt_state_puts(state, " aname=");
+ lib9p_s_format(&self->aname, state);
+#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
+ fmt_state_puts(state, " n_uid=");
+ lib9p_nuid_format(&self->n_uid, state);
+#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rauth_format(struct lib9p_msg_Rauth *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rauth {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " aqid=");
+ lib9p_qid_format(&self->aqid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tattach_format(struct lib9p_msg_Tattach *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tattach {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " afid=");
+ lib9p_fid_format(&self->afid, state);
+ fmt_state_puts(state, " uname=");
+ lib9p_s_format(&self->uname, state);
+ fmt_state_puts(state, " aname=");
+ lib9p_s_format(&self->aname, state);
+#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
+ fmt_state_puts(state, " n_uid=");
+ lib9p_nuid_format(&self->n_uid, state);
+#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rattach_format(struct lib9p_msg_Rattach *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rattach {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rerror_format(struct lib9p_msg_Rerror *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rerror {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " ename=");
+ lib9p_s_format(&self->ename, state);
+#if CONFIG_9P_ENABLE_9P2000_u
+ fmt_state_puts(state, " errno=");
+ lib9p_errno_format(&self->errno, state);
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tflush_format(struct lib9p_msg_Tflush *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tflush {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " oldtag=");
+ fmt_state_printf(state, "%"PRIu16, self->oldtag);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rflush_format(struct lib9p_msg_Rflush *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rflush {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Twalk_format(struct lib9p_msg_Twalk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Twalk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " newfid=");
+ lib9p_fid_format(&self->newfid, state);
+ fmt_state_puts(state, " nwname=");
+ fmt_state_printf(state, "%"PRIu16, self->nwname);
+ fmt_state_puts(state, " wname=[");
+ for (uint16_t i = 0; i < self->nwname; i++) {
+ if (i)
+ fmt_state_puts(state, ", ");
+ lib9p_s_format(&self->wname[i], state);
+ }
+ fmt_state_puts(state, " ]");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rwalk_format(struct lib9p_msg_Rwalk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rwalk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " nwqid=");
+ fmt_state_printf(state, "%"PRIu16, self->nwqid);
+ fmt_state_puts(state, " wqid=[");
+ for (uint16_t i = 0; i < self->nwqid; i++) {
+ if (i)
+ fmt_state_puts(state, ", ");
+ lib9p_qid_format(&self->wqid[i], state);
+ }
+ fmt_state_puts(state, " ]");
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_msg_Topen_format(struct lib9p_msg_Topen *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Topen {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_o_format(&self->mode, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Ropen_format(struct lib9p_msg_Ropen *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Ropen {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " iounit=");
+ fmt_state_printf(state, "%"PRIu32, self->iounit);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tcreate_format(struct lib9p_msg_Tcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " perm=");
+ lib9p_dm_format(&self->perm, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_o_format(&self->mode, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rcreate_format(struct lib9p_msg_Rcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " iounit=");
+ fmt_state_printf(state, "%"PRIu32, self->iounit);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_msg_Tread_format(struct lib9p_msg_Tread *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tread {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " offset=");
+ fmt_state_printf(state, "%"PRIu64, self->offset);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rread_format(struct lib9p_msg_Rread *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rread {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " data=<bytedata>");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Twrite_format(struct lib9p_msg_Twrite *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Twrite {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " offset=");
+ fmt_state_printf(state, "%"PRIu64, self->offset);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " data=<bytedata>");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rwrite_format(struct lib9p_msg_Rwrite *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rwrite {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tclunk_format(struct lib9p_msg_Tclunk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tclunk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rclunk_format(struct lib9p_msg_Rclunk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rclunk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tremove_format(struct lib9p_msg_Tremove *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tremove {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rremove_format(struct lib9p_msg_Rremove *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rremove {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_msg_Tstat_format(struct lib9p_msg_Tstat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tstat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rstat_format(struct lib9p_msg_Rstat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rstat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " stat=");
+ lib9p_stat_format(&self->stat, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Twstat_format(struct lib9p_msg_Twstat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Twstat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " stat=");
+ lib9p_stat_format(&self->stat, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rwstat_format(struct lib9p_msg_Rwstat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rwstat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000_p9p
+static void lib9p_msg_Topenfd_format(struct lib9p_msg_Topenfd *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Topenfd {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_o_format(&self->mode, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Ropenfd_format(struct lib9p_msg_Ropenfd *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Ropenfd {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " iounit=");
+ fmt_state_printf(state, "%"PRIu32, self->iounit);
+ fmt_state_puts(state, " unixfd=");
+ fmt_state_printf(state, "%"PRIu32, self->unixfd);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
+#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
+static void lib9p_nuid_format(lib9p_nuid_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_NUID_NONUID:
+ fmt_state_puts(state, "NONUID");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu32, *self);
+ }
+}
+
+static void lib9p_errno_format(lib9p_errno_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_ERRNO_NOERROR:
+ fmt_state_puts(state, "NOERROR");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu32, *self);
+ }
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
+#if CONFIG_9P_ENABLE_9P2000_L
+static void lib9p_super_magic_format(lib9p_super_magic_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_SUPER_MAGIC_V9FS_MAGIC:
+ fmt_state_puts(state, "V9FS_MAGIC");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu32, *self);
+ }
+}
+
+static void lib9p_lo_format(lib9p_lo_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT32_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<31");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<30");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<29");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<28");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<27");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<26");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<23");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<21");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SYNC");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "CLOEXEC");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "NOATIME");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "NOFOLLOW");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DIRECTORY");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<15)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "LARGEFILE");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<14)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DIRECT");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<13)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "BSD_FASYNC");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<12)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DSYNC");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "NONBLOCK");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "APPEND");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "TRUNC");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "NOCTTY");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "EXCL");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "CREATE");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<5");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<4");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<3");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<2");
+ empty = false;
+ }
+ switch (*self & LIB9P_LO_MODE_MASK) {
+ case LIB9P_LO_MODE_RDONLY:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_RDONLY");
+ empty = false;
+ break;
+ case LIB9P_LO_MODE_WRONLY:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_WRONLY");
+ empty = false;
+ break;
+ case LIB9P_LO_MODE_RDWR:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_RDWR");
+ empty = false;
+ break;
+ case LIB9P_LO_MODE_NOACCESS:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE_NOACCESS");
+ empty = false;
+ break;
+ default:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_printf(state, "%"PRIu32, *self & LIB9P_LO_MODE_MASK);
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_dt_format(lib9p_dt_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_DT_UNKNOWN:
+ fmt_state_puts(state, "UNKNOWN");
+ break;
+ case LIB9P_DT_PIPE:
+ fmt_state_puts(state, "PIPE");
+ break;
+ case LIB9P_DT_CHAR_DEV:
+ fmt_state_puts(state, "CHAR_DEV");
+ break;
+ case LIB9P_DT_DIRECTORY:
+ fmt_state_puts(state, "DIRECTORY");
+ break;
+ case LIB9P_DT_BLOCK_DEV:
+ fmt_state_puts(state, "BLOCK_DEV");
+ break;
+ case LIB9P_DT_REGULAR:
+ fmt_state_puts(state, "REGULAR");
+ break;
+ case LIB9P_DT_SYMLINK:
+ fmt_state_puts(state, "SYMLINK");
+ break;
+ case LIB9P_DT_SOCKET:
+ fmt_state_puts(state, "SOCKET");
+ break;
+ case _LIB9P_DT_WHITEOUT:
+ fmt_state_puts(state, "_WHITEOUT");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu8, *self);
+ }
+}
+
+static void lib9p_mode_format(lib9p_mode_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT32_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<31");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<30");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<29");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<28");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<27");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<26");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<23");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<21");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<20");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<19");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<18");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<17");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<16");
+ empty = false;
+ }
+ switch (*self & LIB9P_MODE_FMT_MASK) {
+ case LIB9P_MODE_FMT_PIPE:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_PIPE");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_CHAR_DEV:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_CHAR_DEV");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_DIRECTORY:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_DIRECTORY");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_BLOCK_DEV:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_BLOCK_DEV");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_REGULAR:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_REGULAR");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_SYMLINK:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_SYMLINK");
+ empty = false;
+ break;
+ case LIB9P_MODE_FMT_SOCKET:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "FMT_SOCKET");
+ empty = false;
+ break;
+ default:
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_printf(state, "%"PRIu32, *self & LIB9P_MODE_FMT_MASK);
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_SETGROUP");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_SETUSER");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_STICKY");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OWNER_R");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OWNER_W");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OWNER_X");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_GROUP_R");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_GROUP_W");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_GROUP_X");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OTHER_R");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OTHER_W");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "PERM_OTHER_X");
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_b4_format(lib9p_b4_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_B4_FALSE:
+ fmt_state_puts(state, "FALSE");
+ break;
+ case LIB9P_B4_TRUE:
+ fmt_state_puts(state, "TRUE");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu32, *self);
+ }
+}
+
+static void lib9p_getattr_format(lib9p_getattr_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT64_C(1)<<63)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<63");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<62)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<62");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<61)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<61");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<60)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<60");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<59)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<59");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<58)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<58");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<57)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<57");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<56)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<56");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<55)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<55");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<54)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<54");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<53)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<53");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<52)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<52");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<51)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<51");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<50)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<50");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<49)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<49");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<48)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<48");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<47)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<47");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<46)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<46");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<45)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<45");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<44)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<44");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<43)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<43");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<42)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<42");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<41)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<41");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<40)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<40");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<39)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<39");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<38)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<38");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<37)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<37");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<36)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<36");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<35)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<35");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<34)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<34");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<33)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<33");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<32)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<32");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<31");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<30");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<29");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<28");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<27");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<26");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<23");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<21");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<20");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<19");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<18");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<17");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<16");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<15)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<15");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<14)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<14");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<13)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "DATA_VERSION");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<12)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GEN");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "BTIME");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "BLOCKS");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SIZE");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "INO");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "CTIME");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MTIME");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "ATIME");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "RDEV");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GID");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "UID");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "NLINK");
+ empty = false;
+ }
+ if (*self & (UINT64_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE");
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_setattr_format(lib9p_setattr_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT32_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<31");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<30");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<29");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<28");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<27");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<26");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<23");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<21");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<20");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<19");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<18");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<17");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<16");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<15)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<15");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<14)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<14");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<13)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<13");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<12)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<12");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<11");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<10");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<9");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MTIME_SET");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "ATIME_SET");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "CTIME");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MTIME");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "ATIME");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "SIZE");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "GID");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "UID");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "MODE");
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_lock_type_format(lib9p_lock_type_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_LOCK_TYPE_RDLCK:
+ fmt_state_puts(state, "RDLCK");
+ break;
+ case LIB9P_LOCK_TYPE_WRLCK:
+ fmt_state_puts(state, "WRLCK");
+ break;
+ case LIB9P_LOCK_TYPE_UNLCK:
+ fmt_state_puts(state, "UNLCK");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu8, *self);
+ }
+}
+
+static void lib9p_lock_flags_format(lib9p_lock_flags_t *self, struct fmt_state *state) {
+ bool empty = true;
+ fmt_state_putchar(state, '(');
+ if (*self & (UINT32_C(1)<<31)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<31");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<30)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<30");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<29)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<29");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<28)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<28");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<27)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<27");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<26)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<26");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<25)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<25");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<24)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<24");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<23)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<23");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<22)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<22");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<21)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<21");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<20)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<20");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<19)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<19");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<18)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<18");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<17)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<17");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<16)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<16");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<15)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<15");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<14)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<14");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<13)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<13");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<12)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<12");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<11)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<11");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<10)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<10");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<9)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<9");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<8)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<8");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<7)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<7");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<6)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<6");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<5)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<5");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<4)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<4");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<3)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<3");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<2)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "1<<2");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<1)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "RECLAIM");
+ empty = false;
+ }
+ if (*self & (UINT32_C(1)<<0)) {
+ if (!empty)
+ fmt_state_putchar(state, '|');
+ fmt_state_puts(state, "BLOCK");
+ empty = false;
+ }
+ if (empty)
+ fmt_state_putchar(state, '0');
+ fmt_state_putchar(state, ')');
+}
+
+static void lib9p_lock_status_format(lib9p_lock_status_t *self, struct fmt_state *state) {
+ switch (*self) {
+ case LIB9P_LOCK_STATUS_SUCCESS:
+ fmt_state_puts(state, "SUCCESS");
+ break;
+ case LIB9P_LOCK_STATUS_BLOCKED:
+ fmt_state_puts(state, "BLOCKED");
+ break;
+ case LIB9P_LOCK_STATUS_ERROR:
+ fmt_state_puts(state, "ERROR");
+ break;
+ case LIB9P_LOCK_STATUS_GRACE:
+ fmt_state_puts(state, "GRACE");
+ break;
+ default:
+ fmt_state_printf(state, "%"PRIu8, *self);
+ }
+}
+
+static void lib9p_msg_Rlerror_format(struct lib9p_msg_Rlerror *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rlerror {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " ecode=");
+ lib9p_errno_format(&self->ecode, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tstatfs_format(struct lib9p_msg_Tstatfs *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tstatfs {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rstatfs_format(struct lib9p_msg_Rstatfs *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rstatfs {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " type=");
+ lib9p_super_magic_format(&self->type, state);
+ fmt_state_puts(state, " bsize=");
+ fmt_state_printf(state, "%"PRIu32, self->bsize);
+ fmt_state_puts(state, " blocks=");
+ fmt_state_printf(state, "%"PRIu64, self->blocks);
+ fmt_state_puts(state, " bfree=");
+ fmt_state_printf(state, "%"PRIu64, self->bfree);
+ fmt_state_puts(state, " bavail=");
+ fmt_state_printf(state, "%"PRIu64, self->bavail);
+ fmt_state_puts(state, " files=");
+ fmt_state_printf(state, "%"PRIu64, self->files);
+ fmt_state_puts(state, " ffree=");
+ fmt_state_printf(state, "%"PRIu64, self->ffree);
+ fmt_state_puts(state, " fsid=");
+ fmt_state_printf(state, "%"PRIu64, self->fsid);
+ fmt_state_puts(state, " namelen=");
+ fmt_state_printf(state, "%"PRIu32, self->namelen);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tlopen_format(struct lib9p_msg_Tlopen *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tlopen {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " flags=");
+ lib9p_lo_format(&self->flags, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rlopen_format(struct lib9p_msg_Rlopen *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rlopen {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " iounit=");
+ fmt_state_printf(state, "%"PRIu32, self->iounit);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tlcreate_format(struct lib9p_msg_Tlcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tlcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " flags=");
+ lib9p_lo_format(&self->flags, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_mode_format(&self->mode, state);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rlcreate_format(struct lib9p_msg_Rlcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rlcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " iounit=");
+ fmt_state_printf(state, "%"PRIu32, self->iounit);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tsymlink_format(struct lib9p_msg_Tsymlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tsymlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " symtgt=");
+ lib9p_s_format(&self->symtgt, state);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rsymlink_format(struct lib9p_msg_Rsymlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rsymlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tmknod_format(struct lib9p_msg_Tmknod *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tmknod {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " dfid=");
+ lib9p_fid_format(&self->dfid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_mode_format(&self->mode, state);
+ fmt_state_puts(state, " major=");
+ fmt_state_printf(state, "%"PRIu32, self->major);
+ fmt_state_puts(state, " minor=");
+ fmt_state_printf(state, "%"PRIu32, self->minor);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rmknod_format(struct lib9p_msg_Rmknod *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rmknod {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Trename_format(struct lib9p_msg_Trename *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Trename {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " dfid=");
+ lib9p_fid_format(&self->dfid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rrename_format(struct lib9p_msg_Rrename *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rrename {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Treadlink_format(struct lib9p_msg_Treadlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Treadlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rreadlink_format(struct lib9p_msg_Rreadlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rreadlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " target=");
+ lib9p_s_format(&self->target, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tgetattr_format(struct lib9p_msg_Tgetattr *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tgetattr {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " request_mask=");
+ lib9p_getattr_format(&self->request_mask, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rgetattr_format(struct lib9p_msg_Rgetattr *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rgetattr {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " valid=");
+ lib9p_getattr_format(&self->valid, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_mode_format(&self->mode, state);
+ fmt_state_puts(state, " uid=");
+ lib9p_nuid_format(&self->uid, state);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " nlink=");
+ fmt_state_printf(state, "%"PRIu64, self->nlink);
+ fmt_state_puts(state, " rdev=");
+ fmt_state_printf(state, "%"PRIu64, self->rdev);
+ fmt_state_puts(state, " filesize=");
+ fmt_state_printf(state, "%"PRIu64, self->filesize);
+ fmt_state_puts(state, " blksize=");
+ fmt_state_printf(state, "%"PRIu64, self->blksize);
+ fmt_state_puts(state, " blocks=");
+ fmt_state_printf(state, "%"PRIu64, self->blocks);
+ fmt_state_puts(state, " atime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->atime_sec);
+ fmt_state_puts(state, " atime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->atime_nsec);
+ fmt_state_puts(state, " mtime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->mtime_sec);
+ fmt_state_puts(state, " mtime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->mtime_nsec);
+ fmt_state_puts(state, " ctime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->ctime_sec);
+ fmt_state_puts(state, " ctime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->ctime_nsec);
+ fmt_state_puts(state, " btime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->btime_sec);
+ fmt_state_puts(state, " btime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->btime_nsec);
+ fmt_state_puts(state, " gen=");
+ fmt_state_printf(state, "%"PRIu64, self->gen);
+ fmt_state_puts(state, " data_version=");
+ fmt_state_printf(state, "%"PRIu64, self->data_version);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tsetattr_format(struct lib9p_msg_Tsetattr *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tsetattr {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " valid=");
+ lib9p_setattr_format(&self->valid, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_mode_format(&self->mode, state);
+ fmt_state_puts(state, " uid=");
+ lib9p_nuid_format(&self->uid, state);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " filesize=");
+ fmt_state_printf(state, "%"PRIu64, self->filesize);
+ fmt_state_puts(state, " atime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->atime_sec);
+ fmt_state_puts(state, " atime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->atime_nsec);
+ fmt_state_puts(state, " mtime_sec=");
+ fmt_state_printf(state, "%"PRIu64, self->mtime_sec);
+ fmt_state_puts(state, " mtime_nsec=");
+ fmt_state_printf(state, "%"PRIu64, self->mtime_nsec);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rsetattr_format(struct lib9p_msg_Rsetattr *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rsetattr {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Txattrwalk_format(struct lib9p_msg_Txattrwalk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Txattrwalk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " newfid=");
+ lib9p_fid_format(&self->newfid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rxattrwalk_format(struct lib9p_msg_Rxattrwalk *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rxattrwalk {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " attr_size=");
+ fmt_state_printf(state, "%"PRIu64, self->attr_size);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Txattrcreate_format(struct lib9p_msg_Txattrcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Txattrcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " attr_size=");
+ fmt_state_printf(state, "%"PRIu64, self->attr_size);
+ fmt_state_puts(state, " flags=");
+ fmt_state_printf(state, "%"PRIu32, self->flags);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rxattrcreate_format(struct lib9p_msg_Rxattrcreate *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rxattrcreate {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Treaddir_format(struct lib9p_msg_Treaddir *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Treaddir {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " offset=");
+ fmt_state_printf(state, "%"PRIu64, self->offset);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rreaddir_format(struct lib9p_msg_Rreaddir *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rreaddir {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " data=<bytedata>");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tfsync_format(struct lib9p_msg_Tfsync *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tfsync {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " datasync=");
+ lib9p_b4_format(&self->datasync, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rfsync_format(struct lib9p_msg_Rfsync *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rfsync {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tlock_format(struct lib9p_msg_Tlock *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tlock {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " type=");
+ lib9p_lock_type_format(&self->type, state);
+ fmt_state_puts(state, " flags=");
+ lib9p_lock_flags_format(&self->flags, state);
+ fmt_state_puts(state, " start=");
+ fmt_state_printf(state, "%"PRIu64, self->start);
+ fmt_state_puts(state, " length=");
+ fmt_state_printf(state, "%"PRIu64, self->length);
+ fmt_state_puts(state, " proc_id=");
+ fmt_state_printf(state, "%"PRIu32, self->proc_id);
+ fmt_state_puts(state, " client_id=");
+ lib9p_s_format(&self->client_id, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rlock_format(struct lib9p_msg_Rlock *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rlock {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " status=");
+ lib9p_lock_status_format(&self->status, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tgetlock_format(struct lib9p_msg_Tgetlock *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tgetlock {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " type=");
+ lib9p_lock_type_format(&self->type, state);
+ fmt_state_puts(state, " start=");
+ fmt_state_printf(state, "%"PRIu64, self->start);
+ fmt_state_puts(state, " length=");
+ fmt_state_printf(state, "%"PRIu64, self->length);
+ fmt_state_puts(state, " proc_id=");
+ fmt_state_printf(state, "%"PRIu32, self->proc_id);
+ fmt_state_puts(state, " client_id=");
+ lib9p_s_format(&self->client_id, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rgetlock_format(struct lib9p_msg_Rgetlock *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rgetlock {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " type=");
+ lib9p_lock_type_format(&self->type, state);
+ fmt_state_puts(state, " start=");
+ fmt_state_printf(state, "%"PRIu64, self->start);
+ fmt_state_puts(state, " length=");
+ fmt_state_printf(state, "%"PRIu64, self->length);
+ fmt_state_puts(state, " proc_id=");
+ fmt_state_printf(state, "%"PRIu32, self->proc_id);
+ fmt_state_puts(state, " client_id=");
+ lib9p_s_format(&self->client_id, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tlink_format(struct lib9p_msg_Tlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " dfid=");
+ lib9p_fid_format(&self->dfid, state);
+ fmt_state_puts(state, " fid=");
+ lib9p_fid_format(&self->fid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rlink_format(struct lib9p_msg_Rlink *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rlink {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tmkdir_format(struct lib9p_msg_Tmkdir *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tmkdir {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " dfid=");
+ lib9p_fid_format(&self->dfid, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " mode=");
+ lib9p_mode_format(&self->mode, state);
+ fmt_state_puts(state, " gid=");
+ lib9p_nuid_format(&self->gid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rmkdir_format(struct lib9p_msg_Rmkdir *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rmkdir {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " qid=");
+ lib9p_qid_format(&self->qid, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Trenameat_format(struct lib9p_msg_Trenameat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Trenameat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " olddirfid=");
+ lib9p_fid_format(&self->olddirfid, state);
+ fmt_state_puts(state, " oldname=");
+ lib9p_s_format(&self->oldname, state);
+ fmt_state_puts(state, " newdirfid=");
+ lib9p_fid_format(&self->newdirfid, state);
+ fmt_state_puts(state, " newname=");
+ lib9p_s_format(&self->newname, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rrenameat_format(struct lib9p_msg_Rrenameat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rrenameat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tunlinkat_format(struct lib9p_msg_Tunlinkat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tunlinkat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " dirfd=");
+ lib9p_fid_format(&self->dirfd, state);
+ fmt_state_puts(state, " name=");
+ lib9p_s_format(&self->name, state);
+ fmt_state_puts(state, " flags=");
+ fmt_state_printf(state, "%"PRIu32, self->flags);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Runlinkat_format(struct lib9p_msg_Runlinkat *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Runlinkat {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+#endif /* CONFIG_9P_ENABLE_9P2000_L */
+#if CONFIG_9P_ENABLE_9P2000_e
+static void lib9p_msg_Tsession_format(struct lib9p_msg_Tsession *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tsession {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " key=");
+ fmt_state_printf(state, "%"PRIu64, self->key);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rsession_format(struct lib9p_msg_Rsession *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rsession {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tsread_format(struct lib9p_msg_Tsread *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tsread {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ fmt_state_printf(state, "%"PRIu32, self->fid);
+ fmt_state_puts(state, " nwname=");
+ fmt_state_printf(state, "%"PRIu16, self->nwname);
+ fmt_state_puts(state, " wname=[");
+ for (uint16_t i = 0; i < self->nwname; i++) {
+ if (i)
+ fmt_state_puts(state, ", ");
+ lib9p_s_format(&self->wname[i], state);
+ }
+ fmt_state_puts(state, " ]");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rsread_format(struct lib9p_msg_Rsread *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rsread {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " data=<bytedata>");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Tswrite_format(struct lib9p_msg_Tswrite *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Tswrite {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " fid=");
+ fmt_state_printf(state, "%"PRIu32, self->fid);
+ fmt_state_puts(state, " nwname=");
+ fmt_state_printf(state, "%"PRIu16, self->nwname);
+ fmt_state_puts(state, " wname=[");
+ for (uint16_t i = 0; i < self->nwname; i++) {
+ if (i)
+ fmt_state_puts(state, ", ");
+ lib9p_s_format(&self->wname[i], state);
+ }
+ fmt_state_puts(state, " ]");
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " data=<bytedata>");
+ fmt_state_puts(state, " }");
+}
+
+static void lib9p_msg_Rswrite_format(struct lib9p_msg_Rswrite *self, struct fmt_state *state) {
+ fmt_state_puts(state, "Rswrite {");
+ fmt_state_puts(state, " tag=");
+ lib9p_tag_format(&self->tag, state);
+ fmt_state_puts(state, " count=");
+ fmt_state_printf(state, "%"PRIu32, self->count);
+ fmt_state_puts(state, " }");
+}
+#endif /* CONFIG_9P_ENABLE_9P2000_e */
+
+/* tables.h *******************************************************************/
+
+const struct _lib9p_ver_tentry _lib9p_table_ver[LIB9P_VER_NUM] = {
+ [LIB9P_VER_unknown] = {.name="unknown", .min_msg_size=9},
+#if CONFIG_9P_ENABLE_9P2000
+ [LIB9P_VER_9P2000] = {.name="9P2000", .min_msg_size=9},
+#endif /* CONFIG_9P_ENABLE_9P2000 */
+#if CONFIG_9P_ENABLE_9P2000_L
+ [LIB9P_VER_9P2000_L] = {.name="9P2000.L", .min_msg_size=9},
+#endif /* CONFIG_9P_ENABLE_9P2000_L */
+#if CONFIG_9P_ENABLE_9P2000_e
+ [LIB9P_VER_9P2000_e] = {.name="9P2000.e", .min_msg_size=9},
+#endif /* CONFIG_9P_ENABLE_9P2000_e */
+#if CONFIG_9P_ENABLE_9P2000_p9p
+ [LIB9P_VER_9P2000_p9p] = {.name="9P2000.p9p", .min_msg_size=9},
+#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
+#if CONFIG_9P_ENABLE_9P2000_u
+ [LIB9P_VER_9P2000_u] = {.name="9P2000.u", .min_msg_size=13},
+#endif /* CONFIG_9P_ENABLE_9P2000_u */
+};
+
+#define _MSG(typ) [LIB9P_TYP_##typ] = { \
+ .name = #typ, \
+ .box_as_fmt_formatter = (_box_as_fmt_formatter_fn_t)lo_box_lib9p_msg_##typ##_as_fmt_formatter, \
+ }
+const struct _lib9p_msg_tentry _lib9p_table_msg[LIB9P_VER_NUM][0x100] = {
+ [LIB9P_VER_unknown] = {
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Rerror),
+ },
#if CONFIG_9P_ENABLE_9P2000
- [LIB9P_VER_9P2000] = 9,
+ [LIB9P_VER_9P2000] = {
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Tauth),
+ _MSG(Rauth),
+ _MSG(Tattach),
+ _MSG(Rattach),
+ _MSG(Rerror),
+ _MSG(Tflush),
+ _MSG(Rflush),
+ _MSG(Twalk),
+ _MSG(Rwalk),
+ _MSG(Topen),
+ _MSG(Ropen),
+ _MSG(Tcreate),
+ _MSG(Rcreate),
+ _MSG(Tread),
+ _MSG(Rread),
+ _MSG(Twrite),
+ _MSG(Rwrite),
+ _MSG(Tclunk),
+ _MSG(Rclunk),
+ _MSG(Tremove),
+ _MSG(Rremove),
+ _MSG(Tstat),
+ _MSG(Rstat),
+ _MSG(Twstat),
+ _MSG(Rwstat),
+ },
#endif /* CONFIG_9P_ENABLE_9P2000 */
#if CONFIG_9P_ENABLE_9P2000_L
- [LIB9P_VER_9P2000_L] = 9,
+ [LIB9P_VER_9P2000_L] = {
+ _MSG(Rlerror),
+ _MSG(Tstatfs),
+ _MSG(Rstatfs),
+ _MSG(Tlopen),
+ _MSG(Rlopen),
+ _MSG(Tlcreate),
+ _MSG(Rlcreate),
+ _MSG(Tsymlink),
+ _MSG(Rsymlink),
+ _MSG(Tmknod),
+ _MSG(Rmknod),
+ _MSG(Trename),
+ _MSG(Rrename),
+ _MSG(Treadlink),
+ _MSG(Rreadlink),
+ _MSG(Tgetattr),
+ _MSG(Rgetattr),
+ _MSG(Tsetattr),
+ _MSG(Rsetattr),
+ _MSG(Txattrwalk),
+ _MSG(Rxattrwalk),
+ _MSG(Txattrcreate),
+ _MSG(Rxattrcreate),
+ _MSG(Treaddir),
+ _MSG(Rreaddir),
+ _MSG(Tfsync),
+ _MSG(Rfsync),
+ _MSG(Tlock),
+ _MSG(Rlock),
+ _MSG(Tgetlock),
+ _MSG(Rgetlock),
+ _MSG(Tlink),
+ _MSG(Rlink),
+ _MSG(Tmkdir),
+ _MSG(Rmkdir),
+ _MSG(Trenameat),
+ _MSG(Rrenameat),
+ _MSG(Tunlinkat),
+ _MSG(Runlinkat),
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Tauth),
+ _MSG(Rauth),
+ _MSG(Tattach),
+ _MSG(Rattach),
+ _MSG(Rerror),
+ _MSG(Tflush),
+ _MSG(Rflush),
+ _MSG(Twalk),
+ _MSG(Rwalk),
+ _MSG(Tread),
+ _MSG(Rread),
+ _MSG(Twrite),
+ _MSG(Rwrite),
+ _MSG(Tclunk),
+ _MSG(Rclunk),
+ _MSG(Tremove),
+ _MSG(Rremove),
+ },
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
- [LIB9P_VER_9P2000_e] = 9,
+ [LIB9P_VER_9P2000_e] = {
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Tauth),
+ _MSG(Rauth),
+ _MSG(Tattach),
+ _MSG(Rattach),
+ _MSG(Rerror),
+ _MSG(Tflush),
+ _MSG(Rflush),
+ _MSG(Twalk),
+ _MSG(Rwalk),
+ _MSG(Topen),
+ _MSG(Ropen),
+ _MSG(Tcreate),
+ _MSG(Rcreate),
+ _MSG(Tread),
+ _MSG(Rread),
+ _MSG(Twrite),
+ _MSG(Rwrite),
+ _MSG(Tclunk),
+ _MSG(Rclunk),
+ _MSG(Tremove),
+ _MSG(Rremove),
+ _MSG(Tstat),
+ _MSG(Rstat),
+ _MSG(Twstat),
+ _MSG(Rwstat),
+ _MSG(Tsession),
+ _MSG(Rsession),
+ _MSG(Tsread),
+ _MSG(Rsread),
+ _MSG(Tswrite),
+ _MSG(Rswrite),
+ },
#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000_p9p
- [LIB9P_VER_9P2000_p9p] = 9,
+ [LIB9P_VER_9P2000_p9p] = {
+ _MSG(Topenfd),
+ _MSG(Ropenfd),
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Tauth),
+ _MSG(Rauth),
+ _MSG(Tattach),
+ _MSG(Rattach),
+ _MSG(Rerror),
+ _MSG(Tflush),
+ _MSG(Rflush),
+ _MSG(Twalk),
+ _MSG(Rwalk),
+ _MSG(Topen),
+ _MSG(Ropen),
+ _MSG(Tcreate),
+ _MSG(Rcreate),
+ _MSG(Tread),
+ _MSG(Rread),
+ _MSG(Twrite),
+ _MSG(Rwrite),
+ _MSG(Tclunk),
+ _MSG(Rclunk),
+ _MSG(Tremove),
+ _MSG(Rremove),
+ _MSG(Tstat),
+ _MSG(Rstat),
+ _MSG(Twstat),
+ _MSG(Rwstat),
+ },
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_u
- [LIB9P_VER_9P2000_u] = 13,
+ [LIB9P_VER_9P2000_u] = {
+ _MSG(Tversion),
+ _MSG(Rversion),
+ _MSG(Tauth),
+ _MSG(Rauth),
+ _MSG(Tattach),
+ _MSG(Rattach),
+ _MSG(Rerror),
+ _MSG(Tflush),
+ _MSG(Rflush),
+ _MSG(Twalk),
+ _MSG(Rwalk),
+ _MSG(Topen),
+ _MSG(Ropen),
+ _MSG(Tcreate),
+ _MSG(Rcreate),
+ _MSG(Tread),
+ _MSG(Rread),
+ _MSG(Twrite),
+ _MSG(Rwrite),
+ _MSG(Tclunk),
+ _MSG(Rclunk),
+ _MSG(Tremove),
+ _MSG(Rremove),
+ _MSG(Tstat),
+ _MSG(Rstat),
+ _MSG(Twstat),
+ _MSG(Rwstat),
+ },
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
-#define _MSG_RECV(typ) [LIB9P_TYP_##typ/2] = { \
- .basesize = sizeof(struct lib9p_msg_##typ), \
- .validate = validate_##typ, \
- .unmarshal = (_unmarshal_fn_t)unmarshal_##typ, \
+#define _MSG_RECV(typ) [LIB9P_TYP_##typ/2] = { \
+ .validate = validate_##typ, \
+ .unmarshal = (_unmarshal_fn_t)unmarshal_##typ, \
}
-#define _MSG_SEND(typ) [LIB9P_TYP_##typ/2] = { \
- .marshal = (_marshal_fn_t)marshal_##typ, \
+#define _MSG_SEND(typ) [LIB9P_TYP_##typ/2] = { \
+ .marshal = (_marshal_fn_t)marshal_##typ, \
}
const struct _lib9p_recv_tentry _lib9p_table_Tmsg_recv[LIB9P_VER_NUM][0x80] = {
@@ -5161,12 +8026,12 @@ const struct _lib9p_send_tentry _lib9p_table_Rmsg_send[LIB9P_VER_NUM][0x80] = {
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
-LM_FLATTEN bool _lib9p_stat_validate(struct _validate_ctx *ctx) {
- return validate_stat(ctx);
+LM_FLATTEN ssize_t _lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes, uint32_t *ret_net_size) {
+ return validate_stat(ctx, net_size, net_bytes, ret_net_size);
}
-LM_FLATTEN void _lib9p_stat_unmarshal(struct _unmarshal_ctx *ctx, struct lib9p_stat *out) {
- unmarshal_stat(ctx, out);
+LM_FLATTEN void _lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out) {
+ unmarshal_stat(ctx, net_bytes, out);
}
-LM_FLATTEN bool _lib9p_stat_marshal(struct _marshal_ctx *ctx, struct lib9p_stat *val) {
- return marshal_stat(ctx, val);
+LM_FLATTEN bool _lib9p_stat_marshal(struct lib9p_ctx *ctx, struct lib9p_stat *val, struct _marshal_ret *ret) {
+ return marshal_stat(ctx, val, ret);
}
diff --git a/lib9p/CMakeLists.txt b/lib9p/CMakeLists.txt
index 707308e..11a58ba 100644
--- a/lib9p/CMakeLists.txt
+++ b/lib9p/CMakeLists.txt
@@ -8,12 +8,14 @@ target_include_directories(lib9p SYSTEM INTERFACE ${CMAKE_CURRENT_SOURCE_DIR}/in
target_sources(lib9p INTERFACE
9p.generated.c
9p.c
+ tables.c
srv.c
)
target_link_libraries(lib9p INTERFACE
libcr_ipc
- libmisc
+ libfmt
libhw_generic
+ libmisc
)
if (ENABLE_TESTS)
diff --git a/lib9p/idl.gen b/lib9p/idl.gen
deleted file mode 100755
index eaeca49..0000000
--- a/lib9p/idl.gen
+++ /dev/null
@@ -1,1439 +0,0 @@
-#!/usr/bin/env python
-# lib9p/idl.gen - Generate C marshalers/unmarshalers for .9p files
-# defining 9P protocol variants.
-#
-# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
-# SPDX-License-Identifier: AGPL-3.0-or-later
-
-import enum
-import graphlib
-import os.path
-import sys
-import typing
-
-sys.path.insert(0, os.path.normpath(os.path.join(__file__, "..")))
-import idl # pylint: disable=wrong-import-position,import-self
-
-# This strives to be "general-purpose" in that it just acts on the
-# *.9p inputs; but (unfortunately?) there are a few special-cases in
-# this script, marked with "SPECIAL".
-
-
-# Utilities ####################################################################
-
-idprefix = "lib9p_"
-
-u32max = (1 << 32) - 1
-u64max = (1 << 64) - 1
-
-
-def tab_ljust(s: str, width: int) -> str:
- cur = len(s.expandtabs(tabsize=8))
- if cur >= width:
- return s
- return s + " " * (width - cur)
-
-
-def add_prefix(p: str, s: str) -> str:
- if s.startswith("_"):
- return "_" + p + s[1:]
- return p + s
-
-
-def c_macro(full: str) -> str:
- full = full.rstrip()
- assert "\n" in full
- lines = [l.rstrip() for l in full.split("\n")]
- width = max(len(l.expandtabs(tabsize=8)) for l in lines[:-1])
- lines = [tab_ljust(l, width) for l in lines]
- return " \\\n".join(lines).rstrip() + "\n"
-
-
-def c_ver_enum(ver: str) -> str:
- return f"{idprefix.upper()}VER_{ver.replace('.', '_')}"
-
-
-def c_ver_ifdef(versions: typing.Collection[str]) -> str:
- return " || ".join(
- f"CONFIG_9P_ENABLE_{v.replace('.', '_')}" for v in sorted(versions)
- )
-
-
-def c_ver_cond(versions: typing.Collection[str]) -> str:
- if len(versions) == 1:
- v = next(v for v in versions)
- return f"is_ver(ctx, {v.replace('.', '_')})"
- return "( " + (" || ".join(c_ver_cond({v}) for v in sorted(versions))) + " )"
-
-
-def c_typename(typ: idl.Type, parent: idl.StructMember | None = None) -> str:
- match typ:
- case idl.Primitive():
- if typ.value == 1 and parent and parent.cnt: # SPECIAL (string)
- return "[[gnu::nonstring]] char"
- return f"uint{typ.value*8}_t"
- case idl.Number():
- return f"{idprefix}{typ.typname}_t"
- case idl.Bitfield():
- return f"{idprefix}{typ.typname}_t"
- case idl.Message():
- return f"struct {idprefix}msg_{typ.typname}"
- case idl.Struct():
- return f"struct {idprefix}{typ.typname}"
- case _:
- raise ValueError(f"not a type: {typ.__class__.__name__}")
-
-
-def c_expr(expr: idl.Expr, lookup_sym: typing.Callable[[str], str]) -> str:
- ret: list[str] = []
- for tok in expr.tokens:
- match tok:
- case idl.ExprOp():
- ret.append(tok.op)
- case idl.ExprLit():
- ret.append(str(tok.val))
- case idl.ExprSym(symname="s32_max"):
- ret.append("INT32_MAX")
- case idl.ExprSym(symname="s64_max"):
- ret.append("INT64_MAX")
- case idl.ExprSym():
- ret.append(lookup_sym(tok.symname))
- case _:
- assert False
- return " ".join(ret)
-
-
-_ifdef_stack: list[str | None] = []
-
-
-def ifdef_push(n: int, _newval: str) -> str:
- # Grow the stack as needed
- while len(_ifdef_stack) < n:
- _ifdef_stack.append(None)
-
- # Set some variables
- parentval: str | None = None
- for x in _ifdef_stack[:-1]:
- if x is not None:
- parentval = x
- oldval = _ifdef_stack[-1]
- newval: str | None = _newval
- if newval == parentval:
- newval = None
-
- # Put newval on the stack.
- _ifdef_stack[-1] = newval
-
- # Build output.
- ret = ""
- if newval != oldval:
- if oldval is not None:
- ret += f"#endif /* {oldval} */\n"
- if newval is not None:
- ret += f"#if {newval}\n"
- return ret
-
-
-def ifdef_pop(n: int) -> str:
- global _ifdef_stack
- ret = ""
- while len(_ifdef_stack) > n:
- if _ifdef_stack[-1] is not None:
- ret += f"#endif /* {_ifdef_stack[-1]} */\n"
- _ifdef_stack = _ifdef_stack[:-1]
- return ret
-
-
-# topo_sorted() ################################################################
-
-
-def topo_sorted(typs: list[idl.UserType]) -> typing.Iterable[idl.UserType]:
- ts: graphlib.TopologicalSorter[idl.UserType] = graphlib.TopologicalSorter()
- for typ in typs:
- match typ:
- case idl.Number():
- ts.add(typ)
- case idl.Bitfield():
- ts.add(typ)
- case idl.Struct(): # and idl.Message():
- deps = [
- member.typ
- for member in typ.members
- if not isinstance(member.typ, idl.Primitive)
- ]
- ts.add(typ, *deps)
- return ts.static_order()
-
-
-# walk() #######################################################################
-
-
-class Path:
- root: idl.Type
- elems: list[idl.StructMember]
-
- def __init__(
- self, root: idl.Type, elems: list[idl.StructMember] | None = None
- ) -> None:
- self.root = root
- self.elems = elems if elems is not None else []
-
- def add(self, elem: idl.StructMember) -> "Path":
- return Path(self.root, self.elems + [elem])
-
- def parent(self) -> "Path":
- return Path(self.root, self.elems[:-1])
-
- def c_str(self, base: str, loopdepth: int = 0) -> str:
- ret = base
- for i, elem in enumerate(self.elems):
- if i > 0:
- ret += "."
- ret += elem.membname
- if elem.cnt:
- ret += f"[{chr(ord('i')+loopdepth)}]"
- loopdepth += 1
- return ret
-
- def __str__(self) -> str:
- return self.c_str(self.root.typname + "->")
-
-
-class WalkCmd(enum.Enum):
- KEEP_GOING = 1
- DONT_RECURSE = 2
- ABORT = 3
-
-
-type WalkHandler = typing.Callable[
- [Path], tuple[WalkCmd, typing.Callable[[], None] | None]
-]
-
-
-def _walk(path: Path, handle: WalkHandler) -> WalkCmd:
- typ = path.elems[-1].typ if path.elems else path.root
-
- ret, atexit = handle(path)
-
- if isinstance(typ, idl.Struct):
- match ret:
- case WalkCmd.KEEP_GOING:
- for member in typ.members:
- if _walk(path.add(member), handle) == WalkCmd.ABORT:
- ret = WalkCmd.ABORT
- break
- case WalkCmd.DONT_RECURSE:
- ret = WalkCmd.KEEP_GOING
- case WalkCmd.ABORT:
- ret = WalkCmd.ABORT
- case _:
- assert False, f"invalid cmd: {ret}"
-
- if atexit:
- atexit()
- return ret
-
-
-def walk(typ: idl.Type, handle: WalkHandler) -> None:
- _walk(Path(typ), handle)
-
-
-# get_buffer_size() ############################################################
-
-
-class BufferSize(typing.NamedTuple):
- min_size: int # really just here to sanity-check against typ.min_size(version)
- exp_size: int # "expected" or max-reasonable size
- max_size: int # really just here to sanity-check against typ.max_size(version)
- max_copy: int
- max_copy_extra: str
- max_iov: int
- max_iov_extra: str
-
-
-class TmpBufferSize:
- min_size: int
- exp_size: int
- max_size: int
- max_copy: int
- max_copy_extra: str
- max_iov: int
- max_iov_extra: str
-
- tmp_starts_with_copy: bool
- tmp_ends_with_copy: bool
-
- def __init__(self) -> None:
- self.min_size = 0
- self.exp_size = 0
- self.max_size = 0
- self.max_copy = 0
- self.max_copy_extra = ""
- self.max_iov = 0
- self.max_iov_extra = ""
- self.tmp_starts_with_copy = False
- self.tmp_ends_with_copy = False
-
-
-def _get_buffer_size(typ: idl.Type, version: str) -> TmpBufferSize:
- assert isinstance(typ, idl.Primitive) or (version in typ.in_versions)
-
- ret = TmpBufferSize()
-
- if not isinstance(typ, idl.Struct):
- assert typ.static_size
- ret.min_size = typ.static_size
- ret.exp_size = typ.static_size
- ret.max_size = typ.static_size
- ret.max_copy = typ.static_size
- ret.max_iov = 1
- ret.tmp_starts_with_copy = True
- ret.tmp_ends_with_copy = True
- return ret
-
- def handle(path: Path) -> tuple[WalkCmd, None]:
- nonlocal ret
- if path.elems:
- child = path.elems[-1]
- if version not in child.in_versions:
- return WalkCmd.DONT_RECURSE, None
- if child.cnt:
- if child.typ.static_size == 1: # SPECIAL (zerocopy)
- ret.max_iov += 1
- # HEURISTIC: 27 for strings (max-strlen from 9P1), 8KiB for other data
- ret.exp_size += 27 if child.membname == "utf8" else 8192
- ret.max_size += child.max_cnt
- ret.tmp_ends_with_copy = False
- return WalkCmd.DONT_RECURSE, None
- sub = _get_buffer_size(child.typ, version)
- ret.exp_size += sub.exp_size * 16 # HEURISTIC: MAXWELEM
- ret.max_size += sub.max_size * child.max_cnt
- if child.membname == "wname" and path.root.typname in (
- "Tsread",
- "Tswrite",
- ): # SPECIAL (9P2000.e)
- assert ret.tmp_ends_with_copy
- assert sub.tmp_starts_with_copy
- assert not sub.tmp_ends_with_copy
- ret.max_copy_extra = (
- f" + (CONFIG_9P_MAX_9P2000_e_WELEM * {sub.max_copy})"
- )
- ret.max_iov_extra = (
- f" + (CONFIG_9P_MAX_9P2000_e_WELEM * {sub.max_iov})"
- )
- ret.max_iov -= 1
- else:
- ret.max_copy += sub.max_copy * child.max_cnt
- if sub.max_iov == 1 and sub.tmp_starts_with_copy: # is purely copy
- ret.max_iov += 1
- else: # contains zero-copy segments
- ret.max_iov += sub.max_iov * child.max_cnt
- if ret.tmp_ends_with_copy and sub.tmp_starts_with_copy:
- # we can merge this one
- ret.max_iov -= 1
- if (
- sub.tmp_ends_with_copy
- and sub.tmp_starts_with_copy
- and sub.max_iov > 1
- ):
- # we can merge these
- ret.max_iov -= child.max_cnt - 1
- ret.tmp_ends_with_copy = sub.tmp_ends_with_copy
- return WalkCmd.DONT_RECURSE, None
- if not isinstance(child.typ, idl.Struct):
- assert child.typ.static_size
- if not ret.tmp_ends_with_copy:
- if ret.max_size == 0:
- ret.tmp_starts_with_copy = True
- ret.max_iov += 1
- ret.tmp_ends_with_copy = True
- ret.min_size += child.typ.static_size
- ret.exp_size += child.typ.static_size
- ret.max_size += child.typ.static_size
- ret.max_copy += child.typ.static_size
- return WalkCmd.KEEP_GOING, None
-
- walk(typ, handle)
- assert ret.min_size == typ.min_size(version)
- assert ret.max_size == typ.max_size(version)
- return ret
-
-
-def get_buffer_size(typ: idl.Type, version: str) -> BufferSize:
- tmp = _get_buffer_size(typ, version)
- return BufferSize(
- min_size=tmp.min_size,
- exp_size=tmp.exp_size,
- max_size=tmp.max_size,
- max_copy=tmp.max_copy,
- max_copy_extra=tmp.max_copy_extra,
- max_iov=tmp.max_iov,
- max_iov_extra=tmp.max_iov_extra,
- )
-
-
-# Generate .h ##################################################################
-
-
-def gen_h(versions: set[str], typs: list[idl.UserType]) -> str:
- global _ifdef_stack
- _ifdef_stack = []
-
- ret = f"""/* Generated by `{' '.join(sys.argv)}`. DO NOT EDIT! */
-
-#ifndef _LIB9P_9P_H_
-\t#error Do not include <lib9p/9p.generated.h> directly; include <lib9p/9p.h> instead
-#endif
-
-#include <stdint.h> /* for uint{{n}}_t types */
-
-#include <libhw/generic/net.h> /* for struct iovec */
-"""
-
- id2typ: dict[int, idl.Message] = {}
- for msg in [msg for msg in typs if isinstance(msg, idl.Message)]:
- id2typ[msg.msgid] = msg
-
- ret += """
-/* config *********************************************************************/
-
-#include "config.h"
-"""
- for ver in sorted(versions):
- ret += "\n"
- ret += f"#ifndef {c_ver_ifdef({ver})}\n"
- ret += f"\t#error config.h must define {c_ver_ifdef({ver})}\n"
- if ver == "9P2000.e": # SPECIAL (9P2000.e)
- ret += "#else\n"
- ret += f"\t#if {c_ver_ifdef({ver})}\n"
- ret += "\t\t#ifndef CONFIG_9P_MAX_9P2000_e_WELEM\n"
- ret += f"\t\t\t#error if {c_ver_ifdef({ver})} then config.h must define CONFIG_9P_MAX_9P2000_e_WELEM\n"
- ret += "\t\t#endif\n"
- ret += "\t\tstatic_assert(CONFIG_9P_MAX_9P2000_e_WELEM > 0);\n"
- ret += "\t#endif\n"
- ret += "#endif\n"
-
- ret += f"""
-/* enum version ***************************************************************/
-
-enum {idprefix}version {{
-"""
- fullversions = ["unknown = 0", *sorted(versions)]
- verwidth = max(len(v) for v in fullversions)
- for ver in fullversions:
- if ver in versions:
- ret += ifdef_push(1, c_ver_ifdef({ver}))
- ret += f"\t{c_ver_enum(ver)},"
- ret += (" " * (verwidth - len(ver))) + ' /* "' + ver.split()[0] + '" */\n'
- ret += ifdef_pop(0)
- ret += f"\t{c_ver_enum('NUM')},\n"
- ret += "};\n"
-
- ret += """
-/* enum msg_type **************************************************************/
-
-"""
- ret += f"enum {idprefix}msg_type {{ /* uint8_t */\n"
- namewidth = max(len(msg.typname) for msg in typs if isinstance(msg, idl.Message))
- for n in range(0x100):
- if n not in id2typ:
- continue
- msg = id2typ[n]
- ret += ifdef_push(1, c_ver_ifdef(msg.in_versions))
- ret += f"\t{idprefix.upper()}TYP_{msg.typname:<{namewidth}} = {msg.msgid},\n"
- ret += ifdef_pop(0)
- ret += "};\n"
-
- ret += """
-/* payload types **************************************************************/
-"""
-
- def per_version_comment(
- typ: idl.UserType, fn: typing.Callable[[idl.UserType, str], str]
- ) -> str:
- lines: dict[str, str] = {}
- for version in sorted(typ.in_versions):
- lines[version] = fn(typ, version)
- if len(set(lines.values())) == 1:
- for _, line in lines.items():
- return f"/* {line} */\n"
- assert False
- else:
- ret = ""
- v_width = max(len(c_ver_enum(v)) for v in typ.in_versions)
- for version, line in lines.items():
- ret += f"/* {c_ver_enum(version):<{v_width}}: {line} */\n"
- return ret
-
- for typ in topo_sorted(typs):
- ret += "\n"
- ret += ifdef_push(1, c_ver_ifdef(typ.in_versions))
-
- def sum_size(typ: idl.UserType, version: str) -> str:
- sz = get_buffer_size(typ, version)
- assert (
- sz.min_size <= sz.exp_size
- and sz.exp_size <= sz.max_size
- and sz.max_size < u64max
- )
- ret = ""
- if sz.min_size == sz.max_size:
- ret += f"size = {sz.min_size:,}"
- else:
- ret += f"min_size = {sz.min_size:,} ; exp_size = {sz.exp_size:,} ; max_size = {sz.max_size:,}"
- if sz.max_size > u32max:
- ret += " (warning: >UINT32_MAX)"
- ret += f" ; max_iov = {sz.max_iov:,}{sz.max_iov_extra} ; max_copy = {sz.max_copy:,}{sz.max_copy_extra}"
- return ret
-
- ret += per_version_comment(typ, sum_size)
-
- match typ:
- case idl.Number():
- ret += f"typedef {c_typename(typ.prim)} {c_typename(typ)};\n"
- prefix = f"{idprefix.upper()}{typ.typname.upper()}_"
- namewidth = max(len(name) for name in typ.vals)
- for name, val in typ.vals.items():
- ret += f"#define {prefix}{name:<{namewidth}} (({c_typename(typ)})UINT{typ.static_size*8}_C({val}))\n"
- case idl.Bitfield():
- ret += f"typedef {c_typename(typ.prim)} {c_typename(typ)};\n"
-
- def bitname(val: idl.Bit | idl.BitAlias) -> str:
- s = val.bitname
- match val:
- case idl.Bit(cat=idl.BitCat.RESERVED):
- s = "_RESERVED_" + s
- case idl.Bit(cat=idl.BitCat.SUBFIELD):
- assert isinstance(typ, idl.Bitfield)
- n = sum(
- 1
- for b in typ.bits[: val.num]
- if b.cat == idl.BitCat.SUBFIELD
- and b.bitname == val.bitname
- )
- s = f"_{s}_{n}"
- case idl.Bit(cat=idl.BitCat.UNUSED):
- return ""
- return add_prefix(f"{idprefix.upper()}{typ.typname.upper()}_", s)
-
- namewidth = max(
- len(bitname(val)) for val in [*typ.bits, *typ.names.values()]
- )
-
- ret += "\n"
- for bit in reversed(typ.bits):
- vers = bit.in_versions
- if bit.cat == idl.BitCat.UNUSED:
- vers = typ.in_versions
- ret += ifdef_push(2, c_ver_ifdef(vers))
-
- # It is important all of the `beg` strings have
- # the same length.
- end = ""
- match bit.cat:
- case (
- idl.BitCat.USED | idl.BitCat.RESERVED | idl.BitCat.SUBFIELD
- ):
- if _ifdef_stack[-1]:
- beg = "# define"
- else:
- beg = "#define "
- case idl.BitCat.UNUSED:
- beg = "/* unused"
- end = " */"
-
- c_name = bitname(bit)
- c_val = f"1<<{bit.num}"
- ret += f"{beg} {c_name:<{namewidth}} (({c_typename(typ)})({c_val})){end}\n"
- if aliases := [
- alias
- for alias in typ.names.values()
- if isinstance(alias, idl.BitAlias)
- ]:
- ret += "\n"
-
- for alias in aliases:
- ret += ifdef_push(2, c_ver_ifdef(alias.in_versions))
-
- end = ""
- if _ifdef_stack[-1]:
- beg = "# define"
- else:
- beg = "#define "
-
- c_name = bitname(alias)
- c_val = alias.val
- ret += f"{beg} {c_name:<{namewidth}} (({c_typename(typ)})({c_val})){end}\n"
- ret += ifdef_pop(1)
- del bitname
- case idl.Struct(): # and idl.Message():
- ret += c_typename(typ) + " {"
- if not typ.members:
- ret += "};\n"
- continue
- ret += "\n"
-
- typewidth = max(len(c_typename(m.typ, m)) for m in typ.members)
-
- for member in typ.members:
- if member.val:
- continue
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- ret += f"\t{c_typename(member.typ, member):<{typewidth}} {'*' if member.cnt else ' '}{member.membname};\n"
- ret += ifdef_pop(1)
- ret += "};\n"
- del typ
- ret += ifdef_pop(0)
-
- ret += """
-/* containers *****************************************************************/
-"""
- ret += "\n"
- ret += f"#define _{idprefix.upper()}MAX(a, b) ((a) > (b)) ? (a) : (b)\n"
-
- tmsg_max_iov: dict[str, int] = {}
- tmsg_max_copy: dict[str, int] = {}
- rmsg_max_iov: dict[str, int] = {}
- rmsg_max_copy: dict[str, int] = {}
- for typ in typs:
- if not isinstance(typ, idl.Message):
- continue
- if typ.typname in ("Tsread", "Tswrite"): # SPECIAL (9P2000.e)
- continue
- max_iov = tmsg_max_iov if typ.msgid % 2 == 0 else rmsg_max_iov
- max_copy = tmsg_max_copy if typ.msgid % 2 == 0 else rmsg_max_copy
- for version in typ.in_versions:
- if version not in max_iov:
- max_iov[version] = 0
- max_copy[version] = 0
- sz = get_buffer_size(typ, version)
- if sz.max_iov > max_iov[version]:
- max_iov[version] = sz.max_iov
- if sz.max_copy > max_copy[version]:
- max_copy[version] = sz.max_copy
-
- for name, table in [
- ("tmsg_max_iov", tmsg_max_iov),
- ("tmsg_max_copy", tmsg_max_copy),
- ("rmsg_max_iov", rmsg_max_iov),
- ("rmsg_max_copy", rmsg_max_copy),
- ]:
- inv: dict[int, set[str]] = {}
- for version, maxval in table.items():
- if maxval not in inv:
- inv[maxval] = set()
- inv[maxval].add(version)
-
- ret += "\n"
- directive = "if"
- seen_e = False # SPECIAL (9P2000.e)
- for maxval in sorted(inv, reverse=True):
- ret += f"#{directive} {c_ver_ifdef(inv[maxval])}\n"
- indent = 1
- if name.startswith("tmsg") and not seen_e: # SPECIAL (9P2000.e)
- typ = next(typ for typ in typs if typ.typname == "Tswrite")
- sz = get_buffer_size(typ, "9P2000.e")
- match name:
- case "tmsg_max_iov":
- maxexpr = f"{sz.max_iov}{sz.max_iov_extra}"
- case "tmsg_max_copy":
- maxexpr = f"{sz.max_copy}{sz.max_copy_extra}"
- case _:
- assert False
- ret += f"\t#if {c_ver_ifdef({"9P2000.e"})}\n"
- ret += f"\t\t#define {idprefix.upper()}{name.upper()} _{idprefix.upper()}MAX({maxval}, {maxexpr})\n"
- ret += "\t#else\n"
- indent += 1
- ret += f"{'\t'*indent}#define {idprefix.upper()}{name.upper()} {maxval}\n"
- if name.startswith("tmsg") and not seen_e: # SPECIAL (9P2000.e)
- ret += "\t#endif\n"
- if "9P2000.e" in inv[maxval]:
- seen_e = True
- directive = "elif"
- ret += "#endif\n"
-
- ret += "\n"
- ret += f"struct {idprefix}Tmsg_send_buf {{\n"
- ret += "\tsize_t iov_cnt;\n"
- ret += f"\tstruct iovec iov[{idprefix.upper()}TMSG_MAX_IOV];\n"
- ret += f"\tuint8_t copied[{idprefix.upper()}TMSG_MAX_COPY];\n"
- ret += "};\n"
-
- ret += "\n"
- ret += f"struct {idprefix}Rmsg_send_buf {{\n"
- ret += "\tsize_t iov_cnt;\n"
- ret += f"\tstruct iovec iov[{idprefix.upper()}RMSG_MAX_IOV];\n"
- ret += f"\tuint8_t copied[{idprefix.upper()}RMSG_MAX_COPY];\n"
- ret += "};\n"
-
- return ret
-
-
-# Generate .c ##################################################################
-
-
-def gen_c(versions: set[str], typs: list[idl.UserType]) -> str:
- global _ifdef_stack
- _ifdef_stack = []
-
- ret = f"""/* Generated by `{' '.join(sys.argv)}`. DO NOT EDIT! */
-
-#include <stdbool.h>
-#include <stddef.h> /* for size_t */
-#include <inttypes.h> /* for PRI* macros */
-#include <string.h> /* for memset() */
-
-#include <libmisc/assert.h>
-
-#include <lib9p/9p.h>
-
-#include "internal.h"
-"""
-
- # utilities ################################################################
- ret += """
-/* utilities ******************************************************************/
-"""
-
- def used(arg: str) -> str:
- return arg
-
- def unused(arg: str) -> str:
- return f"LM_UNUSED({arg})"
-
- id2typ: dict[int, idl.Message] = {}
- for msg in [msg for msg in typs if isinstance(msg, idl.Message)]:
- id2typ[msg.msgid] = msg
-
- def msg_table(grp: str, meth: str, tentry: str, rng: tuple[int, int, int]) -> str:
- ret = f"const {tentry} _{idprefix}table_{grp}_{meth}[{c_ver_enum('NUM')}][{hex(len(range(*rng)))}] = {{\n"
- for ver in ["unknown", *sorted(versions)]:
- if ver != "unknown":
- ret += ifdef_push(1, c_ver_ifdef({ver}))
- ret += f"\t[{c_ver_enum(ver)}] = {{\n"
- for n in range(*rng):
- xmsg: idl.Message | None = id2typ.get(n, None)
- if xmsg:
- if ver == "unknown": # SPECIAL (initialization)
- if xmsg.typname not in ["Tversion", "Rversion", "Rerror"]:
- xmsg = None
- else:
- if ver not in xmsg.in_versions:
- xmsg = None
- if xmsg:
- ret += f"\t\t_MSG_{meth.upper()}({xmsg.typname}),\n"
- ret += "\t},\n"
- ret += ifdef_pop(0)
- ret += "};\n"
- return ret
-
- for v in sorted(versions):
- ret += f"#if CONFIG_9P_ENABLE_{v.replace('.', '_')}\n"
- ret += f"\t#define _is_ver_{v.replace('.', '_')}(v) (v == {c_ver_enum(v)})\n"
- ret += "#else\n"
- ret += f"\t#define _is_ver_{v.replace('.', '_')}(v) false\n"
- ret += "#endif\n"
- ret += "\n"
- ret += "/**\n"
- ret += f" * is_ver(ctx, ver) is essentially `(ctx->ctx->version == {idprefix.upper()}VER_##ver)`,\n"
- ret += f" * but compiles correctly (to `false`) even if `{idprefix.upper()}VER_##ver` isn't defined\n"
- ret += " * (because `!CONFIG_9P_ENABLE_##ver`). This is useful when `||`ing\n"
- ret += " * several version checks together.\n"
- ret += " */\n"
- ret += "#define is_ver(CTX, ver) _is_ver_##ver(CTX->ctx->version)\n"
-
- # strings ##################################################################
- ret += f"""
-/* strings ********************************************************************/
-
-const char *const _{idprefix}table_ver_name[{c_ver_enum('NUM')}] = {{
-"""
- for ver in ["unknown", *sorted(versions)]:
- if ver in versions:
- ret += ifdef_push(1, c_ver_ifdef({ver}))
- ret += f'\t[{c_ver_enum(ver)}] = "{ver}",\n'
- ret += ifdef_pop(0)
- ret += "};\n"
-
- ret += "\n"
- ret += f"#define _MSG_NAME(typ) [{idprefix.upper()}TYP_##typ] = #typ\n"
- ret += msg_table("msg", "name", "char *const", (0, 0x100, 1))
-
- # bitmasks #################################################################
- ret += """
-/* bitmasks *******************************************************************/
-"""
- for typ in typs:
- if not isinstance(typ, idl.Bitfield):
- continue
- ret += "\n"
- ret += ifdef_push(1, c_ver_ifdef(typ.in_versions))
- ret += f"static const {c_typename(typ)} {typ.typname}_masks[{c_ver_enum('NUM')}] = {{\n"
- verwidth = max(len(ver) for ver in versions)
- for ver in sorted(versions):
- ret += ifdef_push(2, c_ver_ifdef({ver}))
- ret += (
- f"\t[{c_ver_enum(ver)}]{' '*(verwidth-len(ver))} = 0b"
- + "".join(
- (
- "1"
- if bit.cat in (idl.BitCat.USED, idl.BitCat.SUBFIELD)
- and ver in bit.in_versions
- else "0"
- )
- for bit in reversed(typ.bits)
- )
- + ",\n"
- )
- ret += ifdef_pop(1)
- ret += "};\n"
- ret += ifdef_pop(0)
-
- # validate_* ###############################################################
- ret += """
-/* validate_* *****************************************************************/
-
-LM_ALWAYS_INLINE static bool _validate_size_net(struct _validate_ctx *ctx, uint32_t n) {
-\tif (__builtin_add_overflow(ctx->net_offset, n, &ctx->net_offset))
-\t\t/* If needed-net-size overflowed uint32_t, then
-\t\t * there's no way that actual-net-size will live up to
-\t\t * that. */
-\t\treturn lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
-\tif (ctx->net_offset > ctx->net_size)
-\t\treturn lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
-\treturn false;
-}
-
-LM_ALWAYS_INLINE static bool _validate_size_host(struct _validate_ctx *ctx, size_t n) {
-\tif (__builtin_add_overflow(ctx->host_extra, n, &ctx->host_extra))
-\t\t/* If needed-host-size overflowed size_t, then there's
-\t\t * no way that actual-net-size will live up to
-\t\t * that. */
-\t\treturn lib9p_error(ctx->ctx, LINUX_EBADMSG, "message is too short for content");
-\treturn false;
-}
-
-LM_ALWAYS_INLINE static bool _validate_list(struct _validate_ctx *ctx,
- size_t cnt,
- _validate_fn_t item_fn, size_t item_host_size) {
-\tfor (size_t i = 0; i < cnt; i++)
-\t\tif (_validate_size_host(ctx, item_host_size) || item_fn(ctx))
-\t\t\treturn true;
-\treturn false;
-}
-
-LM_ALWAYS_INLINE static bool validate_1(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 1); }
-LM_ALWAYS_INLINE static bool validate_2(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 2); }
-LM_ALWAYS_INLINE static bool validate_4(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 4); }
-LM_ALWAYS_INLINE static bool validate_8(struct _validate_ctx *ctx) { return _validate_size_net(ctx, 8); }
-"""
-
- def should_save_value(typ: idl.Struct, member: idl.StructMember) -> bool:
- return bool(
- member.max or member.val or any(m.cnt == member for m in typ.members)
- )
-
- for typ in topo_sorted(typs):
- inline = "LM_FLATTEN" if isinstance(typ, idl.Message) else "LM_ALWAYS_INLINE"
- argfn = unused if (isinstance(typ, idl.Struct) and not typ.members) else used
- ret += "\n"
- ret += ifdef_push(1, c_ver_ifdef(typ.in_versions))
- ret += f"{inline} static bool validate_{typ.typname}(struct _validate_ctx *{argfn('ctx')}) {{\n"
-
- match typ:
- case idl.Number():
- ret += f"\treturn validate_{typ.prim.typname}(ctx);\n"
- case idl.Bitfield():
- ret += f"\t if (validate_{typ.static_size}(ctx))\n"
- ret += "\t\treturn true;\n"
- ret += f"\t{c_typename(typ)} mask = {typ.typname}_masks[ctx->ctx->version];\n"
- if typ.static_size == 1:
- ret += f"\t{c_typename(typ)} val = ctx->net_bytes[ctx->net_offset-1];\n"
- else:
- ret += f"\t{c_typename(typ)} val = uint{typ.static_size*8}le_decode(&ctx->net_bytes[ctx->net_offset-{typ.static_size}]);\n"
- ret += "\tif (val & ~mask)\n"
- ret += f'\t\treturn lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "unknown bits in {typ.typname} bitfield: %#0{typ.static_size}"PRIx{typ.static_size*8}, val & ~mask);\n'
- ret += "\treturn false;\n"
- case idl.Struct(): # and idl.Message()
- if len(typ.members) == 0:
- ret += "\treturn false;\n"
- ret += "}\n"
- continue
-
- # Pass 1 - declare value variables
- for member in typ.members:
- if should_save_value(typ, member):
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- ret += f"\t{c_typename(member.typ)} {member.membname};\n"
- ret += ifdef_pop(1)
-
- # Pass 2 - declare offset variables
- mark_offset: set[str] = set()
- for member in typ.members:
- for tok in [*member.max.tokens, *member.val.tokens]:
- if isinstance(tok, idl.ExprSym) and tok.symname.startswith("&"):
- if tok.symname[1:] not in mark_offset:
- ret += f"\tuint32_t _{tok.symname[1:]}_offset;\n"
- mark_offset.add(tok.symname[1:])
-
- # Pass 3 - main pass
- ret += "\treturn false\n"
- for member in typ.members:
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- ret += "\t || "
- if member.in_versions != typ.in_versions:
- ret += "( " + c_ver_cond(member.in_versions) + " && "
- if member.cnt is not None:
- if member.typ.static_size == 1: # SPECIAL (zerocopy)
- ret += f"_validate_size_net(ctx, {member.cnt.membname})"
- else:
- ret += f"_validate_list(ctx, {member.cnt.membname}, validate_{member.typ.typname}, sizeof({c_typename(member.typ)}))"
- if typ.typname == "s": # SPECIAL (string)
- ret += '\n\t || ({ (!is_valid_utf8_without_nul(&ctx->net_bytes[ctx->net_offset-len], len)) && lib9p_error(ctx->ctx, LINUX_EBADMSG, "message contains invalid UTF-8"); })'
- else:
- if should_save_value(typ, member):
- ret += "("
- if member.membname in mark_offset:
- ret += f"({{ _{member.membname}_offset = ctx->net_offset; "
- ret += f"validate_{member.typ.typname}(ctx)"
- if member.membname in mark_offset:
- ret += "; })"
- if should_save_value(typ, member):
- nbytes = member.static_size
- assert nbytes
- if nbytes == 1:
- ret += f" || ({{ {member.membname} = ctx->net_bytes[ctx->net_offset-1]; false; }}))"
- else:
- ret += f" || ({{ {member.membname} = uint{nbytes*8}le_decode(&ctx->net_bytes[ctx->net_offset-{nbytes}]); false; }}))"
- if member.in_versions != typ.in_versions:
- ret += " )"
- ret += "\n"
-
- # Pass 4 - validate ,max= and ,val= constraints
- for member in typ.members:
-
- def lookup_sym(sym: str) -> str:
- match sym:
- case "end":
- return "ctx->net_offset"
- case _:
- assert sym.startswith("&")
- return f"_{sym[1:]}_offset"
-
- if member.max:
- assert member.static_size
- nbits = member.static_size * 8
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- ret += f"\t || ({{ uint{nbits}_t max = {c_expr(member.max, lookup_sym)}; (((uint{nbits}_t){member.membname}) > max) &&\n"
- ret += f'\t lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "{member.membname} value is too large (%"PRIu{nbits}" > %"PRIu{nbits}")", {member.membname}, max); }})\n'
- if member.val:
- assert member.static_size
- nbits = member.static_size * 8
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- ret += f"\t || ({{ uint{nbits}_t exp = {c_expr(member.val, lookup_sym)}; (((uint{nbits}_t){member.membname}) != exp) &&\n"
- ret += f'\t lib9p_errorf(ctx->ctx, LINUX_EBADMSG, "{member.membname} value is wrong (actual:%"PRIu{nbits}" != correct:%"PRIu{nbits}")", (uint{nbits}_t){member.membname}, exp); }})\n'
-
- ret += ifdef_pop(1)
- ret += "\t ;\n"
- ret += "}\n"
- ret += ifdef_pop(0)
-
- # unmarshal_* ##############################################################
- ret += """
-/* unmarshal_* ****************************************************************/
-
-LM_ALWAYS_INLINE static void unmarshal_1(struct _unmarshal_ctx *ctx, uint8_t *out) {
-\t*out = ctx->net_bytes[ctx->net_offset];
-\tctx->net_offset += 1;
-}
-
-LM_ALWAYS_INLINE static void unmarshal_2(struct _unmarshal_ctx *ctx, uint16_t *out) {
-\t*out = uint16le_decode(&ctx->net_bytes[ctx->net_offset]);
-\tctx->net_offset += 2;
-}
-
-LM_ALWAYS_INLINE static void unmarshal_4(struct _unmarshal_ctx *ctx, uint32_t *out) {
-\t*out = uint32le_decode(&ctx->net_bytes[ctx->net_offset]);
-\tctx->net_offset += 4;
-}
-
-LM_ALWAYS_INLINE static void unmarshal_8(struct _unmarshal_ctx *ctx, uint64_t *out) {
-\t*out = uint64le_decode(&ctx->net_bytes[ctx->net_offset]);
-\tctx->net_offset += 8;
-}
-"""
- for typ in topo_sorted(typs):
- inline = "LM_FLATTEN" if isinstance(typ, idl.Message) else "LM_ALWAYS_INLINE"
- argfn = unused if (isinstance(typ, idl.Struct) and not typ.members) else used
- ret += "\n"
- ret += ifdef_push(1, c_ver_ifdef(typ.in_versions))
- ret += f"{inline} static void unmarshal_{typ.typname}(struct _unmarshal_ctx *{argfn('ctx')}, {c_typename(typ)} *out) {{\n"
- match typ:
- case idl.Number():
- ret += f"\tunmarshal_{typ.prim.typname}(ctx, ({c_typename(typ.prim)} *)out);\n"
- case idl.Bitfield():
- ret += f"\tunmarshal_{typ.prim.typname}(ctx, ({c_typename(typ.prim)} *)out);\n"
- case idl.Struct():
- ret += "\tmemset(out, 0, sizeof(*out));\n"
-
- for member in typ.members:
- ret += ifdef_push(2, c_ver_ifdef(member.in_versions))
- if member.val:
- ret += f"\tctx->net_offset += {member.static_size};\n"
- continue
- ret += "\t"
-
- prefix = "\t"
- if member.in_versions != typ.in_versions:
- ret += "if ( " + c_ver_cond(member.in_versions) + " ) "
- prefix = "\t\t"
- if member.cnt:
- if member.in_versions != typ.in_versions:
- ret += "{\n"
- ret += prefix
- if member.typ.static_size == 1: # SPECIAL (string, zerocopy)
- ret += f"out->{member.membname} = (char *)&ctx->net_bytes[ctx->net_offset];\n"
- ret += f"{prefix}ctx->net_offset += out->{member.cnt.membname};\n"
- else:
- ret += f"out->{member.membname} = ctx->extra;\n"
- ret += f"{prefix}ctx->extra += sizeof(out->{member.membname}[0]) * out->{member.cnt.membname};\n"
- ret += f"{prefix}for (typeof(out->{member.cnt.membname}) i = 0; i < out->{member.cnt.membname}; i++)\n"
- ret += f"{prefix}\tunmarshal_{member.typ.typname}(ctx, &out->{member.membname}[i]);\n"
- if member.in_versions != typ.in_versions:
- ret += "\t}\n"
- else:
- ret += f"unmarshal_{member.typ.typname}(ctx, &out->{member.membname});\n"
- ret += ifdef_pop(1)
- ret += "}\n"
- ret += ifdef_pop(0)
-
- # marshal_* ################################################################
- ret += """
-/* marshal_* ******************************************************************/
-
-"""
- ret += c_macro(
- "#define MARSHAL_BYTES_ZEROCOPY(ctx, data, len)\n"
- "\tif (ctx->net_iov[ctx->net_iov_cnt-1].iov_len)\n"
- "\t\tctx->net_iov_cnt++;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = data;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len = len;\n"
- "\tctx->net_iov_cnt++;\n"
- )
- ret += c_macro(
- "#define MARSHAL_BYTES(ctx, data, len)\n"
- "\tif (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base)\n"
- "\t\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size];\n"
- "\tmemcpy(&ctx->net_copied[ctx->net_copied_size], data, len);\n"
- "\tctx->net_copied_size += len;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len += len;\n"
- )
- ret += c_macro(
- "#define MARSHAL_U8LE(ctx, val)\n"
- "\tif (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base)\n"
- "\t\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size];\n"
- "\tctx->net_copied[ctx->net_copied_size] = val;\n"
- "\tctx->net_copied_size += 1;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len += 1;\n"
- )
- ret += c_macro(
- "#define MARSHAL_U16LE(ctx, val)\n"
- "\tif (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base)\n"
- "\t\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size];\n"
- "\tuint16le_encode(&ctx->net_copied[ctx->net_copied_size], val);\n"
- "\tctx->net_copied_size += 2;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len += 2;\n"
- )
- ret += c_macro(
- "#define MARSHAL_U32LE(ctx, val)\n"
- "\tif (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base)\n"
- "\t\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size];\n"
- "\tuint32le_encode(&ctx->net_copied[ctx->net_copied_size], val);\n"
- "\tctx->net_copied_size += 4;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len += 4;\n"
- )
- ret += c_macro(
- "#define MARSHAL_U64LE(ctx, val)\n"
- "\tif (!ctx->net_iov[ctx->net_iov_cnt-1].iov_base)\n"
- "\t\tctx->net_iov[ctx->net_iov_cnt-1].iov_base = &ctx->net_copied[ctx->net_copied_size];\n"
- "\tuint64le_encode(&ctx->net_copied[ctx->net_copied_size], val);\n"
- "\tctx->net_copied_size += 8;\n"
- "\tctx->net_iov[ctx->net_iov_cnt-1].iov_len += 8;\n"
- )
-
- class OffsetExpr:
- static: int
- cond: dict[frozenset[str], "OffsetExpr"]
- rep: list[tuple[Path, "OffsetExpr"]]
-
- def __init__(self) -> None:
- self.static = 0
- self.rep = []
- self.cond = {}
-
- def add(self, other: "OffsetExpr") -> None:
- self.static += other.static
- self.rep += other.rep
- for k, v in other.cond.items():
- if k in self.cond:
- self.cond[k].add(v)
- else:
- self.cond[k] = v
-
- def gen_c(
- self,
- dsttyp: str,
- dstvar: str,
- root: str,
- indent_depth: int,
- loop_depth: int,
- ) -> str:
- oneline: list[str] = []
- multiline = ""
- if self.static:
- oneline.append(str(self.static))
- for cnt, sub in self.rep:
- if not sub.cond and not sub.rep:
- if sub.static == 1:
- oneline.append(cnt.c_str(root))
- else:
- oneline.append(f"({cnt.c_str(root)})*{sub.static}")
- continue
- loopvar = chr(ord("i") + loop_depth)
- multiline += f"{'\t'*indent_depth}for ({c_typename(cnt.elems[-1].typ)} {loopvar} = 0; {loopvar} < {cnt.c_str(root)}; {loopvar}++) {{\n"
- multiline += sub.gen_c(
- "", dstvar, root, indent_depth + 1, loop_depth + 1
- )
- multiline += f"{'\t'*indent_depth}}}\n"
- for vers, sub in self.cond.items():
- multiline += ifdef_push(indent_depth + 1, c_ver_ifdef(vers))
- multiline += f"{'\t'*indent_depth}if {c_ver_cond(vers)} {{\n"
- multiline += sub.gen_c("", dstvar, root, indent_depth + 1, loop_depth)
- multiline += f"{'\t'*indent_depth}}}\n"
- multiline += ifdef_pop(indent_depth)
- if dsttyp:
- if not oneline:
- oneline.append("0")
- ret = f"{'\t'*indent_depth}{dsttyp} {dstvar} = {' + '.join(oneline)};\n"
- elif oneline:
- ret = f"{'\t'*indent_depth}{dstvar} += {' + '.join(oneline)};\n"
- ret += multiline
- return ret
-
- type OffsetExprRecursion = typing.Callable[[Path], WalkCmd]
-
- def get_offset_expr(typ: idl.UserType, recurse: OffsetExprRecursion) -> OffsetExpr:
- if not isinstance(typ, idl.Struct):
- assert typ.static_size
- ret = OffsetExpr()
- ret.static = typ.static_size
- return ret
-
- stack: list[tuple[Path, OffsetExpr, typing.Callable[[], None]]]
-
- def pop_root() -> None:
- assert False
-
- def pop_cond() -> None:
- nonlocal stack
- key = frozenset(stack[-1][0].elems[-1].in_versions)
- if key in stack[-2][1].cond:
- stack[-2][1].cond[key].add(stack[-1][1])
- else:
- stack[-2][1].cond[key] = stack[-1][1]
- stack = stack[:-1]
-
- def pop_rep() -> None:
- nonlocal stack
- member_path = stack[-1][0]
- member = member_path.elems[-1]
- assert member.cnt
- cnt_path = member_path.parent().add(member.cnt)
- stack[-2][1].rep.append((cnt_path, stack[-1][1]))
- stack = stack[:-1]
-
- def handle(path: Path) -> tuple[WalkCmd, typing.Callable[[], None] | None]:
- nonlocal recurse
-
- ret = recurse(path)
- if ret != WalkCmd.KEEP_GOING:
- return ret, None
-
- nonlocal stack
- stack_len = len(stack)
-
- def pop() -> None:
- nonlocal stack
- nonlocal stack_len
- while len(stack) > stack_len:
- stack[-1][2]()
-
- if path.elems:
- child = path.elems[-1]
- parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
- if child.in_versions < parent.in_versions:
- stack.append((path, OffsetExpr(), pop_cond))
- if child.cnt:
- stack.append((path, OffsetExpr(), pop_rep))
- if not isinstance(child.typ, idl.Struct):
- assert child.typ.static_size
- stack[-1][1].static += child.typ.static_size
- return ret, pop
-
- stack = [(Path(typ), OffsetExpr(), pop_root)]
- walk(typ, handle)
- return stack[0][1]
-
- def go_to_end(path: Path) -> WalkCmd:
- return WalkCmd.KEEP_GOING
-
- def go_to_tok(name: str) -> typing.Callable[[Path], WalkCmd]:
- def ret(path: Path) -> WalkCmd:
- if len(path.elems) == 1 and path.elems[0].membname == name:
- return WalkCmd.ABORT
- return WalkCmd.KEEP_GOING
-
- return ret
-
- for typ in typs:
- if not (
- isinstance(typ, idl.Message) or typ.typname == "stat"
- ): # SPECIAL (include stat)
- continue
- assert isinstance(typ, idl.Struct)
- ret += "\n"
- ret += ifdef_push(1, c_ver_ifdef(typ.in_versions))
- ret += f"static bool marshal_{typ.typname}(struct _marshal_ctx *ctx, {c_typename(typ)} *val) {{\n"
-
- # Pass 1 - check size
- max_size = max(typ.max_size(v) for v in typ.in_versions)
-
- if max_size > u32max: # SPECIAL (9P2000.e)
- ret += get_offset_expr(typ, go_to_end).gen_c(
- "uint64_t", "needed_size", "val->", 1, 0
- )
- ret += "\tif (needed_size > (uint64_t)(ctx->ctx->max_msg_size)) {\n"
- else:
- ret += get_offset_expr(typ, go_to_end).gen_c(
- "uint32_t", "needed_size", "val->", 1, 0
- )
- ret += "\tif (needed_size > ctx->ctx->max_msg_size) {\n"
- if isinstance(typ, idl.Message): # SPECIAL (disable for stat)
- ret += '\t\tlib9p_errorf(ctx->ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",\n'
- ret += f'\t\t\t"{typ.typname}",\n'
- ret += f'\t\t\tctx->ctx->version ? "negotiated" : "{'client' if typ.msgid % 2 == 0 else 'server'}",\n'
- ret += "\t\t\tctx->ctx->max_msg_size);\n"
- ret += "\t\treturn true;\n"
- ret += "\t}\n"
-
- # Pass 2 - write data
- ifdef_depth = 1
- stack: list[tuple[Path, bool]] = [(Path(typ), False)]
-
- def handle(path: Path) -> tuple[WalkCmd, typing.Callable[[], None]]:
- nonlocal ret
- nonlocal ifdef_depth
- nonlocal stack
- stack_len = len(stack)
-
- def pop() -> None:
- nonlocal ret
- nonlocal ifdef_depth
- nonlocal stack
- nonlocal stack_len
- while len(stack) > stack_len:
- ret += f"{'\t'*(len(stack)-1)}}}\n"
- if stack[-1][1]:
- ifdef_depth -= 1
- ret += ifdef_pop(ifdef_depth)
- stack = stack[:-1]
-
- loopdepth = sum(1 for elem in path.elems if elem.cnt)
- struct = path.elems[-1].typ if path.elems else path.root
- if isinstance(struct, idl.Struct):
- offsets: list[str] = []
- for member in struct.members:
- if not member.val:
- continue
- for tok in member.val.tokens:
- if not isinstance(tok, idl.ExprSym):
- continue
- if tok.symname == "end" or tok.symname.startswith("&"):
- if tok.symname not in offsets:
- offsets.append(tok.symname)
- for name in offsets:
- name_prefix = "offsetof_" + "".join(
- m.membname + "_" for m in path.elems
- )
- if name == "end":
- if not path.elems:
- nonlocal max_size
- if max_size > u32max:
- ret += f"{'\t'*len(stack)}uint32_t {name_prefix}end = (uint32_t)needed_size;\n"
- else:
- ret += f"{'\t'*len(stack)}uint32_t {name_prefix}end = needed_size;\n"
- continue
- recurse: OffsetExprRecursion = go_to_end
- else:
- assert name.startswith("&")
- name = name[1:]
- recurse = go_to_tok(name)
- expr = get_offset_expr(struct, recurse)
- expr_prefix = path.c_str("val->", loopdepth)
- if not expr_prefix.endswith(">"):
- expr_prefix += "."
- ret += expr.gen_c(
- "uint32_t",
- name_prefix + name,
- expr_prefix,
- len(stack),
- loopdepth,
- )
- if path.elems:
- child = path.elems[-1]
- parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
- if child.in_versions < parent.in_versions:
- ret += ifdef_push(ifdef_depth + 1, c_ver_ifdef(child.in_versions))
- ifdef_depth += 1
- ret += f"{'\t'*len(stack)}if ({c_ver_cond(child.in_versions)}) {{\n"
- stack.append((path, True))
- if child.cnt:
- cnt_path = path.parent().add(child.cnt)
- if child.typ.static_size == 1: # SPECIAL (zerocopy)
- if path.root.typname == "stat": # SPECIAL (stat)
- ret += f"{'\t'*len(stack)}MARSHAL_BYTES(ctx, {path.c_str('val->')[:-3]}, {cnt_path.c_str('val->')});\n"
- else:
- ret += f"{'\t'*len(stack)}MARSHAL_BYTES_ZEROCOPY(ctx, {path.c_str('val->')[:-3]}, {cnt_path.c_str('val->')});\n"
- return WalkCmd.KEEP_GOING, pop
- loopvar = chr(ord("i") + loopdepth - 1)
- ret += f"{'\t'*len(stack)}for ({c_typename(child.cnt.typ)} {loopvar} = 0; {loopvar} < {cnt_path.c_str('val->')}; {loopvar}++) {{\n"
- stack.append((path, False))
- if not isinstance(child.typ, idl.Struct):
- if child.val:
-
- def lookup_sym(sym: str) -> str:
- nonlocal path
- if sym.startswith("&"):
- sym = sym[1:]
- return (
- "offsetof_"
- + "".join(m.membname + "_" for m in path.elems[:-1])
- + sym
- )
-
- val = c_expr(child.val, lookup_sym)
- else:
- val = path.c_str("val->")
- if isinstance(child.typ, idl.Bitfield):
- val += f" & {child.typ.typname}_masks[ctx->ctx->version]"
- ret += f"{'\t'*len(stack)}MARSHAL_U{child.typ.static_size*8}LE(ctx, {val});\n"
- return WalkCmd.KEEP_GOING, pop
-
- walk(typ, handle)
- del handle
- del stack
- del max_size
-
- ret += "\treturn false;\n"
- ret += "}\n"
- ret += ifdef_pop(0)
-
- # function tables ##########################################################
- ret += """
-/* function tables ************************************************************/
-"""
-
- ret += "\n"
- ret += f"const uint32_t _{idprefix}table_msg_min_size[{c_ver_enum('NUM')}] = {{\n"
- rerror = next(typ for typ in typs if typ.typname == "Rerror")
- ret += f"\t[{c_ver_enum('unknown')}] = {rerror.min_size('9P2000')},\n" # SPECIAL (initialization)
- for ver in sorted(versions):
- ret += ifdef_push(1, c_ver_ifdef({ver}))
- ret += f"\t[{c_ver_enum(ver)}] = {rerror.min_size(ver)},\n"
- ret += ifdef_pop(0)
- ret += "};\n"
-
- ret += "\n"
- ret += c_macro(
- f"#define _MSG_RECV(typ) [{idprefix.upper()}TYP_##typ/2] = {{\n"
- f"\t\t.basesize = sizeof(struct {idprefix}msg_##typ),\n"
- f"\t\t.validate = validate_##typ,\n"
- f"\t\t.unmarshal = (_unmarshal_fn_t)unmarshal_##typ,\n"
- f"\t}}\n"
- )
- ret += c_macro(
- f"#define _MSG_SEND(typ) [{idprefix.upper()}TYP_##typ/2] = {{\n"
- f"\t\t.marshal = (_marshal_fn_t)marshal_##typ,\n"
- f"\t}}\n"
- )
- ret += "\n"
- ret += msg_table("Tmsg", "recv", f"struct _{idprefix}recv_tentry", (0, 0x100, 2))
- ret += "\n"
- ret += msg_table("Rmsg", "recv", f"struct _{idprefix}recv_tentry", (1, 0x100, 2))
- ret += "\n"
- ret += msg_table("Tmsg", "send", f"struct _{idprefix}send_tentry", (0, 0x100, 2))
- ret += "\n"
- ret += msg_table("Rmsg", "send", f"struct _{idprefix}send_tentry", (1, 0x100, 2))
-
- ret += f"""
-LM_FLATTEN bool _{idprefix}stat_validate(struct _validate_ctx *ctx) {{
-\treturn validate_stat(ctx);
-}}
-LM_FLATTEN void _{idprefix}stat_unmarshal(struct _unmarshal_ctx *ctx, struct {idprefix}stat *out) {{
-\tunmarshal_stat(ctx, out);
-}}
-LM_FLATTEN bool _{idprefix}stat_marshal(struct _marshal_ctx *ctx, struct {idprefix}stat *val) {{
-\treturn marshal_stat(ctx, val);
-}}
-"""
-
- ############################################################################
- return ret
-
-
-# Main #########################################################################
-
-
-def main() -> None:
- if typing.TYPE_CHECKING:
-
- class ANSIColors:
- MAGENTA = "\x1b[35m"
- RED = "\x1b[31m"
- RESET = "\x1b[0m"
-
- else:
- from _colorize import ANSIColors # Present in Python 3.13+
-
- if len(sys.argv) < 2:
- raise ValueError("requires at least 1 .9p filename")
- parser = idl.Parser()
- for txtname in sys.argv[1:]:
- try:
- parser.parse_file(txtname)
- except SyntaxError as e:
- print(
- f"{ANSIColors.RED}{e.filename}{ANSIColors.RESET}:{ANSIColors.MAGENTA}{e.lineno}{ANSIColors.RESET}: {e.msg}",
- file=sys.stderr,
- )
- assert e.text
- print(f"\t{e.text}", file=sys.stderr)
- text_suffix = e.text.lstrip()
- text_prefix = e.text[: -len(text_suffix)]
- print(
- f"\t{text_prefix}{ANSIColors.RED}{'~'*len(text_suffix)}{ANSIColors.RESET}",
- file=sys.stderr,
- )
- sys.exit(2)
- versions, typs = parser.all()
- outdir = os.path.normpath(os.path.join(sys.argv[0], ".."))
- with open(
- os.path.join(outdir, "include/lib9p/9p.generated.h"), "w", encoding="utf-8"
- ) as fh:
- fh.write(gen_h(versions, typs))
- with open(os.path.join(outdir, "9p.generated.c"), "w", encoding="utf-8") as fh:
- fh.write(gen_c(versions, typs))
-
-
-if __name__ == "__main__":
- main()
diff --git a/lib9p/idl/0000-README.md b/lib9p/idl/0000-README.md
index e19a1e8..84cf865 100644
--- a/lib9p/idl/0000-README.md
+++ b/lib9p/idl/0000-README.md
@@ -17,35 +17,62 @@ client->server requests, and R-messages are server->client responses
type of a message is represented by a u8 ID; T-messages are even and
R-messages are odd.
-Messages are made up of the primitives; unsigned little-endian
-integers, identified with the following single-character mnemonics:
+9P messages are exchanged over a reliable bidirectional in-order octet
+stream. Messages are made up of the primitives; unsigned
+little-endian integers, identified with the following single-character
+mnemonics:
- 1 = u8
- 2 = u16le
- 4 = u32le
- 8 = u16le
-Out of these primitives, we can make other numeric types,
+Out of these primitives, we can make more complex types:
+
+## User-defined types
+
+### Numeric types
num NUMNAME = PRIMITIVE_TYPE
+ "NAME=VAL"...
+
+Besides just being an alias for a primitive type, a numeric type may
+define 0 or more named constants of that type, each wrapped in
+"quotes".
+
+### Bitfields
-bitfields,
+ bitfield BFNAME = PRIMITIVE_TYPE
+ "bit NBIT=NAME"...
+ "bit NBIT=reserved(NAME)"...
+ "bit NBIT=num(NUMNAME)"...
+ "alias NAME=VAL"...
+ "mask NAME=VAL"...
+ "num(NUMNAME) NAME=VAL"...
- bitfield BFNAME = PRIMITIVE_TYPE "NBIT=NAME... ALIAS=VAL..."
+The same NBIT may not be defined multiple times. The same NAME may
+not be defined multiple times.
-structures,
+ - A `reserved(...)` bit indicates that the bit is named but is not
+ allowed to be used.
+ - `num(...)` bits embed a numeric/enumerated field within a set of
+ bits. Once several bits have been allocated to a numeric field
+ with `bit NBIT=num(NUMNAME)`, constant values for that field may be
+ declared with `num(NUMNAME) NAME=VAL`. For each numeric field, a
+ `mask NUMNAME=BITMASK` is automatically declared.
+ - A `mask` defines a bitmask that selects several bits.
+ - An `alias` defines a convenience alias for a bit or set of bits.
+
+### Structures
struct STRUCTNAME = "FIELDNAME[FIELDTYPE]..."
-and messages (which are a special-case of structures).
+Or a special-case for structs that are messages; `msg` has the same
+syntax as `struct`, but has restrictions on the STRUCTNAME and the
+first 3 fields must all be declared in the same way:
msg Tname = "size[4,val=end-&size] typ[1,val=TYP] tag[tag] REST..."
-Bitfield bit names may be wrapped in `reserved(...)` or
-`subfield(...)`; reserved indicates that the bit is named but is not
-allowed to be used, and subfield indicates that the bit is part of a
-num/enum that is handled by an alias.
-
Struct fields that have numeric types (either primitives or `num`
types) can add to their type `,val=` and/or `,max=` to specify what
the exact value must be and/or what the maximum (inclusive) value is.
@@ -59,11 +86,13 @@ can be
- `&fieldname` to refer to the offset of a field name in that struct,
- the special value `end` to refer to the offset of the end of the
struct,
- - the special value `s32_max` to refer to the constant value
- `(1<<31)-1`, or
- - the special value `s64_max` to refer to the constant value
- `(1<<63)-1`
+ - the special value `u{8,16,32,64}_max` to refer to the constant
+ value `(1<<{n})-1`, or
+ - the special value `s{8,16,32,64}_max` to refer to the constant value
+ `(1<<({n}-1))-1`.
+
+## Parser
A parser for this syntax is given in `__init__.py`. However,
`__init__.py` places the somewhat arbitrary undocumented restrictions
-on fields referenced as the count for a repeated field.
+on fields referenced as the count of a repeated field.
diff --git a/lib9p/idl/0000-TODO.md b/lib9p/idl/0000-TODO.md
index d196ac9..e52902f 100644
--- a/lib9p/idl/0000-TODO.md
+++ b/lib9p/idl/0000-TODO.md
@@ -1,6 +1,6 @@
<!--
lib9p/idl/0000-TODO.md - Changes I intend to make to idl/__init__.py
- and idl.gen
+ and proto.gen
Copyright (C) 2025 Luke T. Shumaker <lukeshu@lukeshu.com>
SPDX-License-Identifier: AGPL-3.0-or-later
@@ -9,5 +9,3 @@
- Decide how to handle duplicate type names from different versions
- Decide how to handle duplicate `enum lib9p_msg_type` names and
values
-- Clean up the iterate-over-all-msgids-in-a-version code
-- Allow for const `.cnt` instead of only having previous-member `.cnt`
diff --git a/lib9p/idl/1992-9P0.9p.wip b/lib9p/idl/1992-9P0.9p.wip
index 086e8e4..a434ba2 100644
--- a/lib9p/idl/1992-9P0.9p.wip
+++ b/lib9p/idl/1992-9P0.9p.wip
@@ -37,40 +37,40 @@ struct errstr = "64*(txt[1])"
# "O"pen flags (flags to pass to Topen and Tcreate)
# Unused bits are *ignored*.
bitfield o = 1
- "0=mode_0" # low bit of the 2-bit READ/WRITE/RDWR/EXEC enum
- "1=mode_1" # high bit of the 2-bit READ/WRITE/RDWR/EXEC enum
- #"2=unused"
- #"3=unused"
- "4=TRUNC"
- #"5=_reserved_CEXEC" # close-on-exec
- "6=RCLOSE" # remove-on-close
- #"7=unused"
+ "bit 0=num(MODE)" # low bit of the 2-bit READ/WRITE/RDWR/EXEC enum
+ "bit 1=num(MODE)" # high bit of the 2-bit READ/WRITE/RDWR/EXEC enum
+ #"bit 2=unused"
+ #"bit 3=unused"
+ "bit 4=TRUNC"
+ "bit 5=reserved(CEXEC)" # close-on-exec
+ "bit 6=RCLOSE" # remove-on-close
+ #"bit 7=unused"
- "READ = 0" # make available for this FID: Tread()
- "WRITE = 1" # make available for this FID: Twrite()
- "RDWR = 2" # make available for this FID: Tread() and Twrite()
- "EXEC = 3" # make available for this FID: Tread()
+ "num(MODE) READ = 0" # make available for this FID: Tread()
+ "num(MODE) WRITE = 1" # make available for this FID: Twrite()
+ "num(MODE) RDWR = 2" # make available for this FID: Tread() and Twrite()
+ "num(MODE) EXEC = 3" # make available for this FID: Tread()
- "MODE_MASK = 0b00000011"
- "FLAG_MASK = 0b11111100"
+ "mask FLAG = 0b11111100"
-# "C"??? "H"??? - file permissions and attributes
+# "CH"annel flags - file permissions and attributes (a "channel" is
+# what a file handle is called inside of the Plan 9 kernel).
bitfield ch = 4
- "31=DIR"
- "30=APPEND"
- "29=EXCL"
+ "bit 31=DIR"
+ "bit 30=APPEND"
+ "bit 29=EXCL"
#...
- "8=OWNER_R"
- "7=OWNER_W"
- "6=OWNER_X"
- "5=GROUP_R"
- "4=GROUP_W"
- "3=GROUP_X"
- "2=OTHER_R"
- "1=OTHER_W"
- "0=OTHER_X"
+ "bit 8=OWNER_R"
+ "bit 7=OWNER_W"
+ "bit 6=OWNER_X"
+ "bit 5=GROUP_R"
+ "bit 4=GROUP_W"
+ "bit 3=GROUP_X"
+ "bit 2=OTHER_R"
+ "bit 1=OTHER_W"
+ "bit 0=OTHER_X"
- "PERM_MASK=0777" # {OWNER,GROUP,OTHER}_{R,W,X}
+ "mask PERM=0777" # {OWNER,GROUP,OTHER}_{R,W,X}
struct stat = "file_name[name]"
"file_owner[name]"
diff --git a/lib9p/idl/1995-9P1.9p.wip b/lib9p/idl/1995-9P1.9p.wip
index 2caf39d..660e24a 100644
--- a/lib9p/idl/1995-9P1.9p.wip
+++ b/lib9p/idl/1995-9P1.9p.wip
@@ -43,7 +43,7 @@ from ./1992-9P0.9p import tag, fid, qid, name, errstr, o, ch, stat
# draft RFC). As I understand it, CHMOUNT indicates that the file is
# mounted by the kernel as a 9P transport; that the kernel has a lock
# on doing I/O on it, so userspace can't do I/O on it.
-bitfield ch += "28=MOUNT"
+bitfield ch += "bit 28=_PLAN9_MOUNT"
# Authentication uses DES encryption. The client obtains a ticket and
# a nonce-key from a separate auth-server; how it does this is beyond
diff --git a/lib9p/idl/1996-Styx.9p.wip b/lib9p/idl/1996-Styx.9p.wip
index 6ba4509..3cb3774 100644
--- a/lib9p/idl/1996-Styx.9p.wip
+++ b/lib9p/idl/1996-Styx.9p.wip
@@ -40,7 +40,7 @@ msg Ropen = "typ[1,val=11] tag[tag] fid[fid] qid[qid]"
msg Tcreate = "typ[1,val=12] tag[tag] fid[fid] name[name] perm[ch] mode[o]"
msg Rcreate = "typ[1,val=13] tag[tag] fid[fid] qid[qid]"
# For `offset:max`, see `fs.c` `f_read()` and `f_write()`.
-# For `count:max`, see `styx.h:MAXFDATA'.
+# For `count:max`, see `styx.h:MAXFDATA`.
msg Tread = "typ[1,val=14] tag[tag] fid[fid] offset[8,max=s64_max] count[2,max=8192]"
msg Rread = "typ[1,val=15] tag[tag] fid[fid] count[2,max=8192] pad[1] count*(data[1])"
msg Twrite = "typ[1,val=16] tag[tag] fid[fid] offset[8,max=s64_max] count[2,max=8192] pad[1] count*(data[1])"
diff --git a/lib9p/idl/2002-9P2000.9p b/lib9p/idl/2002-9P2000.9p
index 2a4f7ed..2b51612 100644
--- a/lib9p/idl/2002-9P2000.9p
+++ b/lib9p/idl/2002-9P2000.9p
@@ -22,64 +22,64 @@ version "9P2000"
# tag - identify a request/response pair
num tag = 2
- "NOTAG = ~0"
+ "NOTAG = u16_max"
# file identifier - like a UNIX file-descriptor
num fid = 4
- "NOFID = ~0"
+ "NOFID = u32_max"
# string - u16le `n`, then `n` bytes of UTF-8, without any nul-bytes
struct s = "len[2] len*(utf8[1])"
# "D"ir-entry "M"ode - file permissions and attributes
bitfield dm = 4
- "31=DIR"
- "30=APPEND"
- "29=EXCL"
- # DMMOUNT has been around in Plan 9 forever (CHMOUNT in <4e),
+ "bit 31=DIR"
+ "bit 30=APPEND"
+ "bit 29=EXCL"
+ # DMMOUNT has been around in Plan 9 since 2e (CHMOUNT in <4e),
# but is undocumented, and is explicitly excluded from the
# 9P2000 draft RFC. As I understand it, DMMOUNT indicates
# that the file is mounted by the kernel as a 9P transport;
# that the kernel has a lock on doing I/O on it, so userspace
# can't do I/O on it.
- "28=reserved(PLAN9_MOUNT)"
- "27=AUTH"
- "26=TMP"
+ "bit 28=_PLAN9_MOUNT"
+ "bit 27=AUTH"
+ "bit 26=TMP"
#...
- "8=OWNER_R"
- "7=OWNER_W"
- "6=OWNER_X"
- "5=GROUP_R"
- "4=GROUP_W"
- "3=GROUP_X"
- "2=OTHER_R"
- "1=OTHER_W"
- "0=OTHER_X"
+ "bit 8=OWNER_R"
+ "bit 7=OWNER_W"
+ "bit 6=OWNER_X"
+ "bit 5=GROUP_R"
+ "bit 4=GROUP_W"
+ "bit 3=GROUP_X"
+ "bit 2=OTHER_R"
+ "bit 1=OTHER_W"
+ "bit 0=OTHER_X"
- "PERM_MASK=0777" # {OWNER,GROUP,OTHER}_{R,W,X}
+ "mask PERM=0777" # {OWNER,GROUP,OTHER}_{R,W,X}
# QID Type - see `struct qid` below
bitfield qt = 1
- "7=DIR"
- "6=APPEND"
- "5=EXCL"
- "4=reserved(PLAN9_MOUNT)" # See "PLAN9_MOUNT" in "dm" above.
- "3=AUTH"
+ "bit 7=DIR"
+ "bit 6=APPEND"
+ "bit 5=EXCL"
+ "bit 4=_PLAN9_MOUNT" # See "_PLAN9_MOUNT" in "dm" above.
+ "bit 3=AUTH"
# Fun historical fact: QTTMP was a relatively late addition to
# Plan 9, in 2003-12.
- "2=TMP"
- #"1=unused"
+ "bit 2=TMP"
+ #"bit 1=unused"
# "The name QTFILE, defined to be zero, identifies the value
# of the type for a plain file."
- "FILE=0"
+ "alias FILE=0"
# uni"Q"ue "ID"entification - "two files on the same server hierarchy
# are the same if and only if their qids are the same"
#
# - "path" is a unique uint64_t that does most of the work in the
# above statement about files being the same if their QIDs are the
-# same; " If a file is deleted and recreated with the same name in
+# same; "If a file is deleted and recreated with the same name in
# the same directory, the old and new path components of the qids
# should be different"
#
@@ -107,22 +107,21 @@ struct stat = "stat_size[2,val=end-&kern_type]"
# "O"pen flags (flags to pass to Topen and Tcreate)
# Unused bits *must* be 0.
bitfield o = 1
- "0=subfield(mode)" # low bit of the 2-bit READ/WRITE/RDWR/EXEC enum
- "1=subfield(mode)" # high bit of the 2-bit READ/WRITE/RDWR/EXEC enum
- #"2=unused"
- #"3=unused"
- "4=TRUNC"
- "5=reserved(CEXEC)" # close-on-exec
- "6=RCLOSE" # remove-on-close
- #"7=unused"
+ "bit 0=num(MODE)" # low bit of the 2-bit READ/WRITE/RDWR/EXEC enum
+ "bit 1=num(MODE)" # high bit of the 2-bit READ/WRITE/RDWR/EXEC enum
+ #"bit 2=unused"
+ #"bit 3=unused"
+ "bit 4=TRUNC"
+ "bit 5=reserved(CEXEC)" # close-on-exec
+ "bit 6=RCLOSE" # remove-on-close
+ #"bit 7=unused"
- "READ = 0" # make available for this FID: Tread()
- "WRITE = 1" # make available for this FID: Twrite()
- "RDWR = 2" # make available for this FID: Tread() and Twrite()
- "EXEC = 3" # make available for this FID: Tread()
+ "num(MODE) READ = 0" # make available for this FID: Tread()
+ "num(MODE) WRITE = 1" # make available for this FID: Twrite()
+ "num(MODE) RDWR = 2" # make available for this FID: Tread() and Twrite()
+ "num(MODE) EXEC = 3" # make available for this FID: Tread()
- "MODE_MASK = 0b00000011"
- "FLAG_MASK = 0b11111100"
+ "mask FLAG = 0b11111100"
# A 9P2000 session goes:
#
diff --git a/lib9p/idl/2005-9P2000.u.9p b/lib9p/idl/2005-9P2000.u.9p
index fefe3e9..6c2f2dc 100644
--- a/lib9p/idl/2005-9P2000.u.9p
+++ b/lib9p/idl/2005-9P2000.u.9p
@@ -12,7 +12,7 @@ from ./2002-9P2000.9p import *
# numeric user ID
num nuid = 4
- "NONUID = ~0"
+ "NONUID = u32_max"
num errno = 4
"NOERROR = 0"
@@ -27,10 +27,10 @@ msg Tattach += "n_uid[nuid]"
msg Rerror += "errno[errno]"
-bitfield dm += "23=DEVICE"
- "21=NAMEDPIPE"
- "20=SOCKET"
- "19=SETUID"
- "18=SETGID"
+bitfield dm += "bit 23=DEVICE"
+ "bit 21=PIPE"
+ "bit 20=SOCKET"
+ "bit 19=SETUID"
+ "bit 18=SETGID"
-bitfield qt += "1=SYMLINK"
+bitfield qt += "bit 1=SYMLINK"
diff --git a/lib9p/idl/2010-9P2000.L.9p b/lib9p/idl/2010-9P2000.L.9p
index 7ac86a6..d81a15b 100644
--- a/lib9p/idl/2010-9P2000.L.9p
+++ b/lib9p/idl/2010-9P2000.L.9p
@@ -39,49 +39,48 @@ num super_magic = 4
# protocol.h (and are different than the Linux kernel's values, which
# vary by architecture).
bitfield lo = 4
- "0=subfield(mode)" # low bit of the 2-bit RDONLY/WRONLY/RDWR/NOACCESS enum
- "1=subfield(mode)" # high bit of the 2-bit RDONLY/WRONLY/RDWR/NOACCESS enum
- #"2=unused"
- #"3=unused"
- #"4=unused"
- #"5=unused"
- "6=CREATE"
- "7=EXCL"
- "8=NOCTTY"
- "9=TRUNC"
- "10=APPEND"
- "11=NONBLOCK"
- "12=DSYNC"
- "13=BSD_FASYNC"
- "14=DIRECT"
- "15=LARGEFILE"
- "16=DIRECTORY"
- "17=NOFOLLOW"
- "18=NOATIME"
- "19=CLOEXEC"
- "20=SYNC"
-
- "RDONLY = 0"
- "WRONLY = 1"
- "RDWR = 2"
- "NOACCESS = 3"
-
- "MODE_MASK = 0b000000000000000000011"
- "FLAG_MASK = 0b111111111111111000000"
+ "bit 0=num(MODE)" # low bit of the 2-bit RDONLY/WRONLY/RDWR/NOACCESS enum
+ "bit 1=num(MODE)" # high bit of the 2-bit RDONLY/WRONLY/RDWR/NOACCESS enum
+ #"bit 2=unused"
+ #"bit 3=unused"
+ #"bit 4=unused"
+ #"bit 5=unused"
+ "bit 6=CREATE"
+ "bit 7=EXCL"
+ "bit 8=NOCTTY"
+ "bit 9=TRUNC"
+ "bit 10=APPEND"
+ "bit 11=NONBLOCK"
+ "bit 12=DSYNC"
+ "bit 13=BSD_FASYNC"
+ "bit 14=DIRECT"
+ "bit 15=LARGEFILE"
+ "bit 16=DIRECTORY"
+ "bit 17=NOFOLLOW"
+ "bit 18=NOATIME"
+ "bit 19=CLOEXEC"
+ "bit 20=SYNC"
+
+ "num(MODE) RDONLY = 0"
+ "num(MODE) WRONLY = 1"
+ "num(MODE) RDWR = 2"
+ "num(MODE) NOACCESS = 3"
+
+ "mask FLAG = 0b111111111111111000000"
# "D"irentry "T"ype
#
# These match the Linux kernel's values.
num dt = 1
- "UNKNOWN = 0"
- "NAMED_PIPE = 1"
- "CHAR_DEV = 2"
- "DIRECTORY = 4"
- "BLOCK_DEV = 6"
- "REGULAR = 8"
- "SYMLINK = 10"
- "SOCKET = 12"
- "WHITEOUT = 14"
+ "UNKNOWN = 0"
+ "PIPE = 1"
+ "CHAR_DEV = 2"
+ "DIRECTORY = 4"
+ "BLOCK_DEV = 6" # proof it's not a bitfield
+ "REGULAR = 8"
+ "SYMLINK = 10" # proof it's not a bitfield
+ "SOCKET = 12" # proof it's not a bitfield
+ "_WHITEOUT = 14" # proof it's not a bitfield
# Mode
#
@@ -89,34 +88,33 @@ num dt = 1
# instead of just 16? Who knows?
bitfield mode = 4
#...
- "15=subfield(fmt)" # bit of the 4-bit FMT_ enum
- "14=subfield(fmt)" # bit of the 4-bit FMT_ enum
- "13=subfield(fmt)" # bit of the 4-bit FMT_ enum
- "12=subfield(fmt)" # bit of the 4-bit FMT_ enum
+ "bit 15=num(FMT)" # bit of the 4-bit FMT_ enum
+ "bit 14=num(FMT)" # bit of the 4-bit FMT_ enum
+ "bit 13=num(FMT)" # bit of the 4-bit FMT_ enum
+ "bit 12=num(FMT)" # bit of the 4-bit FMT_ enum
#...
- "11=PERM_SETGROUP"
- "10=PERM_SETUSER"
- "9=PERM_STICKY"
- "8=PERM_OWNER_R"
- "7=PERM_OWNER_W"
- "6=PERM_OWNER_X"
- "5=PERM_GROUP_R"
- "4=PERM_GROUP_W"
- "3=PERM_GROUP_X"
- "2=PERM_OTHER_R"
- "1=PERM_OTHER_W"
- "0=PERM_OTHER_X"
-
- "FMT_NAMED_PIPE = LIB9P_DT_NAMED_PIPE<<12"
- "FMT_CHAR_DEV = LIB9P_DT_CHAR_DEV<<12"
- "FMT_DIRECTORY = LIB9P_DT_DIRECTORY<<12"
- "FMT_BLOCK_DEV = LIB9P_DT_BLOCK_DEV<<12"
- "FMT_REGULAR = LIB9P_DT_REGULAR<<12"
- "FMT_SYMLINK = LIB9P_DT_SYMLINK<<12"
- "FMT_SOCKET = LIB9P_DT_SOCKET<<12"
-
- "PERM_MASK = 0000777" # PERM_*
- "FMT_MASK = 0170000" # _fmt_*
+ "bit 11=PERM_SETGROUP"
+ "bit 10=PERM_SETUSER"
+ "bit 9=PERM_STICKY"
+ "bit 8=PERM_OWNER_R"
+ "bit 7=PERM_OWNER_W"
+ "bit 6=PERM_OWNER_X"
+ "bit 5=PERM_GROUP_R"
+ "bit 4=PERM_GROUP_W"
+ "bit 3=PERM_GROUP_X"
+ "bit 2=PERM_OTHER_R"
+ "bit 1=PERM_OTHER_W"
+ "bit 0=PERM_OTHER_X"
+
+ "num(FMT) PIPE = dt.PIPE<<12"
+ "num(FMT) CHAR_DEV = dt.CHAR_DEV<<12"
+ "num(FMT) DIRECTORY = dt.DIRECTORY<<12"
+ "num(FMT) BLOCK_DEV = dt.BLOCK_DEV<<12"
+ "num(FMT) REGULAR = dt.REGULAR<<12"
+ "num(FMT) SYMLINK = dt.SYMLINK<<12"
+ "num(FMT) SOCKET = dt.SOCKET<<12"
+
+ "mask PERM = 07777" # PERM_*
# A boolean value that is for some reason 4 bytes wide.
num b4 = 4
@@ -125,35 +123,35 @@ num b4 = 4
# all other values are true also
bitfield getattr = 8
- "0=MODE"
- "1=NLINK"
- "2=UID"
- "3=GID"
- "4=RDEV"
- "5=ATIME"
- "6=MTIME"
- "7=CTIME"
- "8=INO"
- "9=SIZE"
- "10=BLOCKS"
-
- "11=BTIME"
- "12=GEN"
- "13=DATA_VERSION"
-
- "BASIC=0x000007ff" # Mask for fields up to BLOCKS
- "ALL =0x00003fff" # Mask for All fields above
+ "bit 0=MODE"
+ "bit 1=NLINK"
+ "bit 2=UID"
+ "bit 3=GID"
+ "bit 4=RDEV"
+ "bit 5=ATIME"
+ "bit 6=MTIME"
+ "bit 7=CTIME"
+ "bit 8=INO"
+ "bit 9=SIZE"
+ "bit 10=BLOCKS"
+
+ "bit 11=BTIME"
+ "bit 12=GEN"
+ "bit 13=DATA_VERSION"
+
+ "alias BASIC=0x000007ff" # Mask for fields up to BLOCKS
+ "alias ALL =0x00003fff" # Mask for All fields above
bitfield setattr = 4
- "0=MODE"
- "1=UID"
- "2=GID"
- "3=SIZE"
- "4=ATIME"
- "5=MTIME"
- "6=CTIME"
- "7=ATIME_SET"
- "8=MTIME_SET"
+ "bit 0=MODE"
+ "bit 1=UID"
+ "bit 2=GID"
+ "bit 3=SIZE"
+ "bit 4=ATIME"
+ "bit 5=MTIME"
+ "bit 6=CTIME"
+ "bit 7=ATIME_SET"
+ "bit 8=MTIME_SET"
num lock_type = 1
"RDLCK=0"
@@ -161,8 +159,8 @@ num lock_type = 1
"UNLCK=2"
bitfield lock_flags = 4
- "0=BLOCK"
- "1=RECLAIM"
+ "bit 0=BLOCK"
+ "bit 1=RECLAIM"
num lock_status = 1
"SUCCESS=0"
diff --git a/lib9p/idl/__init__.py b/lib9p/idl/__init__.py
index e7b3670..2d09217 100644
--- a/lib9p/idl/__init__.py
+++ b/lib9p/idl/__init__.py
@@ -15,14 +15,27 @@ __all__ = [
# types
"Type",
"Primitive",
+ *["Expr", "ExprTok", "ExprOp", "ExprLit", "ExprSym", "ExprOff", "ExprNum"],
"Number",
- *["Bitfield", "Bit", "BitCat", "BitAlias"],
- *["Struct", "StructMember", "Expr", "ExprOp", "ExprSym", "ExprLit"],
+ *["Bitfield", "Bit", "BitCat", "BitNum", "BitAlias"],
+ *["Struct", "StructMember"],
"Message",
]
# The syntax that this parses is described in `./0000-README.md`.
+# Utilities ####################################################################
+
+
+def get_type(env: dict[str, "Type"], name: str, tc: type["T"]) -> "T":
+ if name not in env:
+ raise NameError(f"Unknown type {name!r}")
+ ret = env[name]
+ if (not isinstance(ret, tc)) or (ret.__class__.__name__ != tc.__name__):
+ raise NameError(f"Type {ret.typname!r} is not a {tc.__name__}")
+ return ret
+
+
# Types ########################################################################
@@ -51,13 +64,129 @@ class Primitive(enum.Enum):
return self.value
+class ExprOp:
+ op: typing.Literal["-", "+", "<<"]
+
+ def __init__(self, op: typing.Literal["-", "+", "<<"]) -> None:
+ self.op = op
+
+
+class ExprLit:
+ val: int
+
+ def __init__(self, val: int) -> None:
+ self.val = val
+
+
+class ExprSym:
+ symname: str
+
+ def __init__(self, name: str) -> None:
+ self.symname = name
+
+
+class ExprOff:
+ membname: str
+
+ def __init__(self, name: str) -> None:
+ self.membname = name
+
+
+class ExprNum:
+ numname: str
+ valname: str
+
+ def __init__(self, numname: str, valname: str) -> None:
+ self.numname = numname
+ self.valname = valname
+
+
+type ExprTok = ExprOp | ExprLit | ExprSym | ExprOff | ExprNum
+
+
+class Expr:
+ tokens: typing.Sequence[ExprTok]
+ const: int | None
+
+ def __init__(
+ self, env: dict[str, "Type"], tokens: typing.Sequence[ExprTok] = ()
+ ) -> None:
+ self.tokens = tokens
+ self.const = self._const(env, tokens)
+
+ def _const(
+ self, env: dict[str, "Type"], toks: typing.Sequence[ExprTok]
+ ) -> int | None:
+ if not toks:
+ return None
+
+ def read_val() -> int | None:
+ nonlocal toks
+ assert toks
+ neg = False
+ match toks[0]:
+ case ExprOp(op="-"):
+ neg = True
+ toks = toks[1:]
+ assert not isinstance(toks[0], ExprOp)
+ val: int
+ match toks[0]:
+ case ExprLit():
+ val = toks[0].val
+ case ExprSym():
+ if m := re.fullmatch(r"^u(8|16|32|64)_max$", toks[0].symname):
+ n = int(m.group(1))
+ val = (1 << n) - 1
+ elif m := re.fullmatch(r"^s(8|16|32|64)_max$", toks[0].symname):
+ n = int(m.group(1))
+ val = (1 << (n - 1)) - 1
+ else:
+ return None
+ case ExprOff():
+ return None
+ case ExprNum():
+ num = get_type(env, toks[0].numname, Number)
+ if toks[0].valname not in num.vals:
+ raise NameError(
+ f"Type {toks[0].numname!r} does not have a value {toks[0].valname!r}"
+ )
+ _val = num.vals[toks[0].valname].const
+ if _val is None:
+ return None
+ val = _val
+ toks = toks[1:]
+ return -val if neg else val
+
+ ret = read_val()
+ if ret is None:
+ return None
+ while toks:
+ assert isinstance(toks[0], ExprOp)
+ op = toks[0].op
+ toks = toks[1:]
+ operand = read_val()
+ if operand is None:
+ return None
+ match op:
+ case "+":
+ ret = ret + operand
+ case "-":
+ ret = ret - operand
+ case "<<":
+ ret = ret << operand
+ return ret
+
+ def __bool__(self) -> bool:
+ return len(self.tokens) > 0
+
+
class Number:
typname: str
in_versions: set[str]
prim: Primitive
- vals: dict[str, str]
+ vals: dict[str, Expr]
def __init__(self) -> None:
self.in_versions = set()
@@ -74,11 +203,31 @@ class Number:
return self.static_size
-class BitCat(enum.Enum):
- UNUSED = 1
- USED = 2
- RESERVED = 3
- SUBFIELD = 4
+class BitAlias:
+ bitname: str
+ in_versions: set[str]
+ val: Expr
+
+ def __init__(self, name: str, val: Expr) -> None:
+ if val.const is None:
+ raise ValueError(f"{name!r} value is not constant")
+ self.bitname = name
+ self.in_versions = set()
+ self.val = val
+
+
+class BitNum:
+ numname: str
+ mask: int
+ vals: dict[str, BitAlias]
+
+ def __init__(self, name: str) -> None:
+ self.numname = name
+ self.mask = 0
+ self.vals = {}
+
+
+type BitCat = typing.Literal["UNUSED", "USED", "RESERVED"] | BitNum
class Bit:
@@ -91,33 +240,32 @@ class Bit:
self.bitname = ""
self.in_versions = set()
self.num = num
- self.cat = BitCat.UNUSED
-
-
-class BitAlias:
- bitname: str
- in_versions: set[str]
- val: str # FIXME: Don't have bitfield aliases be raw C expressions
-
- def __init__(self, name: str, val: str) -> None:
- self.bitname = name
- self.in_versions = set()
- self.val = val
+ self.cat = "UNUSED"
class Bitfield:
typname: str
in_versions: set[str]
prim: Primitive
+
bits: list[Bit]
- names: dict[str, Bit | BitAlias]
+ nums: dict[str, BitNum]
+ masks: dict[str, BitAlias]
+ aliases: dict[str, BitAlias]
+
+ names: set[str]
def __init__(self, name: str, prim: Primitive) -> None:
self.typname = name
self.in_versions = set()
self.prim = prim
+
self.bits = [Bit(i) for i in range(prim.static_size * 8)]
- self.names = {}
+ self.nums = {}
+ self.masks = {}
+ self.aliases = {}
+
+ self.names = set()
@property
def static_size(self) -> int:
@@ -130,40 +278,9 @@ class Bitfield:
return self.static_size
-class ExprLit:
- val: int
-
- def __init__(self, val: int) -> None:
- self.val = val
-
-
-class ExprSym:
- symname: str
-
- def __init__(self, name: str) -> None:
- self.symname = name
-
-
-class ExprOp:
- op: typing.Literal["-", "+"]
-
- def __init__(self, op: typing.Literal["-", "+"]) -> None:
- self.op = op
-
-
-class Expr:
- tokens: list[ExprLit | ExprSym | ExprOp]
-
- def __init__(self) -> None:
- self.tokens = []
-
- def __bool__(self) -> bool:
- return len(self.tokens) > 0
-
-
class StructMember:
# from left-to-right when parsing
- cnt: "StructMember | None" = None
+ cnt: "StructMember| int | None" = None
membname: str
typ: "Type"
max: Expr
@@ -174,6 +291,8 @@ class StructMember:
@property
def min_cnt(self) -> int:
assert self.cnt
+ if isinstance(self.cnt, int):
+ return self.cnt
if not isinstance(self.cnt.typ, Primitive):
raise ValueError(
f"list count must be an integer type: {self.cnt.membname!r}"
@@ -185,6 +304,8 @@ class StructMember:
@property
def max_cnt(self) -> int:
assert self.cnt
+ if isinstance(self.cnt, int):
+ return self.cnt
if not isinstance(self.cnt.typ, Primitive):
raise ValueError(
f"list count must be an integer type: {self.cnt.membname!r}"
@@ -193,21 +314,12 @@ class StructMember:
raise ValueError(f"list count may not have ,val=: {self.cnt.membname!r}")
if self.cnt.max:
# TODO: be more flexible?
- if len(self.cnt.max.tokens) != 1:
+ val = self.cnt.max.const
+ if val is None:
raise ValueError(
- f"list count ,max= may only have 1 token: {self.cnt.membname!r}"
+ f"list count ,max= must be a constant value: {self.cnt.membname!r}"
)
- match tok := self.cnt.max.tokens[0]:
- case ExprLit():
- return tok.val
- case ExprSym(symname="s32_max"):
- return (1 << 31) - 1
- case ExprSym(symname="s64_max"):
- return (1 << 63) - 1
- case _:
- raise ValueError(
- f'list count ,max= only allows literal, "s32_max", and "s64_max" tokens: {self.cnt.membname!r}'
- )
+ return val
return (1 << (self.cnt.typ.value * 8)) - 1
@property
@@ -279,6 +391,8 @@ T = typing.TypeVar("T", Number, Bitfield, Struct, Message)
# Parse ########################################################################
+# common elements ######################
+
re_priname = "(?:1|2|4|8)" # primitive names
re_symname = "(?:[a-zA-Z_][a-zA-Z_0-9]*)" # "symbol" names; most *.9p-defined names
re_symname_u = "(?:[A-Z_][A-Z_0-9]*)" # upper-case "symbol" names; bit names
@@ -288,99 +402,186 @@ re_msgname = r"(?:[TR][a-zA-Z_0-9]*)" # names a message can be
re_memtype = f"(?:{re_symname}|{re_priname})" # typenames that a struct member can be
-re_expr = f"(?:(?:-|\\+|[0-9]+|&?{re_symname})+)"
+valid_syms = [
+ "end",
+ "u8_max",
+ "u16_max",
+ "u32_max",
+ "u64_max",
+ "s8_max",
+ "s16_max",
+ "s32_max",
+ "s64_max",
+]
-re_numspec = f"(?P<name>{re_symname})\\s*=\\s*(?P<val>\\S+)"
+_re_expr_op = r"(?:-|\+|<<)"
-re_bitspec_bit = (
- "(?P<bitnum>[0-9]+)\\s*=\\s*(?:"
+_res_expr_val = {
+ "lit_2": r"0b[01]+",
+ "lit_8": r"0[0-7]+",
+ "lit_10": r"0(?![0-9bxX])|[1-9][0-9]*",
+ "lit_16": r"0[xX][0-9a-fA-F]+",
+ "sym": "|".join(valid_syms), # pre-defined symbols
+ "off": f"&{re_symname}", # offset of a field this struct
+ "num": f"{re_symname}\\.{re_symname}", # `num` values
+}
+
+re_expr_tok = (
+ "(?:"
+ "|".join(
[
- f"(?P<name_used>{re_symname_u})",
- f"reserved\\((?P<name_reserved>{re_symname_u})\\)",
- f"subfield\\((?P<name_subfield>{re_symname_l})\\)",
+ f"(?P<op>{_re_expr_op})",
+ *[f"(?P<{k}>{v})" for k, v in _res_expr_val.items()],
]
)
+ ")"
)
-re_bitspec_alias = f"(?P<name>{re_symname_u})\\s*=\\s*(?P<val>\\S+)"
-re_memberspec = f"(?:(?P<cnt>{re_symname})\\*\\()?(?P<name>{re_symname})\\[(?P<typ>{re_memtype})(?:,max=(?P<max>{re_expr})|,val=(?P<val>{re_expr}))*\\]\\)?"
+_re_expr_val = "(?:" + "|".join(_res_expr_val.values()) + ")"
+re_expr = f"(?:\\s*(?:-\\s*)?{_re_expr_val}\\s*(?:{_re_expr_op}\\s*(?:-\\s*)?{_re_expr_val}\\s*)*)"
-def parse_numspec(ver: str, n: Number, spec: str) -> None:
+
+def parse_expr(env: dict[str, Type], expr: str) -> Expr:
+ assert re.fullmatch(re_expr, expr)
+ tokens: list[ExprTok] = []
+ for m in re.finditer(re_expr_tok, expr):
+ if tok := m.group("op"):
+ tokens.append(ExprOp(typing.cast(typing.Literal["-", "+", "<<"], tok)))
+ elif tok := m.group("lit_2"):
+ tokens.append(ExprLit(int(tok[2:], 2)))
+ elif tok := m.group("lit_8"):
+ tokens.append(ExprLit(int(tok[1:], 8)))
+ elif tok := m.group("lit_10"):
+ tokens.append(ExprLit(int(tok, 10)))
+ elif tok := m.group("lit_16"):
+ tokens.append(ExprLit(int(tok[2:], 16)))
+ elif tok := m.group("sym"):
+ tokens.append(ExprSym(tok))
+ elif tok := m.group("off"):
+ tokens.append(ExprOff(tok[1:]))
+ elif tok := m.group("num"):
+ [numname, valname] = tok.split(".", 1)
+ tokens.append(ExprNum(numname, valname))
+ else:
+ assert False
+ return Expr(env, tokens)
+
+
+# numspec ##############################
+
+re_numspec = f"(?P<name>{re_symname})\\s*=\\s*(?P<val>{re_expr})"
+
+
+def parse_numspec(env: dict[str, Type], ver: str, n: Number, spec: str) -> None:
spec = spec.strip()
if m := re.fullmatch(re_numspec, spec):
name = m.group("name")
- val = m.group("val")
if name in n.vals:
raise ValueError(f"{n.typname}: name {name!r} already assigned")
+ val = parse_expr(env, m.group("val"))
+ if val is None:
+ raise ValueError(
+ f"{n.typname}: {name!r} value is not constant: {m.group('val')!r}"
+ )
n.vals[name] = val
else:
raise SyntaxError(f"invalid num spec {spec!r}")
-def parse_bitspec(ver: str, bf: Bitfield, spec: str) -> None:
+# bitspec ##############################
+
+re_bitspec_bit = (
+ "bit\\s+(?P<bitnum>[0-9]+)\\s*=\\s*(?:"
+ + "|".join(
+ [
+ f"(?P<name_used>{re_symname_u})",
+ f"reserved\\((?P<name_reserved>{re_symname_u})\\)",
+ f"num\\((?P<name_num>{re_symname_u})\\)",
+ ]
+ )
+ + ")"
+)
+re_bitspec_mask = f"mask\\s+(?P<name>{re_symname_u})\\s*=\\s*(?P<val>{re_expr})"
+re_bitspec_alias = f"alias\\s+(?P<name>{re_symname_u})\\s*=\\s*(?P<val>{re_expr})"
+re_bitspec_num = f"num\\((?P<num>{re_symname_u})\\)\\s+(?P<name>{re_symname_u})\\s*=\\s*(?P<val>{re_expr})"
+
+
+def parse_bitspec(env: dict[str, Type], ver: str, bf: Bitfield, spec: str) -> None:
spec = spec.strip()
+ def check_name(name: str, is_num: bool = False) -> None:
+ if name == "MASK":
+ raise ValueError(f"{bf.typname}: bit name may not be {'MASK'!r}: {name!r}")
+ if name.endswith("_MASK"):
+ raise ValueError(
+ f"{bf.typname}: bit name may not end with {'_MASK'!r}: {name!r}"
+ )
+ if name in bf.names and not (is_num and name in bf.nums):
+ raise ValueError(f"{bf.typname}: bit name already assigned: {name!r}")
+
if m := re.fullmatch(re_bitspec_bit, spec):
bitnum = int(m.group("bitnum"))
if bitnum < 0 or bitnum >= len(bf.bits):
raise ValueError(f"{bf.typname}: bit num {bitnum} out-of-bounds")
bit = bf.bits[bitnum]
- if bit.cat != BitCat.UNUSED:
+ if bit.cat != "UNUSED":
raise ValueError(f"{bf.typname}: bit num {bitnum} already assigned")
if name := m.group("name_used"):
bit.bitname = name
- bit.cat = BitCat.USED
+ bit.cat = "USED"
bit.in_versions.add(ver)
elif name := m.group("name_reserved"):
bit.bitname = name
- bit.cat = BitCat.RESERVED
+ bit.cat = "RESERVED"
bit.in_versions.add(ver)
- elif name := m.group("name_subfield"):
+ elif name := m.group("name_num"):
bit.bitname = name
- bit.cat = BitCat.SUBFIELD
+ if name not in bf.nums:
+ bf.nums[name] = BitNum(name)
+ bf.nums[name].mask |= 1 << bit.num
+ bit.cat = bf.nums[name]
bit.in_versions.add(ver)
if bit.bitname:
- if bit.bitname in bf.names:
- other = bf.names[bit.bitname]
- if (
- isinstance(other, Bit)
- and other.cat == bit.cat
- and bit.cat == BitCat.SUBFIELD
- ):
- return
- raise ValueError(
- f"{bf.typname}: bit name {bit.bitname!r} already assigned"
- )
- bf.names[bit.bitname] = bit
+ check_name(name, isinstance(bit.cat, BitNum))
+ bf.names.add(bit.bitname)
+ elif m := re.fullmatch(re_bitspec_mask, spec):
+ mask = BitAlias(m.group("name"), parse_expr(env, m.group("val")))
+ mask.in_versions.add(ver)
+ check_name(mask.bitname)
+ bf.masks[mask.bitname] = mask
+ bf.names.add(mask.bitname)
elif m := re.fullmatch(re_bitspec_alias, spec):
- alias = BitAlias(m.group("name"), m.group("val"))
+ alias = BitAlias(m.group("name"), parse_expr(env, m.group("val")))
alias.in_versions.add(ver)
- if alias.bitname in bf.names:
+ check_name(alias.bitname)
+ bf.aliases[alias.bitname] = alias
+ bf.names.add(alias.bitname)
+ elif m := re.fullmatch(re_bitspec_num, spec):
+ numname = m.group("num")
+ alias = BitAlias(m.group("name"), parse_expr(env, m.group("val")))
+ alias.in_versions.add(ver)
+ check_name(alias.bitname)
+ if numname not in bf.nums:
+ raise NameError(
+ f"{bf.typname}: nested num not allocated any bits: {numname!r}"
+ )
+ assert alias.val.const is not None
+ if alias.val.const & ~bf.nums[numname].mask:
raise ValueError(
- f"{bf.typname}: bit name {alias.bitname!r} already assigned"
+ f"{bf.typname}: {alias.bitname!r} does not fit within bitmask: val={alias.val.const:b} mask={bf.nums[numname].mask}"
)
- bf.names[alias.bitname] = alias
+ bf.nums[numname].vals[alias.bitname] = alias
+ bf.names.add(alias.bitname)
else:
raise SyntaxError(f"invalid bitfield spec {spec!r}")
-def parse_expr(expr: str) -> Expr:
- assert re.fullmatch(re_expr, expr)
- ret = Expr()
- for tok in re.split("([-+])", expr):
- if tok in ("-", "+"):
- # I, for the life of me, do not understand why I need this
- # typing.cast() to keep mypy happy.
- ret.tokens += [ExprOp(typing.cast(typing.Literal["-", "+"], tok))]
- elif re.fullmatch("[0-9]+", tok):
- ret.tokens += [ExprLit(int(tok))]
- else:
- ret.tokens += [ExprSym(tok)]
- return ret
+# struct members #######################
+
+
+re_memberspec = f"(?:(?P<cnt>{re_symname}|[1-9][0-9]*)\\*\\()?(?P<name>{re_symname})\\[(?P<typ>{re_memtype})(?:,max=(?P<max>{re_expr})|,val=(?P<val>{re_expr}))*\\]\\)?"
def parse_members(ver: str, env: dict[str, Type], struct: Struct, specs: str) -> None:
@@ -401,29 +602,44 @@ def parse_members(ver: str, env: dict[str, Type], struct: Struct, specs: str) ->
member.typ = env[m.group("typ")]
if cnt := m.group("cnt"):
- if len(struct.members) == 0 or struct.members[-1].membname != cnt:
- raise ValueError(f"list count must be previous item: {cnt!r}")
- cnt_mem = struct.members[-1]
- member.cnt = cnt_mem
- _ = member.max_cnt # force validation
+ if cnt.isnumeric():
+ member.cnt = int(cnt)
+ else:
+ if len(struct.members) == 0 or struct.members[-1].membname != cnt:
+ raise ValueError(f"list count must be previous item: {cnt!r}")
+ member.cnt = struct.members[-1]
+ _ = member.max_cnt # force validation
if maxstr := m.group("max"):
- if (not isinstance(member.typ, Primitive)) or member.cnt:
- raise ValueError("',max=' may only be specified on a non-repeated atom")
- member.max = parse_expr(maxstr)
+ if (
+ not isinstance(member.typ, Primitive)
+ and not isinstance(member.typ, Number)
+ ) or member.cnt:
+ raise ValueError(
+ "',max=' may only be specified on a non-repeated numeric type"
+ )
+ member.max = parse_expr(env, maxstr)
else:
- member.max = Expr()
+ member.max = Expr(env)
if valstr := m.group("val"):
- if (not isinstance(member.typ, Primitive)) or member.cnt:
- raise ValueError("',val=' may only be specified on a non-repeated atom")
- member.val = parse_expr(valstr)
+ if (
+ not isinstance(member.typ, Primitive)
+ and not isinstance(member.typ, Number)
+ ) or member.cnt:
+ raise ValueError(
+ "',val=' may only be specified on a non-repeated numeric type"
+ )
+ member.val = parse_expr(env, valstr)
else:
- member.val = Expr()
+ member.val = Expr(env)
struct.members += [member]
+# main parser ##########################
+
+
def re_string(grpname: str) -> str:
return f'"(?P<{grpname}>[^"]*)"'
@@ -455,15 +671,6 @@ def parse_file(
"8": Primitive.u64,
}
- def get_type(name: str, tc: type[T]) -> T:
- nonlocal env
- if name not in env:
- raise NameError(f"Unknown type {name!r}")
- ret = env[name]
- if (not isinstance(ret, tc)) or (ret.__class__.__name__ != tc.__name__):
- raise NameError(f"Type {ret.typname!r} is not a {tc.__name__}")
- return ret
-
with open(filename, "r", encoding="utf-8") as fh:
prev: Type | None = None
for lineno, line in enumerate(fh):
@@ -494,12 +701,19 @@ def parse_file(
typ.in_versions.add(version)
case Bitfield():
typ.in_versions.add(version)
- for bit in typ.bits:
- if other_version in bit.in_versions:
- bit.in_versions.add(version)
- for val in typ.names.values():
- if other_version in val.in_versions:
- val.in_versions.add(version)
+ for bf_bit in typ.bits:
+ if other_version in bf_bit.in_versions:
+ bf_bit.in_versions.add(version)
+ for bf_num in typ.nums.values():
+ for bf_val in bf_num.vals.values():
+ if other_version in bf_val.in_versions:
+ bf_val.in_versions.add(version)
+ for bf_mask in typ.masks.values():
+ if other_version in bf_mask.in_versions:
+ bf_mask.in_versions.add(version)
+ for bf_alias in typ.aliases.values():
+ if other_version in bf_alias.in_versions:
+ bf_alias.in_versions.add(version)
case Struct(): # and Message()
typ.in_versions.add(version)
for member in typ.members:
@@ -539,8 +753,8 @@ def parse_file(
env[bf.typname] = bf
prev = bf
elif m := re.fullmatch(re_line_bitfield_, line):
- bf = get_type(m.group("name"), Bitfield)
- parse_bitspec(version, bf, m.group("member"))
+ bf = get_type(env, m.group("name"), Bitfield)
+ parse_bitspec(env, version, bf, m.group("member"))
prev = bf
elif m := re.fullmatch(re_line_struct, line):
@@ -559,7 +773,7 @@ def parse_file(
env[struct.typname] = struct
prev = struct
case "+=":
- struct = get_type(m.group("name"), Struct)
+ struct = get_type(env, m.group("name"), Struct)
parse_members(version, env, struct, m.group("members"))
prev = struct
@@ -577,16 +791,16 @@ def parse_file(
env[msg.typname] = msg
prev = msg
case "+=":
- msg = get_type(m.group("name"), Message)
+ msg = get_type(env, m.group("name"), Message)
parse_members(version, env, msg, m.group("members"))
prev = msg
elif m := re.fullmatch(re_line_cont, line):
match prev:
case Bitfield():
- parse_bitspec(version, prev, m.group("specs"))
+ parse_bitspec(env, version, prev, m.group("specs"))
case Number():
- parse_numspec(version, prev, m.group("specs"))
+ parse_numspec(env, version, prev, m.group("specs"))
case Struct(): # and Message()
parse_members(version, env, prev, m.group("specs"))
case _:
@@ -607,12 +821,6 @@ def parse_file(
typs: list[UserType] = [x for x in env.values() if not isinstance(x, Primitive)]
for typ in [typ for typ in typs if isinstance(typ, Struct)]:
- valid_syms = [
- "end",
- "s32_max",
- "s64_max",
- *["&" + m.membname for m in typ.members],
- ]
for member in typ.members:
if (
not isinstance(member.typ, Primitive)
@@ -622,9 +830,11 @@ def parse_file(
f"{typ.typname}.{member.membname}: type {member.typ.typname} does not exist in {member.in_versions.difference(member.typ.in_versions)}"
)
for tok in [*member.max.tokens, *member.val.tokens]:
- if isinstance(tok, ExprSym) and tok.symname not in valid_syms:
- raise ValueError(
- f"{typ.typname}.{member.membname}: invalid sym: {tok.symname}"
+ if isinstance(tok, ExprOff) and not any(
+ m.membname == tok.membname for m in typ.members
+ ):
+ raise NameError(
+ f"{typ.typname}.{member.membname}: invalid offset: &{tok.membname}"
)
return version, typs
diff --git a/lib9p/include/lib9p/9p.generated.h b/lib9p/include/lib9p/9p.generated.h
index 725e781..7e901a3 100644
--- a/lib9p/include/lib9p/9p.generated.h
+++ b/lib9p/include/lib9p/9p.generated.h
@@ -1,4 +1,4 @@
-/* Generated by `lib9p/idl.gen lib9p/idl/2002-9P2000.9p lib9p/idl/2003-9P2000.p9p.9p lib9p/idl/2005-9P2000.u.9p lib9p/idl/2010-9P2000.L.9p lib9p/idl/2012-9P2000.e.9p`. DO NOT EDIT! */
+/* Generated by `lib9p/proto.gen lib9p/idl/2002-9P2000.9p lib9p/idl/2003-9P2000.p9p.9p lib9p/idl/2005-9P2000.u.9p lib9p/idl/2010-9P2000.L.9p lib9p/idl/2012-9P2000.e.9p`. DO NOT EDIT! */
#ifndef _LIB9P_9P_H_
#error Do not include <lib9p/9p.generated.h> directly; include <lib9p/9p.h> instead
@@ -6,6 +6,7 @@
#include <stdint.h> /* for uint{n}_t types */
+#include <libfmt/fmt.h> /* for fmt_formatter */
#include <libhw/generic/net.h> /* for struct iovec */
/* config *********************************************************************/
@@ -60,6 +61,7 @@ enum lib9p_version {
#endif /* CONFIG_9P_ENABLE_9P2000_u */
LIB9P_VER_NUM,
};
+LO_IMPLEMENTATION_H(fmt_formatter, enum lib9p_version, lib9p_version);
/* enum msg_type **************************************************************/
@@ -153,386 +155,408 @@ enum lib9p_msg_type { /* uint8_t */
LIB9P_TYP_Rswrite = 155,
#endif /* CONFIG_9P_ENABLE_9P2000_e */
};
+LO_IMPLEMENTATION_H(fmt_formatter, enum lib9p_msg_type, lib9p_msg_type);
/* payload types **************************************************************/
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
/* size = 2 ; max_iov = 1 ; max_copy = 2 */
typedef uint16_t lib9p_tag_t;
-#define LIB9P_TAG_NOTAG ((lib9p_tag_t)UINT16_C(~0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_tag_t, lib9p_tag);
+#define LIB9P_TAG_NOTAG ((lib9p_tag_t)(UINT16_MAX))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_fid_t;
-#define LIB9P_FID_NOFID ((lib9p_fid_t)UINT32_C(~0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_fid_t, lib9p_fid);
+#define LIB9P_FID_NOFID ((lib9p_fid_t)(UINT32_MAX))
/* min_size = 2 ; exp_size = 29 ; max_size = 65,537 ; max_iov = 2 ; max_copy = 2 */
struct lib9p_s {
uint16_t len;
[[gnu::nonstring]] char *utf8;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_s, lib9p_s);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_dm_t;
-
-#define LIB9P_DM_DIR ((lib9p_dm_t)(1<<31))
-#define LIB9P_DM_APPEND ((lib9p_dm_t)(1<<30))
-#define LIB9P_DM_EXCL ((lib9p_dm_t)(1<<29))
-#define _LIB9P_DM_RESERVED_PLAN9_MOUNT ((lib9p_dm_t)(1<<28))
-#define LIB9P_DM_AUTH ((lib9p_dm_t)(1<<27))
-#define LIB9P_DM_TMP ((lib9p_dm_t)(1<<26))
-/* unused ((lib9p_dm_t)(1<<25)) */
-/* unused ((lib9p_dm_t)(1<<24)) */
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_dm_t, lib9p_dm);
+/* bits */
+#define LIB9P_DM_DIR ((lib9p_dm_t)(UINT32_C(1)<<31))
+#define LIB9P_DM_APPEND ((lib9p_dm_t)(UINT32_C(1)<<30))
+#define LIB9P_DM_EXCL ((lib9p_dm_t)(UINT32_C(1)<<29))
+#define _LIB9P_DM_PLAN9_MOUNT ((lib9p_dm_t)(UINT32_C(1)<<28))
+#define LIB9P_DM_AUTH ((lib9p_dm_t)(UINT32_C(1)<<27))
+#define LIB9P_DM_TMP ((lib9p_dm_t)(UINT32_C(1)<<26))
+#define _LIB9P_DM_UNUSED_25 ((lib9p_dm_t)(UINT32_C(1)<<25))
+#define _LIB9P_DM_UNUSED_24 ((lib9p_dm_t)(UINT32_C(1)<<24))
#if CONFIG_9P_ENABLE_9P2000_u
-# define LIB9P_DM_DEVICE ((lib9p_dm_t)(1<<23))
+# define LIB9P_DM_DEVICE ((lib9p_dm_t)(UINT32_C(1)<<23))
#endif /* CONFIG_9P_ENABLE_9P2000_u */
-/* unused ((lib9p_dm_t)(1<<22)) */
+#define _LIB9P_DM_UNUSED_22 ((lib9p_dm_t)(UINT32_C(1)<<22))
#if CONFIG_9P_ENABLE_9P2000_u
-# define LIB9P_DM_NAMEDPIPE ((lib9p_dm_t)(1<<21))
-# define LIB9P_DM_SOCKET ((lib9p_dm_t)(1<<20))
-# define LIB9P_DM_SETUID ((lib9p_dm_t)(1<<19))
-# define LIB9P_DM_SETGID ((lib9p_dm_t)(1<<18))
+# define LIB9P_DM_PIPE ((lib9p_dm_t)(UINT32_C(1)<<21))
+# define LIB9P_DM_SOCKET ((lib9p_dm_t)(UINT32_C(1)<<20))
+# define LIB9P_DM_SETUID ((lib9p_dm_t)(UINT32_C(1)<<19))
+# define LIB9P_DM_SETGID ((lib9p_dm_t)(UINT32_C(1)<<18))
#endif /* CONFIG_9P_ENABLE_9P2000_u */
-/* unused ((lib9p_dm_t)(1<<17)) */
-/* unused ((lib9p_dm_t)(1<<16)) */
-/* unused ((lib9p_dm_t)(1<<15)) */
-/* unused ((lib9p_dm_t)(1<<14)) */
-/* unused ((lib9p_dm_t)(1<<13)) */
-/* unused ((lib9p_dm_t)(1<<12)) */
-/* unused ((lib9p_dm_t)(1<<11)) */
-/* unused ((lib9p_dm_t)(1<<10)) */
-/* unused ((lib9p_dm_t)(1<<9)) */
-#define LIB9P_DM_OWNER_R ((lib9p_dm_t)(1<<8))
-#define LIB9P_DM_OWNER_W ((lib9p_dm_t)(1<<7))
-#define LIB9P_DM_OWNER_X ((lib9p_dm_t)(1<<6))
-#define LIB9P_DM_GROUP_R ((lib9p_dm_t)(1<<5))
-#define LIB9P_DM_GROUP_W ((lib9p_dm_t)(1<<4))
-#define LIB9P_DM_GROUP_X ((lib9p_dm_t)(1<<3))
-#define LIB9P_DM_OTHER_R ((lib9p_dm_t)(1<<2))
-#define LIB9P_DM_OTHER_W ((lib9p_dm_t)(1<<1))
-#define LIB9P_DM_OTHER_X ((lib9p_dm_t)(1<<0))
-
-#define LIB9P_DM_PERM_MASK ((lib9p_dm_t)(0777))
+#define _LIB9P_DM_UNUSED_17 ((lib9p_dm_t)(UINT32_C(1)<<17))
+#define _LIB9P_DM_UNUSED_16 ((lib9p_dm_t)(UINT32_C(1)<<16))
+#define _LIB9P_DM_UNUSED_15 ((lib9p_dm_t)(UINT32_C(1)<<15))
+#define _LIB9P_DM_UNUSED_14 ((lib9p_dm_t)(UINT32_C(1)<<14))
+#define _LIB9P_DM_UNUSED_13 ((lib9p_dm_t)(UINT32_C(1)<<13))
+#define _LIB9P_DM_UNUSED_12 ((lib9p_dm_t)(UINT32_C(1)<<12))
+#define _LIB9P_DM_UNUSED_11 ((lib9p_dm_t)(UINT32_C(1)<<11))
+#define _LIB9P_DM_UNUSED_10 ((lib9p_dm_t)(UINT32_C(1)<<10))
+#define _LIB9P_DM_UNUSED_9 ((lib9p_dm_t)(UINT32_C(1)<<9))
+#define LIB9P_DM_OWNER_R ((lib9p_dm_t)(UINT32_C(1)<<8))
+#define LIB9P_DM_OWNER_W ((lib9p_dm_t)(UINT32_C(1)<<7))
+#define LIB9P_DM_OWNER_X ((lib9p_dm_t)(UINT32_C(1)<<6))
+#define LIB9P_DM_GROUP_R ((lib9p_dm_t)(UINT32_C(1)<<5))
+#define LIB9P_DM_GROUP_W ((lib9p_dm_t)(UINT32_C(1)<<4))
+#define LIB9P_DM_GROUP_X ((lib9p_dm_t)(UINT32_C(1)<<3))
+#define LIB9P_DM_OTHER_R ((lib9p_dm_t)(UINT32_C(1)<<2))
+#define LIB9P_DM_OTHER_W ((lib9p_dm_t)(UINT32_C(1)<<1))
+#define LIB9P_DM_OTHER_X ((lib9p_dm_t)(UINT32_C(1)<<0))
+/* masks */
+#define LIB9P_DM_PERM_MASK ((lib9p_dm_t)(0b000000000000000000000111111111))
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
/* size = 1 ; max_iov = 1 ; max_copy = 1 */
typedef uint8_t lib9p_qt_t;
-
-#define LIB9P_QT_DIR ((lib9p_qt_t)(1<<7))
-#define LIB9P_QT_APPEND ((lib9p_qt_t)(1<<6))
-#define LIB9P_QT_EXCL ((lib9p_qt_t)(1<<5))
-#define _LIB9P_QT_RESERVED_PLAN9_MOUNT ((lib9p_qt_t)(1<<4))
-#define LIB9P_QT_AUTH ((lib9p_qt_t)(1<<3))
-#define LIB9P_QT_TMP ((lib9p_qt_t)(1<<2))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_qt_t, lib9p_qt);
+/* bits */
+#define LIB9P_QT_DIR ((lib9p_qt_t)(UINT8_C(1)<<7))
+#define LIB9P_QT_APPEND ((lib9p_qt_t)(UINT8_C(1)<<6))
+#define LIB9P_QT_EXCL ((lib9p_qt_t)(UINT8_C(1)<<5))
+#define _LIB9P_QT_PLAN9_MOUNT ((lib9p_qt_t)(UINT8_C(1)<<4))
+#define LIB9P_QT_AUTH ((lib9p_qt_t)(UINT8_C(1)<<3))
+#define LIB9P_QT_TMP ((lib9p_qt_t)(UINT8_C(1)<<2))
#if CONFIG_9P_ENABLE_9P2000_u
-# define LIB9P_QT_SYMLINK ((lib9p_qt_t)(1<<1))
+# define LIB9P_QT_SYMLINK ((lib9p_qt_t)(UINT8_C(1)<<1))
#endif /* CONFIG_9P_ENABLE_9P2000_u */
-/* unused ((lib9p_qt_t)(1<<0)) */
-
-#define LIB9P_QT_FILE ((lib9p_qt_t)(0))
+#define _LIB9P_QT_UNUSED_0 ((lib9p_qt_t)(UINT8_C(1)<<0))
+/* aliases */
+#define LIB9P_QT_FILE ((lib9p_qt_t)(0))
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_nuid_t;
-#define LIB9P_NUID_NONUID ((lib9p_nuid_t)UINT32_C(~0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_nuid_t, lib9p_nuid);
+#define LIB9P_NUID_NONUID ((lib9p_nuid_t)(UINT32_MAX))
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
/* size = 1 ; max_iov = 1 ; max_copy = 1 */
typedef uint8_t lib9p_o_t;
-
-/* unused ((lib9p_o_t)(1<<7)) */
-#define LIB9P_O_RCLOSE ((lib9p_o_t)(1<<6))
-#define _LIB9P_O_RESERVED_CEXEC ((lib9p_o_t)(1<<5))
-#define LIB9P_O_TRUNC ((lib9p_o_t)(1<<4))
-/* unused ((lib9p_o_t)(1<<3)) */
-/* unused ((lib9p_o_t)(1<<2)) */
-#define _LIB9P_O_mode_1 ((lib9p_o_t)(1<<1))
-#define _LIB9P_O_mode_0 ((lib9p_o_t)(1<<0))
-
-#define LIB9P_O_READ ((lib9p_o_t)(0))
-#define LIB9P_O_WRITE ((lib9p_o_t)(1))
-#define LIB9P_O_RDWR ((lib9p_o_t)(2))
-#define LIB9P_O_EXEC ((lib9p_o_t)(3))
-#define LIB9P_O_MODE_MASK ((lib9p_o_t)(0b00000011))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_o_t, lib9p_o);
+/* bits */
+#define _LIB9P_O_UNUSED_7 ((lib9p_o_t)(UINT8_C(1)<<7))
+#define LIB9P_O_RCLOSE ((lib9p_o_t)(UINT8_C(1)<<6))
+#define _LIB9P_O_RESERVED_CEXEC ((lib9p_o_t)(UINT8_C(1)<<5))
+#define LIB9P_O_TRUNC ((lib9p_o_t)(UINT8_C(1)<<4))
+#define _LIB9P_O_UNUSED_3 ((lib9p_o_t)(UINT8_C(1)<<3))
+#define _LIB9P_O_UNUSED_2 ((lib9p_o_t)(UINT8_C(1)<<2))
+/* number LIB9P_O_MODE_* ((lib9p_o_t)(UINT8_C(1)<<1)) */
+/* number LIB9P_O_MODE_* ((lib9p_o_t)(UINT8_C(1)<<0)) */
+/* masks */
#define LIB9P_O_FLAG_MASK ((lib9p_o_t)(0b11111100))
+/* number: MODE */
+#define LIB9P_O_MODE_READ ((lib9p_o_t)(0))
+#define LIB9P_O_MODE_WRITE ((lib9p_o_t)(1))
+#define LIB9P_O_MODE_RDWR ((lib9p_o_t)(2))
+#define LIB9P_O_MODE_EXEC ((lib9p_o_t)(3))
+#define LIB9P_O_MODE_MASK ((lib9p_o_t)(0b000011))
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_errno_t;
-#define LIB9P_ERRNO_NOERROR ((lib9p_errno_t)UINT32_C(0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_errno_t, lib9p_errno);
+#define LIB9P_ERRNO_NOERROR ((lib9p_errno_t)(0))
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_super_magic_t;
-#define LIB9P_SUPER_MAGIC_V9FS_MAGIC ((lib9p_super_magic_t)UINT32_C(0x01021997))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_super_magic_t, lib9p_super_magic);
+#define LIB9P_SUPER_MAGIC_V9FS_MAGIC ((lib9p_super_magic_t)(16914839))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_lo_t;
-
-/* unused ((lib9p_lo_t)(1<<31)) */
-/* unused ((lib9p_lo_t)(1<<30)) */
-/* unused ((lib9p_lo_t)(1<<29)) */
-/* unused ((lib9p_lo_t)(1<<28)) */
-/* unused ((lib9p_lo_t)(1<<27)) */
-/* unused ((lib9p_lo_t)(1<<26)) */
-/* unused ((lib9p_lo_t)(1<<25)) */
-/* unused ((lib9p_lo_t)(1<<24)) */
-/* unused ((lib9p_lo_t)(1<<23)) */
-/* unused ((lib9p_lo_t)(1<<22)) */
-/* unused ((lib9p_lo_t)(1<<21)) */
-#define LIB9P_LO_SYNC ((lib9p_lo_t)(1<<20))
-#define LIB9P_LO_CLOEXEC ((lib9p_lo_t)(1<<19))
-#define LIB9P_LO_NOATIME ((lib9p_lo_t)(1<<18))
-#define LIB9P_LO_NOFOLLOW ((lib9p_lo_t)(1<<17))
-#define LIB9P_LO_DIRECTORY ((lib9p_lo_t)(1<<16))
-#define LIB9P_LO_LARGEFILE ((lib9p_lo_t)(1<<15))
-#define LIB9P_LO_DIRECT ((lib9p_lo_t)(1<<14))
-#define LIB9P_LO_BSD_FASYNC ((lib9p_lo_t)(1<<13))
-#define LIB9P_LO_DSYNC ((lib9p_lo_t)(1<<12))
-#define LIB9P_LO_NONBLOCK ((lib9p_lo_t)(1<<11))
-#define LIB9P_LO_APPEND ((lib9p_lo_t)(1<<10))
-#define LIB9P_LO_TRUNC ((lib9p_lo_t)(1<<9))
-#define LIB9P_LO_NOCTTY ((lib9p_lo_t)(1<<8))
-#define LIB9P_LO_EXCL ((lib9p_lo_t)(1<<7))
-#define LIB9P_LO_CREATE ((lib9p_lo_t)(1<<6))
-/* unused ((lib9p_lo_t)(1<<5)) */
-/* unused ((lib9p_lo_t)(1<<4)) */
-/* unused ((lib9p_lo_t)(1<<3)) */
-/* unused ((lib9p_lo_t)(1<<2)) */
-#define _LIB9P_LO_mode_1 ((lib9p_lo_t)(1<<1))
-#define _LIB9P_LO_mode_0 ((lib9p_lo_t)(1<<0))
-
-#define LIB9P_LO_RDONLY ((lib9p_lo_t)(0))
-#define LIB9P_LO_WRONLY ((lib9p_lo_t)(1))
-#define LIB9P_LO_RDWR ((lib9p_lo_t)(2))
-#define LIB9P_LO_NOACCESS ((lib9p_lo_t)(3))
-#define LIB9P_LO_MODE_MASK ((lib9p_lo_t)(0b000000000000000000011))
-#define LIB9P_LO_FLAG_MASK ((lib9p_lo_t)(0b111111111111111000000))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_lo_t, lib9p_lo);
+/* bits */
+#define _LIB9P_LO_UNUSED_31 ((lib9p_lo_t)(UINT32_C(1)<<31))
+#define _LIB9P_LO_UNUSED_30 ((lib9p_lo_t)(UINT32_C(1)<<30))
+#define _LIB9P_LO_UNUSED_29 ((lib9p_lo_t)(UINT32_C(1)<<29))
+#define _LIB9P_LO_UNUSED_28 ((lib9p_lo_t)(UINT32_C(1)<<28))
+#define _LIB9P_LO_UNUSED_27 ((lib9p_lo_t)(UINT32_C(1)<<27))
+#define _LIB9P_LO_UNUSED_26 ((lib9p_lo_t)(UINT32_C(1)<<26))
+#define _LIB9P_LO_UNUSED_25 ((lib9p_lo_t)(UINT32_C(1)<<25))
+#define _LIB9P_LO_UNUSED_24 ((lib9p_lo_t)(UINT32_C(1)<<24))
+#define _LIB9P_LO_UNUSED_23 ((lib9p_lo_t)(UINT32_C(1)<<23))
+#define _LIB9P_LO_UNUSED_22 ((lib9p_lo_t)(UINT32_C(1)<<22))
+#define _LIB9P_LO_UNUSED_21 ((lib9p_lo_t)(UINT32_C(1)<<21))
+#define LIB9P_LO_SYNC ((lib9p_lo_t)(UINT32_C(1)<<20))
+#define LIB9P_LO_CLOEXEC ((lib9p_lo_t)(UINT32_C(1)<<19))
+#define LIB9P_LO_NOATIME ((lib9p_lo_t)(UINT32_C(1)<<18))
+#define LIB9P_LO_NOFOLLOW ((lib9p_lo_t)(UINT32_C(1)<<17))
+#define LIB9P_LO_DIRECTORY ((lib9p_lo_t)(UINT32_C(1)<<16))
+#define LIB9P_LO_LARGEFILE ((lib9p_lo_t)(UINT32_C(1)<<15))
+#define LIB9P_LO_DIRECT ((lib9p_lo_t)(UINT32_C(1)<<14))
+#define LIB9P_LO_BSD_FASYNC ((lib9p_lo_t)(UINT32_C(1)<<13))
+#define LIB9P_LO_DSYNC ((lib9p_lo_t)(UINT32_C(1)<<12))
+#define LIB9P_LO_NONBLOCK ((lib9p_lo_t)(UINT32_C(1)<<11))
+#define LIB9P_LO_APPEND ((lib9p_lo_t)(UINT32_C(1)<<10))
+#define LIB9P_LO_TRUNC ((lib9p_lo_t)(UINT32_C(1)<<9))
+#define LIB9P_LO_NOCTTY ((lib9p_lo_t)(UINT32_C(1)<<8))
+#define LIB9P_LO_EXCL ((lib9p_lo_t)(UINT32_C(1)<<7))
+#define LIB9P_LO_CREATE ((lib9p_lo_t)(UINT32_C(1)<<6))
+#define _LIB9P_LO_UNUSED_5 ((lib9p_lo_t)(UINT32_C(1)<<5))
+#define _LIB9P_LO_UNUSED_4 ((lib9p_lo_t)(UINT32_C(1)<<4))
+#define _LIB9P_LO_UNUSED_3 ((lib9p_lo_t)(UINT32_C(1)<<3))
+#define _LIB9P_LO_UNUSED_2 ((lib9p_lo_t)(UINT32_C(1)<<2))
+/* number LIB9P_LO_MODE_* ((lib9p_lo_t)(UINT32_C(1)<<1)) */
+/* number LIB9P_LO_MODE_* ((lib9p_lo_t)(UINT32_C(1)<<0)) */
+/* masks */
+#define LIB9P_LO_FLAG_MASK ((lib9p_lo_t)(0b000000000111111111111111000000))
+/* number: MODE */
+#define LIB9P_LO_MODE_RDONLY ((lib9p_lo_t)(0))
+#define LIB9P_LO_MODE_WRONLY ((lib9p_lo_t)(1))
+#define LIB9P_LO_MODE_RDWR ((lib9p_lo_t)(2))
+#define LIB9P_LO_MODE_NOACCESS ((lib9p_lo_t)(3))
+#define LIB9P_LO_MODE_MASK ((lib9p_lo_t)(0b000000000000000000000000000011))
/* size = 1 ; max_iov = 1 ; max_copy = 1 */
typedef uint8_t lib9p_dt_t;
-#define LIB9P_DT_UNKNOWN ((lib9p_dt_t)UINT8_C(0))
-#define LIB9P_DT_NAMED_PIPE ((lib9p_dt_t)UINT8_C(1))
-#define LIB9P_DT_CHAR_DEV ((lib9p_dt_t)UINT8_C(2))
-#define LIB9P_DT_DIRECTORY ((lib9p_dt_t)UINT8_C(4))
-#define LIB9P_DT_BLOCK_DEV ((lib9p_dt_t)UINT8_C(6))
-#define LIB9P_DT_REGULAR ((lib9p_dt_t)UINT8_C(8))
-#define LIB9P_DT_SYMLINK ((lib9p_dt_t)UINT8_C(10))
-#define LIB9P_DT_SOCKET ((lib9p_dt_t)UINT8_C(12))
-#define LIB9P_DT_WHITEOUT ((lib9p_dt_t)UINT8_C(14))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_dt_t, lib9p_dt);
+#define LIB9P_DT_UNKNOWN ((lib9p_dt_t)(0))
+#define LIB9P_DT_PIPE ((lib9p_dt_t)(1))
+#define LIB9P_DT_CHAR_DEV ((lib9p_dt_t)(2))
+#define LIB9P_DT_DIRECTORY ((lib9p_dt_t)(4))
+#define LIB9P_DT_BLOCK_DEV ((lib9p_dt_t)(6))
+#define LIB9P_DT_REGULAR ((lib9p_dt_t)(8))
+#define LIB9P_DT_SYMLINK ((lib9p_dt_t)(10))
+#define LIB9P_DT_SOCKET ((lib9p_dt_t)(12))
+#define _LIB9P_DT_WHITEOUT ((lib9p_dt_t)(14))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_mode_t;
-
-/* unused ((lib9p_mode_t)(1<<31)) */
-/* unused ((lib9p_mode_t)(1<<30)) */
-/* unused ((lib9p_mode_t)(1<<29)) */
-/* unused ((lib9p_mode_t)(1<<28)) */
-/* unused ((lib9p_mode_t)(1<<27)) */
-/* unused ((lib9p_mode_t)(1<<26)) */
-/* unused ((lib9p_mode_t)(1<<25)) */
-/* unused ((lib9p_mode_t)(1<<24)) */
-/* unused ((lib9p_mode_t)(1<<23)) */
-/* unused ((lib9p_mode_t)(1<<22)) */
-/* unused ((lib9p_mode_t)(1<<21)) */
-/* unused ((lib9p_mode_t)(1<<20)) */
-/* unused ((lib9p_mode_t)(1<<19)) */
-/* unused ((lib9p_mode_t)(1<<18)) */
-/* unused ((lib9p_mode_t)(1<<17)) */
-/* unused ((lib9p_mode_t)(1<<16)) */
-#define _LIB9P_MODE_fmt_3 ((lib9p_mode_t)(1<<15))
-#define _LIB9P_MODE_fmt_2 ((lib9p_mode_t)(1<<14))
-#define _LIB9P_MODE_fmt_1 ((lib9p_mode_t)(1<<13))
-#define _LIB9P_MODE_fmt_0 ((lib9p_mode_t)(1<<12))
-#define LIB9P_MODE_PERM_SETGROUP ((lib9p_mode_t)(1<<11))
-#define LIB9P_MODE_PERM_SETUSER ((lib9p_mode_t)(1<<10))
-#define LIB9P_MODE_PERM_STICKY ((lib9p_mode_t)(1<<9))
-#define LIB9P_MODE_PERM_OWNER_R ((lib9p_mode_t)(1<<8))
-#define LIB9P_MODE_PERM_OWNER_W ((lib9p_mode_t)(1<<7))
-#define LIB9P_MODE_PERM_OWNER_X ((lib9p_mode_t)(1<<6))
-#define LIB9P_MODE_PERM_GROUP_R ((lib9p_mode_t)(1<<5))
-#define LIB9P_MODE_PERM_GROUP_W ((lib9p_mode_t)(1<<4))
-#define LIB9P_MODE_PERM_GROUP_X ((lib9p_mode_t)(1<<3))
-#define LIB9P_MODE_PERM_OTHER_R ((lib9p_mode_t)(1<<2))
-#define LIB9P_MODE_PERM_OTHER_W ((lib9p_mode_t)(1<<1))
-#define LIB9P_MODE_PERM_OTHER_X ((lib9p_mode_t)(1<<0))
-
-#define LIB9P_MODE_FMT_NAMED_PIPE ((lib9p_mode_t)(LIB9P_DT_NAMED_PIPE<<12))
-#define LIB9P_MODE_FMT_CHAR_DEV ((lib9p_mode_t)(LIB9P_DT_CHAR_DEV<<12))
-#define LIB9P_MODE_FMT_DIRECTORY ((lib9p_mode_t)(LIB9P_DT_DIRECTORY<<12))
-#define LIB9P_MODE_FMT_BLOCK_DEV ((lib9p_mode_t)(LIB9P_DT_BLOCK_DEV<<12))
-#define LIB9P_MODE_FMT_REGULAR ((lib9p_mode_t)(LIB9P_DT_REGULAR<<12))
-#define LIB9P_MODE_FMT_SYMLINK ((lib9p_mode_t)(LIB9P_DT_SYMLINK<<12))
-#define LIB9P_MODE_FMT_SOCKET ((lib9p_mode_t)(LIB9P_DT_SOCKET<<12))
-#define LIB9P_MODE_PERM_MASK ((lib9p_mode_t)(0000777))
-#define LIB9P_MODE_FMT_MASK ((lib9p_mode_t)(0170000))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_mode_t, lib9p_mode);
+/* bits */
+#define _LIB9P_MODE_UNUSED_31 ((lib9p_mode_t)(UINT32_C(1)<<31))
+#define _LIB9P_MODE_UNUSED_30 ((lib9p_mode_t)(UINT32_C(1)<<30))
+#define _LIB9P_MODE_UNUSED_29 ((lib9p_mode_t)(UINT32_C(1)<<29))
+#define _LIB9P_MODE_UNUSED_28 ((lib9p_mode_t)(UINT32_C(1)<<28))
+#define _LIB9P_MODE_UNUSED_27 ((lib9p_mode_t)(UINT32_C(1)<<27))
+#define _LIB9P_MODE_UNUSED_26 ((lib9p_mode_t)(UINT32_C(1)<<26))
+#define _LIB9P_MODE_UNUSED_25 ((lib9p_mode_t)(UINT32_C(1)<<25))
+#define _LIB9P_MODE_UNUSED_24 ((lib9p_mode_t)(UINT32_C(1)<<24))
+#define _LIB9P_MODE_UNUSED_23 ((lib9p_mode_t)(UINT32_C(1)<<23))
+#define _LIB9P_MODE_UNUSED_22 ((lib9p_mode_t)(UINT32_C(1)<<22))
+#define _LIB9P_MODE_UNUSED_21 ((lib9p_mode_t)(UINT32_C(1)<<21))
+#define _LIB9P_MODE_UNUSED_20 ((lib9p_mode_t)(UINT32_C(1)<<20))
+#define _LIB9P_MODE_UNUSED_19 ((lib9p_mode_t)(UINT32_C(1)<<19))
+#define _LIB9P_MODE_UNUSED_18 ((lib9p_mode_t)(UINT32_C(1)<<18))
+#define _LIB9P_MODE_UNUSED_17 ((lib9p_mode_t)(UINT32_C(1)<<17))
+#define _LIB9P_MODE_UNUSED_16 ((lib9p_mode_t)(UINT32_C(1)<<16))
+/* number LIB9P_MODE_FMT_* ((lib9p_mode_t)(UINT32_C(1)<<15)) */
+/* number LIB9P_MODE_FMT_* ((lib9p_mode_t)(UINT32_C(1)<<14)) */
+/* number LIB9P_MODE_FMT_* ((lib9p_mode_t)(UINT32_C(1)<<13)) */
+/* number LIB9P_MODE_FMT_* ((lib9p_mode_t)(UINT32_C(1)<<12)) */
+#define LIB9P_MODE_PERM_SETGROUP ((lib9p_mode_t)(UINT32_C(1)<<11))
+#define LIB9P_MODE_PERM_SETUSER ((lib9p_mode_t)(UINT32_C(1)<<10))
+#define LIB9P_MODE_PERM_STICKY ((lib9p_mode_t)(UINT32_C(1)<<9))
+#define LIB9P_MODE_PERM_OWNER_R ((lib9p_mode_t)(UINT32_C(1)<<8))
+#define LIB9P_MODE_PERM_OWNER_W ((lib9p_mode_t)(UINT32_C(1)<<7))
+#define LIB9P_MODE_PERM_OWNER_X ((lib9p_mode_t)(UINT32_C(1)<<6))
+#define LIB9P_MODE_PERM_GROUP_R ((lib9p_mode_t)(UINT32_C(1)<<5))
+#define LIB9P_MODE_PERM_GROUP_W ((lib9p_mode_t)(UINT32_C(1)<<4))
+#define LIB9P_MODE_PERM_GROUP_X ((lib9p_mode_t)(UINT32_C(1)<<3))
+#define LIB9P_MODE_PERM_OTHER_R ((lib9p_mode_t)(UINT32_C(1)<<2))
+#define LIB9P_MODE_PERM_OTHER_W ((lib9p_mode_t)(UINT32_C(1)<<1))
+#define LIB9P_MODE_PERM_OTHER_X ((lib9p_mode_t)(UINT32_C(1)<<0))
+/* masks */
+#define LIB9P_MODE_PERM_MASK ((lib9p_mode_t)(0b000000000000000000111111111111))
+/* number: FMT */
+#define LIB9P_MODE_FMT_PIPE ((lib9p_mode_t)(LIB9P_DT_PIPE << 12))
+#define LIB9P_MODE_FMT_CHAR_DEV ((lib9p_mode_t)(LIB9P_DT_CHAR_DEV << 12))
+#define LIB9P_MODE_FMT_DIRECTORY ((lib9p_mode_t)(LIB9P_DT_DIRECTORY << 12))
+#define LIB9P_MODE_FMT_BLOCK_DEV ((lib9p_mode_t)(LIB9P_DT_BLOCK_DEV << 12))
+#define LIB9P_MODE_FMT_REGULAR ((lib9p_mode_t)(LIB9P_DT_REGULAR << 12))
+#define LIB9P_MODE_FMT_SYMLINK ((lib9p_mode_t)(LIB9P_DT_SYMLINK << 12))
+#define LIB9P_MODE_FMT_SOCKET ((lib9p_mode_t)(LIB9P_DT_SOCKET << 12))
+#define LIB9P_MODE_FMT_MASK ((lib9p_mode_t)(0b000000000000001111000000000000))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_b4_t;
-#define LIB9P_B4_FALSE ((lib9p_b4_t)UINT32_C(0))
-#define LIB9P_B4_TRUE ((lib9p_b4_t)UINT32_C(1))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_b4_t, lib9p_b4);
+#define LIB9P_B4_FALSE ((lib9p_b4_t)(0))
+#define LIB9P_B4_TRUE ((lib9p_b4_t)(1))
/* size = 8 ; max_iov = 1 ; max_copy = 8 */
typedef uint64_t lib9p_getattr_t;
-
-/* unused ((lib9p_getattr_t)(1<<63)) */
-/* unused ((lib9p_getattr_t)(1<<62)) */
-/* unused ((lib9p_getattr_t)(1<<61)) */
-/* unused ((lib9p_getattr_t)(1<<60)) */
-/* unused ((lib9p_getattr_t)(1<<59)) */
-/* unused ((lib9p_getattr_t)(1<<58)) */
-/* unused ((lib9p_getattr_t)(1<<57)) */
-/* unused ((lib9p_getattr_t)(1<<56)) */
-/* unused ((lib9p_getattr_t)(1<<55)) */
-/* unused ((lib9p_getattr_t)(1<<54)) */
-/* unused ((lib9p_getattr_t)(1<<53)) */
-/* unused ((lib9p_getattr_t)(1<<52)) */
-/* unused ((lib9p_getattr_t)(1<<51)) */
-/* unused ((lib9p_getattr_t)(1<<50)) */
-/* unused ((lib9p_getattr_t)(1<<49)) */
-/* unused ((lib9p_getattr_t)(1<<48)) */
-/* unused ((lib9p_getattr_t)(1<<47)) */
-/* unused ((lib9p_getattr_t)(1<<46)) */
-/* unused ((lib9p_getattr_t)(1<<45)) */
-/* unused ((lib9p_getattr_t)(1<<44)) */
-/* unused ((lib9p_getattr_t)(1<<43)) */
-/* unused ((lib9p_getattr_t)(1<<42)) */
-/* unused ((lib9p_getattr_t)(1<<41)) */
-/* unused ((lib9p_getattr_t)(1<<40)) */
-/* unused ((lib9p_getattr_t)(1<<39)) */
-/* unused ((lib9p_getattr_t)(1<<38)) */
-/* unused ((lib9p_getattr_t)(1<<37)) */
-/* unused ((lib9p_getattr_t)(1<<36)) */
-/* unused ((lib9p_getattr_t)(1<<35)) */
-/* unused ((lib9p_getattr_t)(1<<34)) */
-/* unused ((lib9p_getattr_t)(1<<33)) */
-/* unused ((lib9p_getattr_t)(1<<32)) */
-/* unused ((lib9p_getattr_t)(1<<31)) */
-/* unused ((lib9p_getattr_t)(1<<30)) */
-/* unused ((lib9p_getattr_t)(1<<29)) */
-/* unused ((lib9p_getattr_t)(1<<28)) */
-/* unused ((lib9p_getattr_t)(1<<27)) */
-/* unused ((lib9p_getattr_t)(1<<26)) */
-/* unused ((lib9p_getattr_t)(1<<25)) */
-/* unused ((lib9p_getattr_t)(1<<24)) */
-/* unused ((lib9p_getattr_t)(1<<23)) */
-/* unused ((lib9p_getattr_t)(1<<22)) */
-/* unused ((lib9p_getattr_t)(1<<21)) */
-/* unused ((lib9p_getattr_t)(1<<20)) */
-/* unused ((lib9p_getattr_t)(1<<19)) */
-/* unused ((lib9p_getattr_t)(1<<18)) */
-/* unused ((lib9p_getattr_t)(1<<17)) */
-/* unused ((lib9p_getattr_t)(1<<16)) */
-/* unused ((lib9p_getattr_t)(1<<15)) */
-/* unused ((lib9p_getattr_t)(1<<14)) */
-#define LIB9P_GETATTR_DATA_VERSION ((lib9p_getattr_t)(1<<13))
-#define LIB9P_GETATTR_GEN ((lib9p_getattr_t)(1<<12))
-#define LIB9P_GETATTR_BTIME ((lib9p_getattr_t)(1<<11))
-#define LIB9P_GETATTR_BLOCKS ((lib9p_getattr_t)(1<<10))
-#define LIB9P_GETATTR_SIZE ((lib9p_getattr_t)(1<<9))
-#define LIB9P_GETATTR_INO ((lib9p_getattr_t)(1<<8))
-#define LIB9P_GETATTR_CTIME ((lib9p_getattr_t)(1<<7))
-#define LIB9P_GETATTR_MTIME ((lib9p_getattr_t)(1<<6))
-#define LIB9P_GETATTR_ATIME ((lib9p_getattr_t)(1<<5))
-#define LIB9P_GETATTR_RDEV ((lib9p_getattr_t)(1<<4))
-#define LIB9P_GETATTR_GID ((lib9p_getattr_t)(1<<3))
-#define LIB9P_GETATTR_UID ((lib9p_getattr_t)(1<<2))
-#define LIB9P_GETATTR_NLINK ((lib9p_getattr_t)(1<<1))
-#define LIB9P_GETATTR_MODE ((lib9p_getattr_t)(1<<0))
-
-#define LIB9P_GETATTR_BASIC ((lib9p_getattr_t)(0x000007ff))
-#define LIB9P_GETATTR_ALL ((lib9p_getattr_t)(0x00003fff))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_getattr_t, lib9p_getattr);
+/* bits */
+#define _LIB9P_GETATTR_UNUSED_63 ((lib9p_getattr_t)(UINT64_C(1)<<63))
+#define _LIB9P_GETATTR_UNUSED_62 ((lib9p_getattr_t)(UINT64_C(1)<<62))
+#define _LIB9P_GETATTR_UNUSED_61 ((lib9p_getattr_t)(UINT64_C(1)<<61))
+#define _LIB9P_GETATTR_UNUSED_60 ((lib9p_getattr_t)(UINT64_C(1)<<60))
+#define _LIB9P_GETATTR_UNUSED_59 ((lib9p_getattr_t)(UINT64_C(1)<<59))
+#define _LIB9P_GETATTR_UNUSED_58 ((lib9p_getattr_t)(UINT64_C(1)<<58))
+#define _LIB9P_GETATTR_UNUSED_57 ((lib9p_getattr_t)(UINT64_C(1)<<57))
+#define _LIB9P_GETATTR_UNUSED_56 ((lib9p_getattr_t)(UINT64_C(1)<<56))
+#define _LIB9P_GETATTR_UNUSED_55 ((lib9p_getattr_t)(UINT64_C(1)<<55))
+#define _LIB9P_GETATTR_UNUSED_54 ((lib9p_getattr_t)(UINT64_C(1)<<54))
+#define _LIB9P_GETATTR_UNUSED_53 ((lib9p_getattr_t)(UINT64_C(1)<<53))
+#define _LIB9P_GETATTR_UNUSED_52 ((lib9p_getattr_t)(UINT64_C(1)<<52))
+#define _LIB9P_GETATTR_UNUSED_51 ((lib9p_getattr_t)(UINT64_C(1)<<51))
+#define _LIB9P_GETATTR_UNUSED_50 ((lib9p_getattr_t)(UINT64_C(1)<<50))
+#define _LIB9P_GETATTR_UNUSED_49 ((lib9p_getattr_t)(UINT64_C(1)<<49))
+#define _LIB9P_GETATTR_UNUSED_48 ((lib9p_getattr_t)(UINT64_C(1)<<48))
+#define _LIB9P_GETATTR_UNUSED_47 ((lib9p_getattr_t)(UINT64_C(1)<<47))
+#define _LIB9P_GETATTR_UNUSED_46 ((lib9p_getattr_t)(UINT64_C(1)<<46))
+#define _LIB9P_GETATTR_UNUSED_45 ((lib9p_getattr_t)(UINT64_C(1)<<45))
+#define _LIB9P_GETATTR_UNUSED_44 ((lib9p_getattr_t)(UINT64_C(1)<<44))
+#define _LIB9P_GETATTR_UNUSED_43 ((lib9p_getattr_t)(UINT64_C(1)<<43))
+#define _LIB9P_GETATTR_UNUSED_42 ((lib9p_getattr_t)(UINT64_C(1)<<42))
+#define _LIB9P_GETATTR_UNUSED_41 ((lib9p_getattr_t)(UINT64_C(1)<<41))
+#define _LIB9P_GETATTR_UNUSED_40 ((lib9p_getattr_t)(UINT64_C(1)<<40))
+#define _LIB9P_GETATTR_UNUSED_39 ((lib9p_getattr_t)(UINT64_C(1)<<39))
+#define _LIB9P_GETATTR_UNUSED_38 ((lib9p_getattr_t)(UINT64_C(1)<<38))
+#define _LIB9P_GETATTR_UNUSED_37 ((lib9p_getattr_t)(UINT64_C(1)<<37))
+#define _LIB9P_GETATTR_UNUSED_36 ((lib9p_getattr_t)(UINT64_C(1)<<36))
+#define _LIB9P_GETATTR_UNUSED_35 ((lib9p_getattr_t)(UINT64_C(1)<<35))
+#define _LIB9P_GETATTR_UNUSED_34 ((lib9p_getattr_t)(UINT64_C(1)<<34))
+#define _LIB9P_GETATTR_UNUSED_33 ((lib9p_getattr_t)(UINT64_C(1)<<33))
+#define _LIB9P_GETATTR_UNUSED_32 ((lib9p_getattr_t)(UINT64_C(1)<<32))
+#define _LIB9P_GETATTR_UNUSED_31 ((lib9p_getattr_t)(UINT64_C(1)<<31))
+#define _LIB9P_GETATTR_UNUSED_30 ((lib9p_getattr_t)(UINT64_C(1)<<30))
+#define _LIB9P_GETATTR_UNUSED_29 ((lib9p_getattr_t)(UINT64_C(1)<<29))
+#define _LIB9P_GETATTR_UNUSED_28 ((lib9p_getattr_t)(UINT64_C(1)<<28))
+#define _LIB9P_GETATTR_UNUSED_27 ((lib9p_getattr_t)(UINT64_C(1)<<27))
+#define _LIB9P_GETATTR_UNUSED_26 ((lib9p_getattr_t)(UINT64_C(1)<<26))
+#define _LIB9P_GETATTR_UNUSED_25 ((lib9p_getattr_t)(UINT64_C(1)<<25))
+#define _LIB9P_GETATTR_UNUSED_24 ((lib9p_getattr_t)(UINT64_C(1)<<24))
+#define _LIB9P_GETATTR_UNUSED_23 ((lib9p_getattr_t)(UINT64_C(1)<<23))
+#define _LIB9P_GETATTR_UNUSED_22 ((lib9p_getattr_t)(UINT64_C(1)<<22))
+#define _LIB9P_GETATTR_UNUSED_21 ((lib9p_getattr_t)(UINT64_C(1)<<21))
+#define _LIB9P_GETATTR_UNUSED_20 ((lib9p_getattr_t)(UINT64_C(1)<<20))
+#define _LIB9P_GETATTR_UNUSED_19 ((lib9p_getattr_t)(UINT64_C(1)<<19))
+#define _LIB9P_GETATTR_UNUSED_18 ((lib9p_getattr_t)(UINT64_C(1)<<18))
+#define _LIB9P_GETATTR_UNUSED_17 ((lib9p_getattr_t)(UINT64_C(1)<<17))
+#define _LIB9P_GETATTR_UNUSED_16 ((lib9p_getattr_t)(UINT64_C(1)<<16))
+#define _LIB9P_GETATTR_UNUSED_15 ((lib9p_getattr_t)(UINT64_C(1)<<15))
+#define _LIB9P_GETATTR_UNUSED_14 ((lib9p_getattr_t)(UINT64_C(1)<<14))
+#define LIB9P_GETATTR_DATA_VERSION ((lib9p_getattr_t)(UINT64_C(1)<<13))
+#define LIB9P_GETATTR_GEN ((lib9p_getattr_t)(UINT64_C(1)<<12))
+#define LIB9P_GETATTR_BTIME ((lib9p_getattr_t)(UINT64_C(1)<<11))
+#define LIB9P_GETATTR_BLOCKS ((lib9p_getattr_t)(UINT64_C(1)<<10))
+#define LIB9P_GETATTR_SIZE ((lib9p_getattr_t)(UINT64_C(1)<<9))
+#define LIB9P_GETATTR_INO ((lib9p_getattr_t)(UINT64_C(1)<<8))
+#define LIB9P_GETATTR_CTIME ((lib9p_getattr_t)(UINT64_C(1)<<7))
+#define LIB9P_GETATTR_MTIME ((lib9p_getattr_t)(UINT64_C(1)<<6))
+#define LIB9P_GETATTR_ATIME ((lib9p_getattr_t)(UINT64_C(1)<<5))
+#define LIB9P_GETATTR_RDEV ((lib9p_getattr_t)(UINT64_C(1)<<4))
+#define LIB9P_GETATTR_GID ((lib9p_getattr_t)(UINT64_C(1)<<3))
+#define LIB9P_GETATTR_UID ((lib9p_getattr_t)(UINT64_C(1)<<2))
+#define LIB9P_GETATTR_NLINK ((lib9p_getattr_t)(UINT64_C(1)<<1))
+#define LIB9P_GETATTR_MODE ((lib9p_getattr_t)(UINT64_C(1)<<0))
+/* aliases */
+#define LIB9P_GETATTR_BASIC ((lib9p_getattr_t)(2047))
+#define LIB9P_GETATTR_ALL ((lib9p_getattr_t)(16383))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_setattr_t;
-
-/* unused ((lib9p_setattr_t)(1<<31)) */
-/* unused ((lib9p_setattr_t)(1<<30)) */
-/* unused ((lib9p_setattr_t)(1<<29)) */
-/* unused ((lib9p_setattr_t)(1<<28)) */
-/* unused ((lib9p_setattr_t)(1<<27)) */
-/* unused ((lib9p_setattr_t)(1<<26)) */
-/* unused ((lib9p_setattr_t)(1<<25)) */
-/* unused ((lib9p_setattr_t)(1<<24)) */
-/* unused ((lib9p_setattr_t)(1<<23)) */
-/* unused ((lib9p_setattr_t)(1<<22)) */
-/* unused ((lib9p_setattr_t)(1<<21)) */
-/* unused ((lib9p_setattr_t)(1<<20)) */
-/* unused ((lib9p_setattr_t)(1<<19)) */
-/* unused ((lib9p_setattr_t)(1<<18)) */
-/* unused ((lib9p_setattr_t)(1<<17)) */
-/* unused ((lib9p_setattr_t)(1<<16)) */
-/* unused ((lib9p_setattr_t)(1<<15)) */
-/* unused ((lib9p_setattr_t)(1<<14)) */
-/* unused ((lib9p_setattr_t)(1<<13)) */
-/* unused ((lib9p_setattr_t)(1<<12)) */
-/* unused ((lib9p_setattr_t)(1<<11)) */
-/* unused ((lib9p_setattr_t)(1<<10)) */
-/* unused ((lib9p_setattr_t)(1<<9)) */
-#define LIB9P_SETATTR_MTIME_SET ((lib9p_setattr_t)(1<<8))
-#define LIB9P_SETATTR_ATIME_SET ((lib9p_setattr_t)(1<<7))
-#define LIB9P_SETATTR_CTIME ((lib9p_setattr_t)(1<<6))
-#define LIB9P_SETATTR_MTIME ((lib9p_setattr_t)(1<<5))
-#define LIB9P_SETATTR_ATIME ((lib9p_setattr_t)(1<<4))
-#define LIB9P_SETATTR_SIZE ((lib9p_setattr_t)(1<<3))
-#define LIB9P_SETATTR_GID ((lib9p_setattr_t)(1<<2))
-#define LIB9P_SETATTR_UID ((lib9p_setattr_t)(1<<1))
-#define LIB9P_SETATTR_MODE ((lib9p_setattr_t)(1<<0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_setattr_t, lib9p_setattr);
+/* bits */
+#define _LIB9P_SETATTR_UNUSED_31 ((lib9p_setattr_t)(UINT32_C(1)<<31))
+#define _LIB9P_SETATTR_UNUSED_30 ((lib9p_setattr_t)(UINT32_C(1)<<30))
+#define _LIB9P_SETATTR_UNUSED_29 ((lib9p_setattr_t)(UINT32_C(1)<<29))
+#define _LIB9P_SETATTR_UNUSED_28 ((lib9p_setattr_t)(UINT32_C(1)<<28))
+#define _LIB9P_SETATTR_UNUSED_27 ((lib9p_setattr_t)(UINT32_C(1)<<27))
+#define _LIB9P_SETATTR_UNUSED_26 ((lib9p_setattr_t)(UINT32_C(1)<<26))
+#define _LIB9P_SETATTR_UNUSED_25 ((lib9p_setattr_t)(UINT32_C(1)<<25))
+#define _LIB9P_SETATTR_UNUSED_24 ((lib9p_setattr_t)(UINT32_C(1)<<24))
+#define _LIB9P_SETATTR_UNUSED_23 ((lib9p_setattr_t)(UINT32_C(1)<<23))
+#define _LIB9P_SETATTR_UNUSED_22 ((lib9p_setattr_t)(UINT32_C(1)<<22))
+#define _LIB9P_SETATTR_UNUSED_21 ((lib9p_setattr_t)(UINT32_C(1)<<21))
+#define _LIB9P_SETATTR_UNUSED_20 ((lib9p_setattr_t)(UINT32_C(1)<<20))
+#define _LIB9P_SETATTR_UNUSED_19 ((lib9p_setattr_t)(UINT32_C(1)<<19))
+#define _LIB9P_SETATTR_UNUSED_18 ((lib9p_setattr_t)(UINT32_C(1)<<18))
+#define _LIB9P_SETATTR_UNUSED_17 ((lib9p_setattr_t)(UINT32_C(1)<<17))
+#define _LIB9P_SETATTR_UNUSED_16 ((lib9p_setattr_t)(UINT32_C(1)<<16))
+#define _LIB9P_SETATTR_UNUSED_15 ((lib9p_setattr_t)(UINT32_C(1)<<15))
+#define _LIB9P_SETATTR_UNUSED_14 ((lib9p_setattr_t)(UINT32_C(1)<<14))
+#define _LIB9P_SETATTR_UNUSED_13 ((lib9p_setattr_t)(UINT32_C(1)<<13))
+#define _LIB9P_SETATTR_UNUSED_12 ((lib9p_setattr_t)(UINT32_C(1)<<12))
+#define _LIB9P_SETATTR_UNUSED_11 ((lib9p_setattr_t)(UINT32_C(1)<<11))
+#define _LIB9P_SETATTR_UNUSED_10 ((lib9p_setattr_t)(UINT32_C(1)<<10))
+#define _LIB9P_SETATTR_UNUSED_9 ((lib9p_setattr_t)(UINT32_C(1)<<9))
+#define LIB9P_SETATTR_MTIME_SET ((lib9p_setattr_t)(UINT32_C(1)<<8))
+#define LIB9P_SETATTR_ATIME_SET ((lib9p_setattr_t)(UINT32_C(1)<<7))
+#define LIB9P_SETATTR_CTIME ((lib9p_setattr_t)(UINT32_C(1)<<6))
+#define LIB9P_SETATTR_MTIME ((lib9p_setattr_t)(UINT32_C(1)<<5))
+#define LIB9P_SETATTR_ATIME ((lib9p_setattr_t)(UINT32_C(1)<<4))
+#define LIB9P_SETATTR_SIZE ((lib9p_setattr_t)(UINT32_C(1)<<3))
+#define LIB9P_SETATTR_GID ((lib9p_setattr_t)(UINT32_C(1)<<2))
+#define LIB9P_SETATTR_UID ((lib9p_setattr_t)(UINT32_C(1)<<1))
+#define LIB9P_SETATTR_MODE ((lib9p_setattr_t)(UINT32_C(1)<<0))
/* size = 1 ; max_iov = 1 ; max_copy = 1 */
typedef uint8_t lib9p_lock_type_t;
-#define LIB9P_LOCK_TYPE_RDLCK ((lib9p_lock_type_t)UINT8_C(0))
-#define LIB9P_LOCK_TYPE_WRLCK ((lib9p_lock_type_t)UINT8_C(1))
-#define LIB9P_LOCK_TYPE_UNLCK ((lib9p_lock_type_t)UINT8_C(2))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_lock_type_t, lib9p_lock_type);
+#define LIB9P_LOCK_TYPE_RDLCK ((lib9p_lock_type_t)(0))
+#define LIB9P_LOCK_TYPE_WRLCK ((lib9p_lock_type_t)(1))
+#define LIB9P_LOCK_TYPE_UNLCK ((lib9p_lock_type_t)(2))
/* size = 4 ; max_iov = 1 ; max_copy = 4 */
typedef uint32_t lib9p_lock_flags_t;
-
-/* unused ((lib9p_lock_flags_t)(1<<31)) */
-/* unused ((lib9p_lock_flags_t)(1<<30)) */
-/* unused ((lib9p_lock_flags_t)(1<<29)) */
-/* unused ((lib9p_lock_flags_t)(1<<28)) */
-/* unused ((lib9p_lock_flags_t)(1<<27)) */
-/* unused ((lib9p_lock_flags_t)(1<<26)) */
-/* unused ((lib9p_lock_flags_t)(1<<25)) */
-/* unused ((lib9p_lock_flags_t)(1<<24)) */
-/* unused ((lib9p_lock_flags_t)(1<<23)) */
-/* unused ((lib9p_lock_flags_t)(1<<22)) */
-/* unused ((lib9p_lock_flags_t)(1<<21)) */
-/* unused ((lib9p_lock_flags_t)(1<<20)) */
-/* unused ((lib9p_lock_flags_t)(1<<19)) */
-/* unused ((lib9p_lock_flags_t)(1<<18)) */
-/* unused ((lib9p_lock_flags_t)(1<<17)) */
-/* unused ((lib9p_lock_flags_t)(1<<16)) */
-/* unused ((lib9p_lock_flags_t)(1<<15)) */
-/* unused ((lib9p_lock_flags_t)(1<<14)) */
-/* unused ((lib9p_lock_flags_t)(1<<13)) */
-/* unused ((lib9p_lock_flags_t)(1<<12)) */
-/* unused ((lib9p_lock_flags_t)(1<<11)) */
-/* unused ((lib9p_lock_flags_t)(1<<10)) */
-/* unused ((lib9p_lock_flags_t)(1<<9)) */
-/* unused ((lib9p_lock_flags_t)(1<<8)) */
-/* unused ((lib9p_lock_flags_t)(1<<7)) */
-/* unused ((lib9p_lock_flags_t)(1<<6)) */
-/* unused ((lib9p_lock_flags_t)(1<<5)) */
-/* unused ((lib9p_lock_flags_t)(1<<4)) */
-/* unused ((lib9p_lock_flags_t)(1<<3)) */
-/* unused ((lib9p_lock_flags_t)(1<<2)) */
-#define LIB9P_LOCK_FLAGS_RECLAIM ((lib9p_lock_flags_t)(1<<1))
-#define LIB9P_LOCK_FLAGS_BLOCK ((lib9p_lock_flags_t)(1<<0))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_lock_flags_t, lib9p_lock_flags);
+/* bits */
+#define _LIB9P_LOCK_FLAGS_UNUSED_31 ((lib9p_lock_flags_t)(UINT32_C(1)<<31))
+#define _LIB9P_LOCK_FLAGS_UNUSED_30 ((lib9p_lock_flags_t)(UINT32_C(1)<<30))
+#define _LIB9P_LOCK_FLAGS_UNUSED_29 ((lib9p_lock_flags_t)(UINT32_C(1)<<29))
+#define _LIB9P_LOCK_FLAGS_UNUSED_28 ((lib9p_lock_flags_t)(UINT32_C(1)<<28))
+#define _LIB9P_LOCK_FLAGS_UNUSED_27 ((lib9p_lock_flags_t)(UINT32_C(1)<<27))
+#define _LIB9P_LOCK_FLAGS_UNUSED_26 ((lib9p_lock_flags_t)(UINT32_C(1)<<26))
+#define _LIB9P_LOCK_FLAGS_UNUSED_25 ((lib9p_lock_flags_t)(UINT32_C(1)<<25))
+#define _LIB9P_LOCK_FLAGS_UNUSED_24 ((lib9p_lock_flags_t)(UINT32_C(1)<<24))
+#define _LIB9P_LOCK_FLAGS_UNUSED_23 ((lib9p_lock_flags_t)(UINT32_C(1)<<23))
+#define _LIB9P_LOCK_FLAGS_UNUSED_22 ((lib9p_lock_flags_t)(UINT32_C(1)<<22))
+#define _LIB9P_LOCK_FLAGS_UNUSED_21 ((lib9p_lock_flags_t)(UINT32_C(1)<<21))
+#define _LIB9P_LOCK_FLAGS_UNUSED_20 ((lib9p_lock_flags_t)(UINT32_C(1)<<20))
+#define _LIB9P_LOCK_FLAGS_UNUSED_19 ((lib9p_lock_flags_t)(UINT32_C(1)<<19))
+#define _LIB9P_LOCK_FLAGS_UNUSED_18 ((lib9p_lock_flags_t)(UINT32_C(1)<<18))
+#define _LIB9P_LOCK_FLAGS_UNUSED_17 ((lib9p_lock_flags_t)(UINT32_C(1)<<17))
+#define _LIB9P_LOCK_FLAGS_UNUSED_16 ((lib9p_lock_flags_t)(UINT32_C(1)<<16))
+#define _LIB9P_LOCK_FLAGS_UNUSED_15 ((lib9p_lock_flags_t)(UINT32_C(1)<<15))
+#define _LIB9P_LOCK_FLAGS_UNUSED_14 ((lib9p_lock_flags_t)(UINT32_C(1)<<14))
+#define _LIB9P_LOCK_FLAGS_UNUSED_13 ((lib9p_lock_flags_t)(UINT32_C(1)<<13))
+#define _LIB9P_LOCK_FLAGS_UNUSED_12 ((lib9p_lock_flags_t)(UINT32_C(1)<<12))
+#define _LIB9P_LOCK_FLAGS_UNUSED_11 ((lib9p_lock_flags_t)(UINT32_C(1)<<11))
+#define _LIB9P_LOCK_FLAGS_UNUSED_10 ((lib9p_lock_flags_t)(UINT32_C(1)<<10))
+#define _LIB9P_LOCK_FLAGS_UNUSED_9 ((lib9p_lock_flags_t)(UINT32_C(1)<<9))
+#define _LIB9P_LOCK_FLAGS_UNUSED_8 ((lib9p_lock_flags_t)(UINT32_C(1)<<8))
+#define _LIB9P_LOCK_FLAGS_UNUSED_7 ((lib9p_lock_flags_t)(UINT32_C(1)<<7))
+#define _LIB9P_LOCK_FLAGS_UNUSED_6 ((lib9p_lock_flags_t)(UINT32_C(1)<<6))
+#define _LIB9P_LOCK_FLAGS_UNUSED_5 ((lib9p_lock_flags_t)(UINT32_C(1)<<5))
+#define _LIB9P_LOCK_FLAGS_UNUSED_4 ((lib9p_lock_flags_t)(UINT32_C(1)<<4))
+#define _LIB9P_LOCK_FLAGS_UNUSED_3 ((lib9p_lock_flags_t)(UINT32_C(1)<<3))
+#define _LIB9P_LOCK_FLAGS_UNUSED_2 ((lib9p_lock_flags_t)(UINT32_C(1)<<2))
+#define LIB9P_LOCK_FLAGS_RECLAIM ((lib9p_lock_flags_t)(UINT32_C(1)<<1))
+#define LIB9P_LOCK_FLAGS_BLOCK ((lib9p_lock_flags_t)(UINT32_C(1)<<0))
/* size = 1 ; max_iov = 1 ; max_copy = 1 */
typedef uint8_t lib9p_lock_status_t;
-#define LIB9P_LOCK_STATUS_SUCCESS ((lib9p_lock_status_t)UINT8_C(0))
-#define LIB9P_LOCK_STATUS_BLOCKED ((lib9p_lock_status_t)UINT8_C(1))
-#define LIB9P_LOCK_STATUS_ERROR ((lib9p_lock_status_t)UINT8_C(2))
-#define LIB9P_LOCK_STATUS_GRACE ((lib9p_lock_status_t)UINT8_C(3))
+LO_IMPLEMENTATION_H(fmt_formatter, lib9p_lock_status_t, lib9p_lock_status);
+#define LIB9P_LOCK_STATUS_SUCCESS ((lib9p_lock_status_t)(0))
+#define LIB9P_LOCK_STATUS_BLOCKED ((lib9p_lock_status_t)(1))
+#define LIB9P_LOCK_STATUS_ERROR ((lib9p_lock_status_t)(2))
+#define LIB9P_LOCK_STATUS_GRACE ((lib9p_lock_status_t)(3))
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -541,11 +565,13 @@ struct lib9p_msg_Tflush {
lib9p_tag_t tag;
uint16_t oldtag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tflush, lib9p_msg_Tflush);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rflush {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rflush, lib9p_msg_Rflush);
/* min_size = 11 ; exp_size = 8,203 ; max_size = 2,147,483,658 ; max_iov = 2 ; max_copy = 11 */
struct lib9p_msg_Rread {
@@ -553,22 +579,26 @@ struct lib9p_msg_Rread {
uint32_t count;
[[gnu::nonstring]] char *data;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rread, lib9p_msg_Rread);
/* size = 11 ; max_iov = 1 ; max_copy = 11 */
struct lib9p_msg_Rwrite {
lib9p_tag_t tag;
uint32_t count;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rwrite, lib9p_msg_Rwrite);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rclunk {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rclunk, lib9p_msg_Rclunk);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rremove {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rremove, lib9p_msg_Rremove);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -576,6 +606,7 @@ struct lib9p_msg_Rremove {
struct lib9p_msg_Rwstat {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rwstat, lib9p_msg_Rwstat);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -583,22 +614,26 @@ struct lib9p_msg_Rwstat {
struct lib9p_msg_Rrename {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rrename, lib9p_msg_Rrename);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rsetattr {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rsetattr, lib9p_msg_Rsetattr);
/* size = 15 ; max_iov = 1 ; max_copy = 15 */
struct lib9p_msg_Rxattrwalk {
lib9p_tag_t tag;
uint64_t attr_size;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rxattrwalk, lib9p_msg_Rxattrwalk);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rxattrcreate {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rxattrcreate, lib9p_msg_Rxattrcreate);
/* min_size = 11 ; exp_size = 8,203 ; max_size = 4,294,967,306 (warning: >UINT32_MAX) ; max_iov = 2 ; max_copy = 11 */
struct lib9p_msg_Rreaddir {
@@ -606,26 +641,31 @@ struct lib9p_msg_Rreaddir {
uint32_t count;
[[gnu::nonstring]] char *data;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rreaddir, lib9p_msg_Rreaddir);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rfsync {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rfsync, lib9p_msg_Rfsync);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rlink {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rlink, lib9p_msg_Rlink);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rrenameat {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rrenameat, lib9p_msg_Rrenameat);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Runlinkat {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Runlinkat, lib9p_msg_Runlinkat);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
@@ -634,11 +674,13 @@ struct lib9p_msg_Tsession {
lib9p_tag_t tag;
uint64_t key;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tsession, lib9p_msg_Tsession);
/* size = 7 ; max_iov = 1 ; max_copy = 7 */
struct lib9p_msg_Rsession {
lib9p_tag_t tag;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rsession, lib9p_msg_Rsession);
/* min_size = 11 ; exp_size = 8,203 ; max_size = 4,294,967,306 (warning: >UINT32_MAX) ; max_iov = 2 ; max_copy = 11 */
struct lib9p_msg_Rsread {
@@ -646,12 +688,14 @@ struct lib9p_msg_Rsread {
uint32_t count;
[[gnu::nonstring]] char *data;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rsread, lib9p_msg_Rsread);
/* size = 11 ; max_iov = 1 ; max_copy = 11 */
struct lib9p_msg_Rswrite {
lib9p_tag_t tag;
uint32_t count;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rswrite, lib9p_msg_Rswrite);
#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -662,6 +706,7 @@ struct lib9p_msg_Tread {
uint64_t offset;
uint32_t count;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tread, lib9p_msg_Tread);
/* min_size = 23 ; exp_size = 8,215 ; max_size = 2,147,483,670 ; max_iov = 2 ; max_copy = 23 */
struct lib9p_msg_Twrite {
@@ -671,18 +716,21 @@ struct lib9p_msg_Twrite {
uint32_t count;
[[gnu::nonstring]] char *data;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Twrite, lib9p_msg_Twrite);
/* size = 11 ; max_iov = 1 ; max_copy = 11 */
struct lib9p_msg_Tclunk {
lib9p_tag_t tag;
lib9p_fid_t fid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tclunk, lib9p_msg_Tclunk);
/* size = 11 ; max_iov = 1 ; max_copy = 11 */
struct lib9p_msg_Tremove {
lib9p_tag_t tag;
lib9p_fid_t fid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tremove, lib9p_msg_Tremove);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -691,6 +739,7 @@ struct lib9p_msg_Tstat {
lib9p_tag_t tag;
lib9p_fid_t fid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tstat, lib9p_msg_Tstat);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -699,12 +748,14 @@ struct lib9p_msg_Tstatfs {
lib9p_tag_t tag;
lib9p_fid_t fid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tstatfs, lib9p_msg_Tstatfs);
/* size = 11 ; max_iov = 1 ; max_copy = 11 */
struct lib9p_msg_Treadlink {
lib9p_tag_t tag;
lib9p_fid_t fid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Treadlink, lib9p_msg_Treadlink);
/* size = 23 ; max_iov = 1 ; max_copy = 23 */
struct lib9p_msg_Treaddir {
@@ -713,6 +764,7 @@ struct lib9p_msg_Treaddir {
uint64_t offset;
uint32_t count;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Treaddir, lib9p_msg_Treaddir);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -722,6 +774,7 @@ struct lib9p_msg_Tversion {
uint32_t max_msg_size;
struct lib9p_s version;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tversion, lib9p_msg_Tversion);
/* min_size = 13 ; exp_size = 40 ; max_size = 65,548 ; max_iov = 2 ; max_copy = 13 */
struct lib9p_msg_Rversion {
@@ -729,6 +782,7 @@ struct lib9p_msg_Rversion {
uint32_t max_msg_size;
struct lib9p_s version;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rversion, lib9p_msg_Rversion);
/* min_size = 17 ; exp_size = 481 ; max_size = 1,048,609 ; max_iov = 32 ; max_copy = 49 */
struct lib9p_msg_Twalk {
@@ -738,6 +792,7 @@ struct lib9p_msg_Twalk {
uint16_t nwname;
struct lib9p_s *wname;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Twalk, lib9p_msg_Twalk);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -748,12 +803,14 @@ struct lib9p_msg_Trename {
lib9p_fid_t dfid;
struct lib9p_s name;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Trename, lib9p_msg_Trename);
/* min_size = 9 ; exp_size = 36 ; max_size = 65,544 ; max_iov = 2 ; max_copy = 9 */
struct lib9p_msg_Rreadlink {
lib9p_tag_t tag;
struct lib9p_s target;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rreadlink, lib9p_msg_Rreadlink);
/* min_size = 17 ; exp_size = 44 ; max_size = 65,552 ; max_iov = 2 ; max_copy = 17 */
struct lib9p_msg_Txattrwalk {
@@ -762,6 +819,7 @@ struct lib9p_msg_Txattrwalk {
lib9p_fid_t newfid;
struct lib9p_s name;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Txattrwalk, lib9p_msg_Txattrwalk);
/* min_size = 25 ; exp_size = 52 ; max_size = 65,560 ; max_iov = 3 ; max_copy = 25 */
struct lib9p_msg_Txattrcreate {
@@ -771,6 +829,7 @@ struct lib9p_msg_Txattrcreate {
uint64_t attr_size;
uint32_t flags;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Txattrcreate, lib9p_msg_Txattrcreate);
/* min_size = 17 ; exp_size = 44 ; max_size = 65,552 ; max_iov = 2 ; max_copy = 17 */
struct lib9p_msg_Tlink {
@@ -779,6 +838,7 @@ struct lib9p_msg_Tlink {
lib9p_fid_t fid;
struct lib9p_s name;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tlink, lib9p_msg_Tlink);
/* min_size = 19 ; exp_size = 73 ; max_size = 131,089 ; max_iov = 4 ; max_copy = 19 */
struct lib9p_msg_Trenameat {
@@ -788,6 +848,7 @@ struct lib9p_msg_Trenameat {
lib9p_fid_t newdirfid;
struct lib9p_s newname;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Trenameat, lib9p_msg_Trenameat);
/* min_size = 17 ; exp_size = 44 ; max_size = 65,552 ; max_iov = 3 ; max_copy = 17 */
struct lib9p_msg_Tunlinkat {
@@ -796,6 +857,7 @@ struct lib9p_msg_Tunlinkat {
struct lib9p_s name;
uint32_t flags;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tunlinkat, lib9p_msg_Tunlinkat);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000_e
@@ -806,6 +868,7 @@ struct lib9p_msg_Tsread {
uint16_t nwname;
struct lib9p_s *wname;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tsread, lib9p_msg_Tsread);
/* min_size = 17 ; exp_size = 8,673 ; max_size = 8,589,934,607 (warning: >UINT32_MAX) ; max_iov = 2 + (CONFIG_9P_MAX_9P2000_e_WELEM * 2) ; max_copy = 17 + (CONFIG_9P_MAX_9P2000_e_WELEM * 2) */
struct lib9p_msg_Tswrite {
@@ -816,6 +879,7 @@ struct lib9p_msg_Tswrite {
uint32_t count;
[[gnu::nonstring]] char *data;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tswrite, lib9p_msg_Tswrite);
#endif /* CONFIG_9P_ENABLE_9P2000_e */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -825,6 +889,7 @@ struct lib9p_qid {
uint32_t vers;
uint64_t path;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_qid, lib9p_qid);
/* LIB9P_VER_9P2000 : min_size = 15 ; exp_size = 69 ; max_size = 131,085 ; max_iov = 4 ; max_copy = 15 */
/* LIB9P_VER_9P2000_L : min_size = 19 ; exp_size = 73 ; max_size = 131,089 ; max_iov = 5 ; max_copy = 19 */
@@ -840,6 +905,7 @@ struct lib9p_msg_Tauth {
lib9p_nuid_t n_uid;
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tauth, lib9p_msg_Tauth);
/* LIB9P_VER_9P2000 : min_size = 19 ; exp_size = 73 ; max_size = 131,089 ; max_iov = 4 ; max_copy = 19 */
/* LIB9P_VER_9P2000_L : min_size = 23 ; exp_size = 77 ; max_size = 131,093 ; max_iov = 5 ; max_copy = 23 */
@@ -856,6 +922,7 @@ struct lib9p_msg_Tattach {
lib9p_nuid_t n_uid;
#endif /* CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_u */
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tattach, lib9p_msg_Tattach);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -867,6 +934,7 @@ struct lib9p_msg_Tsymlink {
struct lib9p_s symtgt;
lib9p_nuid_t gid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tsymlink, lib9p_msg_Tsymlink);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -876,6 +944,7 @@ struct lib9p_msg_Topen {
lib9p_fid_t fid;
lib9p_o_t mode;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Topen, lib9p_msg_Topen);
/* min_size = 18 ; exp_size = 45 ; max_size = 65,553 ; max_iov = 3 ; max_copy = 18 */
struct lib9p_msg_Tcreate {
@@ -885,6 +954,7 @@ struct lib9p_msg_Tcreate {
lib9p_dm_t perm;
lib9p_o_t mode;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tcreate, lib9p_msg_Tcreate);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_p9p
@@ -894,6 +964,7 @@ struct lib9p_msg_Topenfd {
lib9p_fid_t fid;
lib9p_o_t mode;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Topenfd, lib9p_msg_Topenfd);
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -909,6 +980,7 @@ struct lib9p_msg_Rerror {
lib9p_errno_t errno;
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rerror, lib9p_msg_Rerror);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -917,6 +989,7 @@ struct lib9p_msg_Rlerror {
lib9p_tag_t tag;
lib9p_errno_t ecode;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rlerror, lib9p_msg_Rlerror);
/* size = 67 ; max_iov = 1 ; max_copy = 67 */
struct lib9p_msg_Rstatfs {
@@ -931,6 +1004,7 @@ struct lib9p_msg_Rstatfs {
uint64_t fsid;
uint32_t namelen;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rstatfs, lib9p_msg_Rstatfs);
/* size = 15 ; max_iov = 1 ; max_copy = 15 */
struct lib9p_msg_Tlopen {
@@ -938,6 +1012,7 @@ struct lib9p_msg_Tlopen {
lib9p_fid_t fid;
lib9p_lo_t flags;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tlopen, lib9p_msg_Tlopen);
/* min_size = 25 ; exp_size = 52 ; max_size = 65,560 ; max_iov = 3 ; max_copy = 25 */
struct lib9p_msg_Tlcreate {
@@ -948,6 +1023,7 @@ struct lib9p_msg_Tlcreate {
lib9p_mode_t mode;
lib9p_nuid_t gid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tlcreate, lib9p_msg_Tlcreate);
/* min_size = 29 ; exp_size = 56 ; max_size = 65,564 ; max_iov = 3 ; max_copy = 29 */
struct lib9p_msg_Tmknod {
@@ -959,6 +1035,7 @@ struct lib9p_msg_Tmknod {
uint32_t minor;
lib9p_nuid_t gid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tmknod, lib9p_msg_Tmknod);
/* min_size = 21 ; exp_size = 48 ; max_size = 65,556 ; max_iov = 3 ; max_copy = 21 */
struct lib9p_msg_Tmkdir {
@@ -968,6 +1045,7 @@ struct lib9p_msg_Tmkdir {
lib9p_mode_t mode;
lib9p_nuid_t gid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tmkdir, lib9p_msg_Tmkdir);
/* size = 15 ; max_iov = 1 ; max_copy = 15 */
struct lib9p_msg_Tfsync {
@@ -975,6 +1053,7 @@ struct lib9p_msg_Tfsync {
lib9p_fid_t fid;
lib9p_b4_t datasync;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tfsync, lib9p_msg_Tfsync);
/* size = 19 ; max_iov = 1 ; max_copy = 19 */
struct lib9p_msg_Tgetattr {
@@ -982,6 +1061,7 @@ struct lib9p_msg_Tgetattr {
lib9p_fid_t fid;
lib9p_getattr_t request_mask;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tgetattr, lib9p_msg_Tgetattr);
/* size = 67 ; max_iov = 1 ; max_copy = 67 */
struct lib9p_msg_Tsetattr {
@@ -997,6 +1077,7 @@ struct lib9p_msg_Tsetattr {
uint64_t mtime_sec;
uint64_t mtime_nsec;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tsetattr, lib9p_msg_Tsetattr);
/* min_size = 34 ; exp_size = 61 ; max_size = 65,569 ; max_iov = 2 ; max_copy = 34 */
struct lib9p_msg_Tgetlock {
@@ -1008,6 +1089,7 @@ struct lib9p_msg_Tgetlock {
uint32_t proc_id;
struct lib9p_s client_id;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tgetlock, lib9p_msg_Tgetlock);
/* min_size = 30 ; exp_size = 57 ; max_size = 65,565 ; max_iov = 2 ; max_copy = 30 */
struct lib9p_msg_Rgetlock {
@@ -1018,6 +1100,7 @@ struct lib9p_msg_Rgetlock {
uint32_t proc_id;
struct lib9p_s client_id;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rgetlock, lib9p_msg_Rgetlock);
/* min_size = 38 ; exp_size = 65 ; max_size = 65,573 ; max_iov = 2 ; max_copy = 38 */
struct lib9p_msg_Tlock {
@@ -1030,12 +1113,14 @@ struct lib9p_msg_Tlock {
uint32_t proc_id;
struct lib9p_s client_id;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Tlock, lib9p_msg_Tlock);
/* size = 8 ; max_iov = 1 ; max_copy = 8 */
struct lib9p_msg_Rlock {
lib9p_tag_t tag;
lib9p_lock_status_t status;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rlock, lib9p_msg_Rlock);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -1062,6 +1147,7 @@ struct lib9p_stat {
lib9p_nuid_t file_last_modified_n_uid;
#endif /* CONFIG_9P_ENABLE_9P2000_u */
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_stat, lib9p_stat);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -1070,12 +1156,14 @@ struct lib9p_msg_Rauth {
lib9p_tag_t tag;
struct lib9p_qid aqid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rauth, lib9p_msg_Rauth);
/* size = 20 ; max_iov = 1 ; max_copy = 20 */
struct lib9p_msg_Rattach {
lib9p_tag_t tag;
struct lib9p_qid qid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rattach, lib9p_msg_Rattach);
/* min_size = 9 ; exp_size = 217 ; max_size = 217 ; max_iov = 1 ; max_copy = 217 */
struct lib9p_msg_Rwalk {
@@ -1083,6 +1171,7 @@ struct lib9p_msg_Rwalk {
uint16_t nwqid;
struct lib9p_qid *wqid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rwalk, lib9p_msg_Rwalk);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_L || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -1092,6 +1181,7 @@ struct lib9p_msg_Ropen {
struct lib9p_qid qid;
uint32_t iounit;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Ropen, lib9p_msg_Ropen);
/* size = 24 ; max_iov = 1 ; max_copy = 24 */
struct lib9p_msg_Rcreate {
@@ -1099,6 +1189,7 @@ struct lib9p_msg_Rcreate {
struct lib9p_qid qid;
uint32_t iounit;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rcreate, lib9p_msg_Rcreate);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
#if CONFIG_9P_ENABLE_9P2000_p9p
@@ -1109,6 +1200,7 @@ struct lib9p_msg_Ropenfd {
uint32_t iounit;
uint32_t unixfd;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Ropenfd, lib9p_msg_Ropenfd);
#endif /* CONFIG_9P_ENABLE_9P2000_p9p */
#if CONFIG_9P_ENABLE_9P2000_L
@@ -1118,6 +1210,7 @@ struct lib9p_msg_Rlopen {
struct lib9p_qid qid;
uint32_t iounit;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rlopen, lib9p_msg_Rlopen);
/* size = 24 ; max_iov = 1 ; max_copy = 24 */
struct lib9p_msg_Rlcreate {
@@ -1125,18 +1218,21 @@ struct lib9p_msg_Rlcreate {
struct lib9p_qid qid;
uint32_t iounit;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rlcreate, lib9p_msg_Rlcreate);
/* size = 20 ; max_iov = 1 ; max_copy = 20 */
struct lib9p_msg_Rsymlink {
lib9p_tag_t tag;
struct lib9p_qid qid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rsymlink, lib9p_msg_Rsymlink);
/* size = 20 ; max_iov = 1 ; max_copy = 20 */
struct lib9p_msg_Rmknod {
lib9p_tag_t tag;
struct lib9p_qid qid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rmknod, lib9p_msg_Rmknod);
/* size = 160 ; max_iov = 1 ; max_copy = 160 */
struct lib9p_msg_Rgetattr {
@@ -1162,12 +1258,14 @@ struct lib9p_msg_Rgetattr {
uint64_t gen;
uint64_t data_version;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rgetattr, lib9p_msg_Rgetattr);
/* size = 20 ; max_iov = 1 ; max_copy = 20 */
struct lib9p_msg_Rmkdir {
lib9p_tag_t tag;
struct lib9p_qid qid;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rmkdir, lib9p_msg_Rmkdir);
#endif /* CONFIG_9P_ENABLE_9P2000_L */
#if CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u
@@ -1179,6 +1277,7 @@ struct lib9p_msg_Rstat {
lib9p_tag_t tag;
struct lib9p_stat stat;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Rstat, lib9p_msg_Rstat);
/* LIB9P_VER_9P2000 : min_size = 62 ; exp_size = 170 ; max_size = 262,202 ; max_iov = 8 ; max_copy = 62 */
/* LIB9P_VER_9P2000_e : min_size = 62 ; exp_size = 170 ; max_size = 262,202 ; max_iov = 8 ; max_copy = 62 */
@@ -1189,6 +1288,7 @@ struct lib9p_msg_Twstat {
lib9p_fid_t fid;
struct lib9p_stat stat;
};
+LO_IMPLEMENTATION_H(fmt_formatter, struct lib9p_msg_Twstat, lib9p_msg_Twstat);
#endif /* CONFIG_9P_ENABLE_9P2000 || CONFIG_9P_ENABLE_9P2000_e || CONFIG_9P_ENABLE_9P2000_p9p || CONFIG_9P_ENABLE_9P2000_u */
/* containers *****************************************************************/
diff --git a/lib9p/include/lib9p/9p.h b/lib9p/include/lib9p/9p.h
index 35b7ef2..5919260 100644
--- a/lib9p/include/lib9p/9p.h
+++ b/lib9p/include/lib9p/9p.h
@@ -18,6 +18,7 @@
#ifndef CONFIG_9P_MAX_ERR_SIZE
#error config.h must define CONFIG_9P_MAX_ERR_SIZE
#endif
+static_assert(CONFIG_9P_MAX_ERR_SIZE <= UINT16_MAX);
/* constants ******************************************************************/
@@ -60,6 +61,12 @@ int lib9p_error(struct lib9p_ctx *ctx, lib9p_errno_t linux_errno, char const *ms
/** Write a printf-style error into ctx, return -1. */
int lib9p_errorf(struct lib9p_ctx *ctx, lib9p_errno_t linux_errno, char const *fmt, ...) [[gnu::format(printf, 3, 4)]];
+/* misc utilities *************************************************************/
+
+uint32_t lib9p_version_min_msg_size(enum lib9p_version);
+
+lo_interface fmt_formatter lo_box_lib9p_msg_as_fmt_formatter(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body);
+
/* main T-message functions ***************************************************/
/**
@@ -159,7 +166,7 @@ static inline void lib9p_stat_assert(struct lib9p_stat stat) {
* @return whether there was an error
*/
bool lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes,
- uint32_t *ret_net_size, ssize_t *ret_host_size);
+ uint32_t *ret_net_size, ssize_t *ret_host_size);
/**
* Unmarshal the 9P `net_bytes` into the C struct `ret_obj`.
@@ -170,12 +177,10 @@ bool lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_
* @param ctx : negotiated protocol parameters
* @param net_bytes : network-encoded stat structure
*
- * @return ret_obj : where to put the stat object itself
- * @return ret_extra : where to put strings for the stat object
- * @return consumed net_bytes
+ * @return ret : the stat object, must be at least lib9p_stat_validate()->ret_net_size bytes
*/
-uint32_t lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
- struct lib9p_stat *ret_obj, void *ret_extra);
+void lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
+ struct lib9p_stat *ret);
/**
* Marhsal a `struct lib9p_stat` structure into a byte-array.
diff --git a/lib9p/include/lib9p/srv.h b/lib9p/include/lib9p/srv.h
index 83aabc0..ff5ebdc 100644
--- a/lib9p/include/lib9p/srv.h
+++ b/lib9p/include/lib9p/srv.h
@@ -37,53 +37,98 @@ int lib9p_srv_acknowledge_flush(struct lib9p_srv_ctx *ctx);
/* interface definitions ******************************************************/
-#define lib9p_srv_file_LO_IFACE \
- /* all - resource management */ \
- LO_FUNC(void , free ) /* must not error */ \
- LO_FUNC(struct lib9p_qid , qid ) /* must not error */ \
- LO_FUNC(uint32_t , chio , struct lib9p_srv_ctx *, \
- bool rd, bool wr, \
- bool trunc) \
- \
- /* all - syscalls */ \
- LO_FUNC(struct lib9p_stat , stat , struct lib9p_srv_ctx *) \
- LO_FUNC(void , wstat , struct lib9p_srv_ctx *, \
- struct lib9p_stat new) \
- LO_FUNC(void , remove , struct lib9p_srv_ctx *) \
- \
- /* directories - base */ \
- LO_FUNC(lo_interface lib9p_srv_file, dopen , struct lib9p_srv_ctx *, \
- struct lib9p_s childname) \
- LO_FUNC(lo_interface lib9p_srv_file, dcreate, struct lib9p_srv_ctx *, \
- struct lib9p_s childname, \
- lib9p_dm_t perm, \
- lib9p_o_t flags) \
- \
- /* directories - once opened */ \
- LO_FUNC(size_t /* <- obj cnt */ , dread , struct lib9p_srv_ctx *, \
- uint8_t *buf, \
- /* num bytes -> */ uint32_t byte_count, \
- /* starting at this object -> */ size_t obj_offset) \
- \
- /* non-directories - once opened */ \
- LO_FUNC(uint32_t , pread , struct lib9p_srv_ctx *, \
- void *buf, \
- uint32_t byte_count, \
- uint64_t byte_offset) \
- LO_FUNC(uint32_t , pwrite , struct lib9p_srv_ctx *, \
- void *buf, \
- uint32_t byte_count, \
+lo_interface lib9p_srv_fio;
+lo_interface lib9p_srv_dio;
+
+/* FIXME: I don't like that the pointers returned by stat() and
+ * pread() have to remain live after they return. Perhaps a
+ * `respond()`-callback? But that just reads as gross in C.
+ *
+ * FIXME: It would be nice if pread() could return more than 1 iovec.
+ */
+#define lib9p_srv_file_LO_IFACE \
+ /* resource management **********************************************/ \
+ \
+ /** \
+ * free() is be called when all FIDs associated with the file are \
+ * clunked. \
+ * \
+ * free() MUST NOT error. \
+ */ \
+ LO_FUNC(void , free ) \
+ \
+ /** \
+ * qid() is called frequently and returns the current QID of the file. \
+ * The .path field MUST never change, the .type field may change in \
+ * response to wstat() calls (but the QT_DIR bit MUST NOT change), and \
+ * the .vers field may change frequently in response to any number of \
+ * things (wstat(), write(), or non-9P events). \
+ * \
+ * qid() MUST NOT error. \
+ */ \
+ LO_FUNC(struct lib9p_qid , qid ) \
+ \
+ /* non-"opened" generic I/O *****************************************/ \
+ \
+ LO_FUNC(struct lib9p_stat , stat , struct lib9p_srv_ctx *) \
+ LO_FUNC(void , wstat , struct lib9p_srv_ctx *, \
+ struct lib9p_stat new) \
+ LO_FUNC(void , remove , struct lib9p_srv_ctx *) \
+ \
+ /* non-"opened" directory I/O ***************************************/ \
+ \
+ LO_FUNC(lo_interface lib9p_srv_file, dwalk , struct lib9p_srv_ctx *, \
+ struct lib9p_s childname) \
+ LO_FUNC(lo_interface lib9p_srv_file, dcreate, struct lib9p_srv_ctx *, \
+ struct lib9p_s childname, \
+ lib9p_dm_t perm, \
+ lib9p_o_t flags) \
+ \
+ /* open() for I/O ***************************************************/ \
+ \
+ LO_FUNC(lo_interface lib9p_srv_fio , fopen , struct lib9p_srv_ctx *, \
+ bool rd, bool wr, \
+ bool trunc) \
+ LO_FUNC(lo_interface lib9p_srv_dio , dopen , struct lib9p_srv_ctx *)
+LO_INTERFACE(lib9p_srv_file);
+
+#define lib9p_srv_fio_LO_IFACE \
+ LO_FUNC(struct lib9p_qid , qid ) \
+ LO_FUNC(void , iofree ) \
+ LO_FUNC(uint32_t , iounit ) \
+ LO_FUNC(void , pread , struct lib9p_srv_ctx *, \
+ uint32_t byte_count, \
+ uint64_t byte_offset, \
+ struct iovec *ret) \
+ LO_FUNC(uint32_t , pwrite , struct lib9p_srv_ctx *, \
+ void *buf, \
+ uint32_t byte_count, \
uint64_t byte_offset)
-LO_INTERFACE(lib9p_srv_file)
+LO_INTERFACE(lib9p_srv_fio);
+
+/* FIXME: The dio interface just feels clunky. I'm not in a rush to
+ * change it because util9p_static_dir is already implemented and I
+ * don't anticipate the sbc-harness needing another dio
+ * implementation. But if I wanted lib9p to be used outside of
+ * sbc-harness, this is one of the first things that I'd want to
+ * change.
+ */
+#define lib9p_srv_dio_LO_IFACE \
+ LO_FUNC(struct lib9p_qid , qid ) \
+ LO_FUNC(void , iofree ) \
+ LO_FUNC(size_t /* <- obj cnt */ , dread , struct lib9p_srv_ctx *, \
+ uint8_t *buf, \
+ /* num bytes -> */ uint32_t byte_count, \
+ /* starting at this object -> */ size_t obj_offset)
+LO_INTERFACE(lib9p_srv_dio);
#define LIB9P_SRV_NOTDIR(TYP, NAM) \
- static lo_interface lib9p_srv_file NAM##_dopen (TYP *, struct lib9p_srv_ctx *, struct lib9p_s) { assert_notreached("not a directory"); } \
+ static lo_interface lib9p_srv_file NAM##_dwalk (TYP *, struct lib9p_srv_ctx *, struct lib9p_s) { assert_notreached("not a directory"); } \
static lo_interface lib9p_srv_file NAM##_dcreate(TYP *, struct lib9p_srv_ctx *, struct lib9p_s, lib9p_dm_t, lib9p_o_t) { assert_notreached("not a directory"); } \
- static size_t NAM##_dread (TYP *, struct lib9p_srv_ctx *, uint8_t *, uint32_t, size_t) { assert_notreached("not a directory"); }
+ static lo_interface lib9p_srv_dio NAM##_dopen (TYP *, struct lib9p_srv_ctx *) { assert_notreached("not a directory"); }
#define LIB9P_SRV_NOTFILE(TYP, NAM) \
- static uint32_t NAM##_pread (TYP *, struct lib9p_srv_ctx *, void *, uint32_t, uint64_t) { assert_notreached("not a file"); } \
- static uint32_t NAM##_pwrite(TYP *, struct lib9p_srv_ctx *, void *, uint32_t, uint64_t) { assert_notreached("not a file"); }
+ static lo_interface lib9p_srv_fio NAM##_fopen (TYP *, struct lib9p_srv_ctx *, bool, bool, bool) { assert_notreached("not a file"); }
/* main server entrypoints ****************************************************/
@@ -103,16 +148,32 @@ struct lib9p_srv {
};
/**
+ * In an infinite loop, accept a connection and read messages from it until
+ * close; dispatching requests to a pool of lib9p_srv_write_cr() coroutines
+ * with the same `srv`.
+ *
* Will just close the connection if a T-message has a size[4] <7.
*
+ * @param srv: The server configuration and state; has an associated pool of
+ * lib9p_srv_write_cr() coroutines.
+ * @param listener: The listener object to accept connections from.
+ *
* @errno LINUX_EMSGSIZE T-message has size[4] bigger than max_msg_size
* @errno LINUX_EDOM Tversion specified an impossibly small max_msg_size
* @errno LINUX_EOPNOTSUPP T-message has an R-message type, or an unrecognized T-message type
* @errno LINUX_EBADMSG T-message has wrong size[4] for its content, or has invalid UTF-8
* @errno LINUX_ERANGE R-message does not fit into max_msg_size
*/
-
[[noreturn]] void lib9p_srv_read_cr(struct lib9p_srv *srv, lo_interface net_stream_listener listener);
+
+/**
+ * Service requests to the `struct lib9p_srv *srv` argument that have been
+ * read by lib9p_srv_read_cr().
+ *
+ * @param struct lib9p_srv *srv: The server configuration and state; has an
+ * associated pool of lib9p_srv_read_cr()
+ * coroutines.
+ */
COROUTINE lib9p_srv_write_cr(void *_srv);
#endif /* _LIB9P_SRV_H_ */
diff --git a/lib9p/internal.h b/lib9p/internal.h
deleted file mode 100644
index 801dc4c..0000000
--- a/lib9p/internal.h
+++ /dev/null
@@ -1,129 +0,0 @@
-/* lib9p/internal.h - Internal machinery shared between parts of lib9p
- *
- * Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
- * SPDX-License-Identifier: AGPL-3.0-or-later
- */
-
-#ifndef _LIB9P_INTERNAL_H_
-#define _LIB9P_INTERNAL_H_
-
-#include <stddef.h> /* for size_t */
-#include <limits.h> /* for SSIZE_MAX, not set by newlib */
-#ifndef SSIZE_MAX
-#define SSIZE_MAX (SIZE_MAX >> 1)
-#endif
-
-#include <libmisc/endian.h>
-#include <libmisc/macro.h>
-
-#include <lib9p/9p.h>
-
-/* configuration **************************************************************/
-
-#include "config.h"
-
-#ifndef CONFIG_9P_MAX_MSG_SIZE
- #error config.h must define CONFIG_9P_MAX_MSG_SIZE
-#endif
-#ifndef CONFIG_9P_MAX_HOSTMSG_SIZE
- #error config.h must define CONFIG_9P_MAX_HOSTMSG_SIZE
-#endif
-#ifndef CONFIG_9P_MAX_ERR_SIZE
- #error config.h must define CONFIG_9P_MAX_ERR_SIZE
-#endif
-
-static_assert(CONFIG_9P_MAX_ERR_SIZE <= UINT16_MAX);
-static_assert(CONFIG_9P_MAX_MSG_SIZE <= CONFIG_9P_MAX_HOSTMSG_SIZE);
-static_assert(CONFIG_9P_MAX_HOSTMSG_SIZE <= SSIZE_MAX);
-
-/* specialized contexts *******************************************************/
-
-struct _validate_ctx {
- /* input */
- struct lib9p_ctx *ctx;
- uint32_t net_size;
- uint8_t *net_bytes;
-
- /* output */
- uint32_t net_offset;
- /* Increment `host_extra` to pre-allocate space that is
- * "extra" beyond sizeof(). */
- size_t host_extra;
-};
-typedef bool (*_validate_fn_t)(struct _validate_ctx *ctx);
-
-struct _unmarshal_ctx {
- /* input */
- struct lib9p_ctx *ctx;
- uint8_t *net_bytes;
-
- /* output */
- uint32_t net_offset;
- /* `extra` points to the beginning of unallocated space. */
- void *extra;
-};
-typedef void (*_unmarshal_fn_t)(struct _unmarshal_ctx *ctx, void *out);
-
-struct _marshal_ctx {
- /* input */
- struct lib9p_ctx *ctx;
-
- /* output */
- size_t net_iov_cnt;
- struct iovec *net_iov;
- size_t net_copied_size;
- uint8_t *net_copied;
-};
-typedef bool (*_marshal_fn_t)(struct _marshal_ctx *ctx, void *host_val);
-
-/* tables / exports ***********************************************************/
-
-struct _lib9p_recv_tentry {
- size_t basesize;
- _validate_fn_t validate;
- _unmarshal_fn_t unmarshal;
-};
-
-struct _lib9p_send_tentry {
- _marshal_fn_t marshal;
-};
-
-extern const char *const _lib9p_table_ver_name[LIB9P_VER_NUM];
-extern const char *const _lib9p_table_msg_name[LIB9P_VER_NUM][0x100];
-extern const uint32_t _lib9p_table_msg_min_size[LIB9P_VER_NUM];
-extern const struct _lib9p_recv_tentry _lib9p_table_Tmsg_recv[LIB9P_VER_NUM][0x80];
-extern const struct _lib9p_recv_tentry _lib9p_table_Rmsg_recv[LIB9P_VER_NUM][0x80];
-extern const struct _lib9p_send_tentry _lib9p_table_Tmsg_send[LIB9P_VER_NUM][0x80];
-extern const struct _lib9p_send_tentry _lib9p_table_Rmsg_send[LIB9P_VER_NUM][0x80];
-
-bool _lib9p_stat_validate(struct _validate_ctx *ctx);
-void _lib9p_stat_unmarshal(struct _unmarshal_ctx *ctx, struct lib9p_stat *out);
-bool _lib9p_stat_marshal(struct _marshal_ctx *ctx, struct lib9p_stat *val);
-
-/* unmarshal utilities ********************************************************/
-
-static inline bool _is_valid_utf8(uint8_t *str, size_t len, bool forbid_nul) {
- uint32_t ch;
- uint8_t chlen;
- assert(str);
- for (size_t pos = 0; pos < len;) {
- if ((str[pos] & 0b10000000) == 0b00000000) { ch = str[pos] & 0b01111111; chlen = 1; }
- else if ((str[pos] & 0b11100000) == 0b11000000) { ch = str[pos] & 0b00011111; chlen = 2; }
- else if ((str[pos] & 0b11110000) == 0b11100000) { ch = str[pos] & 0b00001111; chlen = 3; }
- else if ((str[pos] & 0b11111000) == 0b11110000) { ch = str[pos] & 0b00000111; chlen = 4; }
- else return false;
- if ((ch == 0 && (chlen != 1 || forbid_nul)) || pos + chlen > len) return false;
- for (uint8_t i = 1; i < chlen; i++) {
- if ((str[pos+i] & 0b11000000) != 0b10000000) return false;
- ch = (ch << 6) | (str[pos+i] & 0b00111111);
- }
- if (ch > 0x10FFFF) return false;
- pos += chlen;
- }
- return true;
-}
-
-#define is_valid_utf8(str, len) _is_valid_utf8(str, len, false)
-#define is_valid_utf8_without_nul(str, len) _is_valid_utf8(str, len, true)
-
-#endif /* _LIB9P_INTERNAL_H_ */
diff --git a/lib9p/map.h b/lib9p/map.h
index ab9564f..c5eab0f 100644
--- a/lib9p/map.h
+++ b/lib9p/map.h
@@ -4,8 +4,6 @@
* SPDX-License-Identifier: AGPL-3.0-or-later
*/
-#include "internal.h"
-
/**
* `#define` `NAME`, `KEY_T`, `VAL_T`, and `CAP`; then `#include
* "map.h".
diff --git a/lib9p/proto.gen b/lib9p/proto.gen
new file mode 100755
index 0000000..60f1347
--- /dev/null
+++ b/lib9p/proto.gen
@@ -0,0 +1,15 @@
+#!/usr/bin/env python
+# lib9p/proto.gen - Generate C marshalers/unmarshalers for .9p files
+# defining 9P protocol variants.
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import os.path
+import sys
+
+sys.path.insert(0, os.path.normpath(os.path.join(__file__, "..")))
+import protogen # pylint: disable=wrong-import-position
+
+if __name__ == "__main__":
+ protogen.main()
diff --git a/lib9p/protogen/__init__.py b/lib9p/protogen/__init__.py
new file mode 100644
index 0000000..c2c6173
--- /dev/null
+++ b/lib9p/protogen/__init__.py
@@ -0,0 +1,57 @@
+# lib9p/protogen/__init__.py - Generate C marshalers/unmarshalers for
+# .9p files defining 9P protocol variants
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import os.path
+import sys
+import typing
+
+import idl
+
+from . import c, h
+
+# pylint: disable=unused-variable
+__all__ = ["main"]
+
+
+def main() -> None:
+ if typing.TYPE_CHECKING:
+
+ class ANSIColors:
+ MAGENTA = "\x1b[35m"
+ RED = "\x1b[31m"
+ RESET = "\x1b[0m"
+
+ else:
+ from _colorize import ANSIColors # Present in Python 3.13+
+
+ if len(sys.argv) < 2:
+ raise ValueError("requires at least 1 .9p filename")
+ parser = idl.Parser()
+ for txtname in sys.argv[1:]:
+ try:
+ parser.parse_file(txtname)
+ except SyntaxError as e:
+ print(
+ f"{ANSIColors.RED}{e.filename}{ANSIColors.RESET}:{ANSIColors.MAGENTA}{e.lineno}{ANSIColors.RESET}: {e.msg}",
+ file=sys.stderr,
+ )
+ assert e.text
+ print(f"\t{e.text}", file=sys.stderr)
+ text_suffix = e.text.lstrip()
+ text_prefix = e.text[: -len(text_suffix)]
+ print(
+ f"\t{text_prefix}{ANSIColors.RED}{'~'*len(text_suffix)}{ANSIColors.RESET}",
+ file=sys.stderr,
+ )
+ sys.exit(2)
+ versions, typs = parser.all()
+ outdir = os.path.normpath(os.path.join(sys.argv[0], ".."))
+ with open(
+ os.path.join(outdir, "include/lib9p/9p.generated.h"), "w", encoding="utf-8"
+ ) as fh:
+ fh.write(h.gen_h(versions, typs))
+ with open(os.path.join(outdir, "9p.generated.c"), "w", encoding="utf-8") as fh:
+ fh.write(c.gen_c(versions, typs))
diff --git a/lib9p/protogen/c.py b/lib9p/protogen/c.py
new file mode 100644
index 0000000..a6824ce
--- /dev/null
+++ b/lib9p/protogen/c.py
@@ -0,0 +1,201 @@
+# lib9p/protogen/c.py - Generate 9p.generated.c
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import sys
+
+import idl
+
+from . import c9util, c_format, c_marshal, c_unmarshal, c_validate, cutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+
+# pylint: disable=unused-variable
+__all__ = ["gen_c"]
+
+
+def gen_c(versions: set[str], typs: list[idl.UserType]) -> str:
+ cutil.ifdef_init()
+
+ ret = f"""/* Generated by `{' '.join(sys.argv)}`. DO NOT EDIT! */
+
+#include <stdbool.h>
+#include <stddef.h> /* for size_t */
+#include <inttypes.h> /* for PRI* macros */
+#include <string.h> /* for memset() */
+
+#include <libmisc/assert.h>
+#include <libmisc/endian.h>
+
+#include <lib9p/9p.h>
+
+#include "tables.h"
+#include "utf8.h"
+"""
+ # libobj vtables ###########################################################
+ ret += """
+/* libobj vtables *************************************************************/
+"""
+ for typ in typs:
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ ret += f"LO_IMPLEMENTATION_C(fmt_formatter, {c9util.typename(typ)}, {c9util.basename(typ)}, static);\n"
+ ret += cutil.ifdef_pop(0)
+
+ # utilities ################################################################
+ ret += """
+/* utilities ******************************************************************/
+"""
+
+ id2typ: dict[int, idl.Message] = {}
+ for msg in [msg for msg in typs if isinstance(msg, idl.Message)]:
+ id2typ[msg.msgid] = msg
+
+ for v in sorted(versions):
+ ret += f"#if CONFIG_9P_ENABLE_{v.replace('.', '_')}\n"
+ ret += (
+ f"\t#define _is_ver_{v.replace('.', '_')}(v) (v == {c9util.ver_enum(v)})\n"
+ )
+ ret += "#else\n"
+ ret += f"\t#define _is_ver_{v.replace('.', '_')}(v) false\n"
+ ret += "#endif\n"
+ ret += "\n"
+ ret += "/**\n"
+ ret += f" * is_ver(ctx, ver) is essentially `(ctx->version == {c9util.Ident('VER_')}##ver)`, but\n"
+ ret += f" * compiles correctly (to `false`) even if `{c9util.Ident('VER_')}##ver` isn't defined\n"
+ ret += " * (because `!CONFIG_9P_ENABLE_##ver`). This is useful when `||`ing\n"
+ ret += " * several version checks together.\n"
+ ret += " */\n"
+ ret += "#define is_ver(ctx, ver) _is_ver_##ver((ctx)->version)\n"
+
+ # bitmasks #################################################################
+ ret += """
+/* bitmasks *******************************************************************/
+"""
+ for typ in typs:
+ if not isinstance(typ, idl.Bitfield):
+ continue
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ ret += f"static const {c9util.typename(typ)} {typ.typname}_masks[{c9util.ver_enum('NUM')}] = {{\n"
+ verwidth = max(len(ver) for ver in versions)
+ for ver in sorted(versions):
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef({ver}))
+ ret += (
+ f"\t[{c9util.ver_enum(ver)}]{' '*(verwidth-len(ver))} = 0b"
+ + "".join(
+ (
+ "1"
+ if (bit.cat == "USED" or isinstance(bit.cat, idl.BitNum))
+ and ver in bit.in_versions
+ else "0"
+ )
+ for bit in reversed(typ.bits)
+ )
+ + ",\n"
+ )
+ ret += cutil.ifdef_pop(1)
+ ret += "};\n"
+ ret += cutil.ifdef_pop(0)
+
+ # validate_* ###############################################################
+ ret += c_validate.gen_c_validate(versions, typs)
+
+ # unmarshal_* ##############################################################
+ ret += c_unmarshal.gen_c_unmarshal(versions, typs)
+
+ # marshal_* ################################################################
+ ret += c_marshal.gen_c_marshal(versions, typs)
+
+ # *_format #################################################################
+ ret += c_format.gen_c_format(versions, typs)
+
+ # tables.h #################################################################
+ ret += """
+/* tables.h *******************************************************************/
+"""
+
+ ret += "\n"
+ ret += f"const struct {c9util.ident('_ver_tentry')} {c9util.ident('_table_ver')}[{c9util.ver_enum('NUM')}] = {{\n"
+ rerror = next(typ for typ in typs if typ.typname == "Rerror")
+ for ver in ["unknown", *sorted(versions)]:
+ if ver == "unknown":
+ min_msg_size = rerror.min_size("9P2000") # SPECIAL (initialization)
+ else:
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef({ver}))
+ min_msg_size = rerror.min_size(ver)
+ ret += f'\t[{c9util.ver_enum(ver)}] = {{.name="{ver}", .min_msg_size={min_msg_size}}},\n'
+ ret += cutil.ifdef_pop(0)
+ ret += "};\n"
+
+ def msg_table(
+ cstruct: str, cname: str, each: str, _range: tuple[int, int, int]
+ ) -> str:
+ ret = f"const struct {c9util.ident(cstruct)} {c9util.ident(cname)}[{c9util.ver_enum('NUM')}][{hex(len(range(*_range)))}] = {{\n"
+ for ver in ["unknown", *sorted(versions)]:
+ if ver != "unknown":
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef({ver}))
+ ret += f"\t[{c9util.ver_enum(ver)}] = {{\n"
+ for n in range(*_range):
+ xmsg: idl.Message | None = id2typ.get(n, None)
+ if xmsg:
+ if ver == "unknown": # SPECIAL (initialization)
+ if xmsg.typname not in ["Tversion", "Rversion", "Rerror"]:
+ xmsg = None
+ else:
+ if ver not in xmsg.in_versions:
+ xmsg = None
+ if xmsg:
+ ret += f"\t\t{each}({xmsg.typname}),\n"
+ ret += "\t},\n"
+ ret += cutil.ifdef_pop(0)
+ ret += "};\n"
+ return ret
+
+ ret += "\n"
+ ret += cutil.macro(
+ f"#define _MSG(typ) [{c9util.Ident('TYP_')}##typ] = {{\n"
+ f"\t\t.name = #typ,\n"
+ f"\t\t.box_as_fmt_formatter = (_box_as_fmt_formatter_fn_t)lo_box_{c9util.ident('msg_')}##typ##_as_fmt_formatter,\n"
+ f"\t}}\n"
+ )
+ ret += msg_table("_msg_tentry", "_table_msg", "_MSG", (0, 0x100, 1))
+
+ ret += "\n"
+ ret += cutil.macro(
+ f"#define _MSG_RECV(typ) [{c9util.Ident('TYP_')}##typ/2] = {{\n"
+ f"\t\t.validate = validate_##typ,\n"
+ f"\t\t.unmarshal = (_unmarshal_fn_t)unmarshal_##typ,\n"
+ f"\t}}\n"
+ )
+ ret += cutil.macro(
+ f"#define _MSG_SEND(typ) [{c9util.Ident('TYP_')}##typ/2] = {{\n"
+ f"\t\t.marshal = (_marshal_fn_t)marshal_##typ,\n"
+ f"\t}}\n"
+ )
+ ret += "\n"
+ ret += msg_table("_recv_tentry", "_table_Tmsg_recv", "_MSG_RECV", (0, 0x100, 2))
+ ret += "\n"
+ ret += msg_table("_recv_tentry", "_table_Rmsg_recv", "_MSG_RECV", (1, 0x100, 2))
+ ret += "\n"
+ ret += msg_table("_send_tentry", "_table_Tmsg_send", "_MSG_SEND", (0, 0x100, 2))
+ ret += "\n"
+ ret += msg_table("_send_tentry", "_table_Rmsg_send", "_MSG_SEND", (1, 0x100, 2))
+
+ ret += f"""
+LM_FLATTEN ssize_t {c9util.ident('_stat_validate')}(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes, uint32_t *ret_net_size) {{
+\treturn validate_stat(ctx, net_size, net_bytes, ret_net_size);
+}}
+LM_FLATTEN void {c9util.ident('_stat_unmarshal')}(struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out) {{
+\tunmarshal_stat(ctx, net_bytes, out);
+}}
+LM_FLATTEN bool {c9util.ident('_stat_marshal')}(struct lib9p_ctx *ctx, struct {c9util.ident('stat')} *val, struct _marshal_ret *ret) {{
+\treturn marshal_stat(ctx, val, ret);
+}}
+"""
+
+ ############################################################################
+ return ret
diff --git a/lib9p/protogen/c9util.py b/lib9p/protogen/c9util.py
new file mode 100644
index 0000000..cf91951
--- /dev/null
+++ b/lib9p/protogen/c9util.py
@@ -0,0 +1,134 @@
+# lib9p/protogen/c9util.py - Utilities for generating lib9p-specific C
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import re
+import typing
+
+import idl
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+# pylint: disable=unused-variable
+__all__ = [
+ "add_prefix",
+ "ident",
+ "Ident",
+ "IDENT",
+ "ver_enum",
+ "ver_ifdef",
+ "ver_cond",
+ "typename",
+ "idl_expr",
+]
+
+# idents #######################################################################
+
+
+def add_prefix(p: str, s: str) -> str:
+ if s.startswith("_"):
+ return "_" + p + s[1:]
+ return p + s
+
+
+def _ident(p: str, s: str) -> str:
+ return add_prefix(p, s.replace(".", "_"))
+
+
+def ident(s: str) -> str:
+ return _ident("lib9p_", s)
+
+
+def Ident(s: str) -> str:
+ return _ident("lib9p_".upper(), s)
+
+
+def IDENT(s: str) -> str:
+ return _ident("lib9p_", s).upper()
+
+
+# versions #####################################################################
+
+
+def ver_enum(ver: str) -> str:
+ return Ident("VER_" + ver)
+
+
+def ver_ifdef(versions: typing.Collection[str]) -> str:
+ return " || ".join(
+ f"CONFIG_9P_ENABLE_{v.replace('.', '_')}" for v in sorted(versions)
+ )
+
+
+def ver_cond(versions: typing.Collection[str]) -> str:
+ if len(versions) == 1:
+ v = next(v for v in versions)
+ return f"is_ver(ctx, {v.replace('.', '_')})"
+ return "( " + (" || ".join(ver_cond({v}) for v in sorted(versions))) + " )"
+
+
+# misc #########################################################################
+
+
+def basename(typ: idl.UserType) -> str:
+ match typ:
+ case idl.Number():
+ return ident(typ.typname)
+ case idl.Bitfield():
+ return ident(typ.typname)
+ case idl.Message():
+ return ident(f"msg_{typ.typname}")
+ case idl.Struct():
+ return ident(typ.typname)
+ case _:
+ raise ValueError(f"not a defined type: {typ.__class__.__name__}")
+
+
+def typename(typ: idl.Type, parent: idl.StructMember | None = None) -> str:
+ match typ:
+ case idl.Primitive():
+ if typ.value == 1 and parent and parent.cnt: # SPECIAL (string)
+ return "[[gnu::nonstring]] char"
+ return f"uint{typ.value*8}_t"
+ case idl.Number():
+ return f"{basename(typ)}_t"
+ case idl.Bitfield():
+ return f"{basename(typ)}_t"
+ case idl.Message():
+ return f"struct {basename(typ)}"
+ case idl.Struct():
+ return f"struct {basename(typ)}"
+ case _:
+ raise ValueError(f"not a type: {typ.__class__.__name__}")
+
+
+def idl_expr(
+ expr: idl.Expr, lookup_sym: typing.Callable[[str], str], bitwidth: int = 0
+) -> str:
+ ret: list[str] = []
+ for tok in expr.tokens:
+ match tok:
+ case idl.ExprOp():
+ ret.append(tok.op)
+ case idl.ExprLit():
+ if bitwidth:
+ ret.append(f"{tok.val:#0{bitwidth}b}")
+ else:
+ ret.append(str(tok.val))
+ case idl.ExprSym():
+ if m := re.fullmatch(r"^u(8|16|32|64)_max$", tok.symname):
+ ret.append(f"UINT{m.group(1)}_MAX")
+ elif m := re.fullmatch(r"^s(8|16|32|64)_max$", tok.symname):
+ ret.append(f"INT{m.group(1)}_MAX")
+ else:
+ ret.append(lookup_sym(tok.symname))
+ case idl.ExprOff():
+ ret.append(lookup_sym("&" + tok.membname))
+ case idl.ExprNum():
+ ret.append(Ident(add_prefix(f"{tok.numname}_".upper(), tok.valname)))
+ case _:
+ assert False
+ return " ".join(ret)
diff --git a/lib9p/protogen/c_format.py b/lib9p/protogen/c_format.py
new file mode 100644
index 0000000..a1bcbf3
--- /dev/null
+++ b/lib9p/protogen/c_format.py
@@ -0,0 +1,142 @@
+# lib9p/protogen/c_format.py - Generate C pretty-print functions
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+
+import idl
+
+from . import c9util, cutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+# pylint: disable=unused-variable
+__all__ = ["gen_c_format"]
+
+
+def bf_numname(typ: idl.Bitfield, num: idl.BitNum, base: str) -> str:
+ prefix = f"{typ.typname}_{num.numname}_".upper()
+ return c9util.Ident(c9util.add_prefix(prefix, base))
+
+
+def gen_c_format(versions: set[str], typs: list[idl.UserType]) -> str:
+ ret = """
+/* *_format *******************************************************************/
+"""
+ for typ in typs:
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ ret += f"static void {c9util.basename(typ)}_format({c9util.typename(typ)} *self, struct fmt_state *state) {{\n"
+ match typ:
+ case idl.Number():
+ if typ.vals:
+ ret += "\tswitch (*self) {\n"
+ for name in typ.vals:
+ ret += f"\tcase {c9util.Ident(c9util.add_prefix(f'{typ.typname}_'.upper(), name))}:\n"
+ ret += f'\t\tfmt_state_puts(state, "{name}");\n'
+ ret += "\t\tbreak;\n"
+ ret += "\tdefault:\n"
+ ret += f'\t\tfmt_state_printf(state, "%"PRIu{typ.static_size*8}, *self);\n'
+ ret += "\t}\n"
+ else:
+ ret += f'\t\tfmt_state_printf(state, "%"PRIu{typ.static_size*8}, *self);\n'
+ case idl.Bitfield():
+ val = "*self"
+ if typ.typname == "dm": # SPECIAL (pretty file permissions)
+ val = f"(*self & ~(({c9util.typename(typ)})0777))"
+ ret += "\tbool empty = true;\n"
+ ret += "\tfmt_state_putchar(state, '(');\n"
+ nums: set[str] = set()
+
+ for bit in reversed(typ.bits):
+ match bit.cat:
+ case "UNUSED" | "USED" | "RESERVED":
+ if bit.cat == "UNUSED":
+ bitname = f"1<<{bit.num}"
+ else:
+ bitname = bit.bitname
+ ret += f"\tif ({val} & (UINT{typ.static_size*8}_C(1)<<{bit.num})) {{\n"
+ ret += "\t\tif (!empty)\n"
+ ret += "\t\t\tfmt_state_putchar(state, '|');\n"
+ ret += f'\t\tfmt_state_puts(state, "{bitname}");\n'
+ ret += "\t\tempty = false;\n"
+ ret += "\t}\n"
+ case idl.BitNum():
+ if bit.cat.numname in nums:
+ continue
+ ret += f"\tswitch ({val} & {bf_numname(typ, bit.cat, 'MASK')}) {{\n"
+ for name in bit.cat.vals:
+ ret += f"\tcase {bf_numname(typ, bit.cat, name)}:\n"
+ bitname = c9util.add_prefix(
+ f"{bit.cat.numname}_".upper(), name
+ )
+ ret += "\t\tif (!empty)\n"
+ ret += "\t\t\tfmt_state_putchar(state, '|');\n"
+ ret += f'\t\tfmt_state_puts(state, "{bitname}");\n'
+ ret += "\t\tempty = false;\n"
+ ret += "\t\tbreak;\n"
+ ret += "\tdefault:\n"
+ ret += "\t\tif (!empty)\n"
+ ret += "\t\t\tfmt_state_putchar(state, '|');\n"
+ ret += f'\t\tfmt_state_printf(state, "%"PRIu{typ.static_size*8}, {val} & {bf_numname(typ, bit.cat, 'MASK')});\n'
+ ret += "\t\tempty = false;\n"
+ ret += "\t}\n"
+ nums.add(bit.cat.numname)
+ if typ.typname == "dm": # SPECIAL (pretty file permissions)
+ ret += "\tif (!empty)\n"
+ ret += "\t\tfmt_state_putchar(state, '|');\n"
+ ret += f'\tfmt_state_printf(state, "%#04"PRIo{typ.static_size*8}, *self & 0777);\n'
+ else:
+ ret += "\tif (empty)\n"
+ ret += "\t\tfmt_state_putchar(state, '0');\n"
+ ret += "\tfmt_state_putchar(state, ')');\n"
+ case idl.Struct(typname="s"): # SPECIAL(string)
+ ret += "\t/* https://gcc.gnu.org/bugzilla/show_bug.cgi?id=47781 */\n"
+ ret += "#pragma GCC diagnostic push\n"
+ ret += '#pragma GCC diagnostic ignored "-Wformat"\n'
+ ret += '#pragma GCC diagnostic ignored "-Wformat-extra-args"\n'
+ ret += '\tfmt_state_printf(state, "%.*q", self->len, self->utf8);\n'
+ ret += "#pragma GCC diagnostic pop\n"
+ case idl.Struct(): # and idl.Message():
+ if isinstance(typ, idl.Message):
+ ret += f'\tfmt_state_puts(state, "{typ.typname} {{");\n'
+ else:
+ ret += "\tfmt_state_putchar(state, '{');\n"
+ for member in typ.members:
+ if member.val:
+ continue
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(member.in_versions))
+ if member.cnt:
+ if member.typ.static_size == 1: # SPECIAL (data)
+ ret += f'\tfmt_state_puts(state, " {member.membname}=<bytedata>");\n'
+ continue
+ if isinstance(member.cnt, int):
+ cnt_str = str(member.cnt)
+ cnt_typ = "size_t"
+ else:
+ cnt_str = f"self->{member.cnt.membname}"
+ cnt_typ = c9util.typename(member.cnt.typ)
+ ret += f'\tfmt_state_puts(state, " {member.membname}=[");\n'
+ ret += f"\tfor ({cnt_typ} i = 0; i < {cnt_str}; i++) {{\n"
+ ret += "\t\tif (i)\n"
+ ret += '\t\t\tfmt_state_puts(state, ", ");\n'
+ if isinstance(member.typ, idl.Primitive):
+ ret += f'\t\tfmt_state_printf(state, "%"PRIu{member.typ.static_size*8}, self->{member.membname}[i]);\n'
+ else:
+ ret += f"\t\t{c9util.basename(member.typ)}_format(&self->{member.membname}[i], state);\n"
+ ret += "\t}\n"
+ ret += '\tfmt_state_puts(state, " ]");\n'
+ else:
+ ret += f'\tfmt_state_puts(state, " {member.membname}=");\n'
+ if isinstance(member.typ, idl.Primitive):
+ ret += f'\tfmt_state_printf(state, "%"PRIu{member.typ.static_size*8}, self->{member.membname});\n'
+ else:
+ ret += f"\t{c9util.basename(member.typ)}_format(&self->{member.membname}, state);\n"
+ ret += cutil.ifdef_pop(1)
+ ret += '\tfmt_state_puts(state, " }");\n'
+ ret += "}\n"
+ ret += cutil.ifdef_pop(0)
+
+ return ret
diff --git a/lib9p/protogen/c_marshal.py b/lib9p/protogen/c_marshal.py
new file mode 100644
index 0000000..4dab864
--- /dev/null
+++ b/lib9p/protogen/c_marshal.py
@@ -0,0 +1,403 @@
+# lib9p/protogen/c_marshal.py - Generate C marshal functions
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import typing
+
+import idl
+
+from . import c9util, cutil, idlutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+
+# pylint: disable=unused-variable
+__all__ = ["gen_c_marshal"]
+
+# get_offset_expr() ############################################################
+
+
+class OffsetExpr:
+ static: int
+ cond: dict[frozenset[str], "OffsetExpr"]
+ rep: list[tuple[idlutil.Path | int, "OffsetExpr"]]
+
+ def __init__(self) -> None:
+ self.static = 0
+ self.rep = []
+ self.cond = {}
+
+ def add(self, other: "OffsetExpr") -> None:
+ self.static += other.static
+ self.rep += other.rep
+ for k, v in other.cond.items():
+ if k in self.cond:
+ self.cond[k].add(v)
+ else:
+ self.cond[k] = v
+
+ def gen_c(
+ self,
+ dsttyp: str,
+ dstvar: str,
+ root: str,
+ indent_depth: int,
+ loop_depth: int,
+ ) -> str:
+ oneline: list[str] = []
+ multiline = ""
+ if self.static:
+ oneline.append(str(self.static))
+ for cnt, sub in self.rep:
+ if isinstance(cnt, int):
+ cnt_str = str(cnt)
+ cnt_typ = "size_t"
+ else:
+ cnt_str = cnt.c_str(root)
+ cnt_typ = c9util.typename(cnt.elems[-1].typ)
+ if not sub.cond and not sub.rep:
+ if sub.static == 1:
+ oneline.append(cnt_str)
+ else:
+ oneline.append(f"({cnt_str})*{sub.static}")
+ continue
+ loopvar = chr(ord("i") + loop_depth)
+ multiline += f"{'\t'*indent_depth}for ({cnt_typ} {loopvar} = 0; {loopvar} < {cnt_str}; {loopvar}++) {{\n"
+ multiline += sub.gen_c("", dstvar, root, indent_depth + 1, loop_depth + 1)
+ multiline += f"{'\t'*indent_depth}}}\n"
+ for vers, sub in self.cond.items():
+ multiline += cutil.ifdef_push(indent_depth + 1, c9util.ver_ifdef(vers))
+ multiline += f"{'\t'*indent_depth}if {c9util.ver_cond(vers)} {{\n"
+ multiline += sub.gen_c("", dstvar, root, indent_depth + 1, loop_depth)
+ multiline += f"{'\t'*indent_depth}}}\n"
+ multiline += cutil.ifdef_pop(indent_depth)
+ ret = ""
+ if dsttyp:
+ if not oneline:
+ oneline.append("0")
+ ret += f"{'\t'*indent_depth}{dsttyp} {dstvar} = {' + '.join(oneline)};\n"
+ elif oneline:
+ ret += f"{'\t'*indent_depth}{dstvar} += {' + '.join(oneline)};\n"
+ ret += multiline
+ return ret
+
+
+type OffsetExprRecursion = typing.Callable[[idlutil.Path], idlutil.WalkCmd]
+
+
+def get_offset_expr(typ: idl.UserType, recurse: OffsetExprRecursion) -> OffsetExpr:
+ if not isinstance(typ, idl.Struct):
+ assert typ.static_size
+ ret = OffsetExpr()
+ ret.static = typ.static_size
+ return ret
+
+ class ExprStackItem(typing.NamedTuple):
+ path: idlutil.Path
+ expr: OffsetExpr
+ pop: typing.Callable[[], None]
+
+ expr_stack: list[ExprStackItem]
+
+ def pop_root() -> None:
+ assert False
+
+ def pop_cond() -> None:
+ nonlocal expr_stack
+ key = frozenset(expr_stack[-1].path.elems[-1].in_versions)
+ if key in expr_stack[-2].expr.cond:
+ expr_stack[-2].expr.cond[key].add(expr_stack[-1].expr)
+ else:
+ expr_stack[-2].expr.cond[key] = expr_stack[-1].expr
+ expr_stack = expr_stack[:-1]
+
+ def pop_rep() -> None:
+ nonlocal expr_stack
+ member_path = expr_stack[-1].path
+ member = member_path.elems[-1]
+ assert member.cnt
+ cnt: idlutil.Path | int
+ if isinstance(member.cnt, int):
+ cnt = member.cnt
+ else:
+ cnt = member_path.parent().add(member.cnt)
+ expr_stack[-2].expr.rep.append((cnt, expr_stack[-1].expr))
+ expr_stack = expr_stack[:-1]
+
+ def handle(
+ path: idlutil.Path,
+ ) -> tuple[idlutil.WalkCmd, typing.Callable[[], None] | None]:
+ nonlocal recurse
+
+ ret = recurse(path)
+ if ret != idlutil.WalkCmd.KEEP_GOING:
+ return ret, None
+
+ nonlocal expr_stack
+ expr_stack_len = len(expr_stack)
+
+ def pop() -> None:
+ nonlocal expr_stack
+ nonlocal expr_stack_len
+ while len(expr_stack) > expr_stack_len:
+ expr_stack[-1].pop()
+
+ if path.elems:
+ child = path.elems[-1]
+ parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
+ if child.in_versions < parent.in_versions:
+ expr_stack.append(
+ ExprStackItem(path=path, expr=OffsetExpr(), pop=pop_cond)
+ )
+ if child.cnt:
+ expr_stack.append(
+ ExprStackItem(path=path, expr=OffsetExpr(), pop=pop_rep)
+ )
+ if not isinstance(child.typ, idl.Struct):
+ assert child.typ.static_size
+ expr_stack[-1].expr.static += child.typ.static_size
+ return ret, pop
+
+ expr_stack = [
+ ExprStackItem(path=idlutil.Path(typ), expr=OffsetExpr(), pop=pop_root)
+ ]
+ idlutil.walk(typ, handle)
+ return expr_stack[0].expr
+
+
+def go_to_end(path: idlutil.Path) -> idlutil.WalkCmd:
+ return idlutil.WalkCmd.KEEP_GOING
+
+
+def go_to_tok(name: str) -> typing.Callable[[idlutil.Path], idlutil.WalkCmd]:
+ def ret(path: idlutil.Path) -> idlutil.WalkCmd:
+ if len(path.elems) == 1 and path.elems[0].membname == name:
+ return idlutil.WalkCmd.ABORT
+ return idlutil.WalkCmd.KEEP_GOING
+
+ return ret
+
+
+# Generate .c ##################################################################
+
+
+def gen_c_marshal(versions: set[str], typs: list[idl.UserType]) -> str:
+ ret = """
+/* marshal_* ******************************************************************/
+
+"""
+ ret += cutil.macro(
+ "#define MARSHAL_BYTES_ZEROCOPY(ctx, data, len)\n"
+ "\tif (ret->net_iov[ret->net_iov_cnt-1].iov_len)\n"
+ "\t\tret->net_iov_cnt++;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_base = data;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len = len;\n"
+ "\tret->net_iov_cnt++;\n"
+ )
+ ret += cutil.macro(
+ "#define MARSHAL_BYTES(ctx, data, len)\n"
+ "\tif (!ret->net_iov[ret->net_iov_cnt-1].iov_base)\n"
+ "\t\tret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size];\n"
+ "\tmemcpy(&ret->net_copied[ret->net_copied_size], data, len);\n"
+ "\tret->net_copied_size += len;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len += len;\n"
+ )
+ ret += cutil.macro(
+ "#define MARSHAL_U8LE(ctx, val)\n"
+ "\tif (!ret->net_iov[ret->net_iov_cnt-1].iov_base)\n"
+ "\t\tret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size];\n"
+ "\tret->net_copied[ret->net_copied_size] = val;\n"
+ "\tret->net_copied_size += 1;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len += 1;\n"
+ )
+ ret += cutil.macro(
+ "#define MARSHAL_U16LE(ctx, val)\n"
+ "\tif (!ret->net_iov[ret->net_iov_cnt-1].iov_base)\n"
+ "\t\tret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size];\n"
+ "\tuint16le_encode(&ret->net_copied[ret->net_copied_size], val);\n"
+ "\tret->net_copied_size += 2;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len += 2;\n"
+ )
+ ret += cutil.macro(
+ "#define MARSHAL_U32LE(ctx, val)\n"
+ "\tif (!ret->net_iov[ret->net_iov_cnt-1].iov_base)\n"
+ "\t\tret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size];\n"
+ "\tuint32le_encode(&ret->net_copied[ret->net_copied_size], val);\n"
+ "\tret->net_copied_size += 4;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len += 4;\n"
+ )
+ ret += cutil.macro(
+ "#define MARSHAL_U64LE(ctx, val)\n"
+ "\tif (!ret->net_iov[ret->net_iov_cnt-1].iov_base)\n"
+ "\t\tret->net_iov[ret->net_iov_cnt-1].iov_base = &ret->net_copied[ret->net_copied_size];\n"
+ "\tuint64le_encode(&ret->net_copied[ret->net_copied_size], val);\n"
+ "\tret->net_copied_size += 8;\n"
+ "\tret->net_iov[ret->net_iov_cnt-1].iov_len += 8;\n"
+ )
+
+ class IndentLevel(typing.NamedTuple):
+ ifdef: bool # whether this is both `{` and `#if`, or just `{`
+
+ indent_stack: list[IndentLevel]
+
+ def ifdef_lvl() -> int:
+ return sum(1 if lvl.ifdef else 0 for lvl in indent_stack)
+
+ def indent_lvl() -> int:
+ return len(indent_stack)
+
+ max_size: int
+
+ def handle(
+ path: idlutil.Path,
+ ) -> tuple[idlutil.WalkCmd, typing.Callable[[], None]]:
+ nonlocal ret
+ nonlocal indent_stack
+ nonlocal max_size
+ indent_stack_len = len(indent_stack)
+
+ def pop() -> None:
+ nonlocal ret
+ nonlocal indent_stack
+ nonlocal indent_stack_len
+ while len(indent_stack) > indent_stack_len:
+ if len(indent_stack) == indent_stack_len + 1 and indent_stack[-1].ifdef:
+ break
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+
+ loopdepth = sum(1 for elem in path.elems if elem.cnt)
+ struct = path.elems[-1].typ if path.elems else path.root
+ if isinstance(struct, idl.Struct):
+ offsets: list[str] = []
+ for member in struct.members:
+ if not member.val:
+ continue
+ for tok in member.val.tokens:
+ match tok:
+ case idl.ExprSym(symname="end"):
+ if tok.symname not in offsets:
+ offsets.append(tok.symname)
+ case idl.ExprOff():
+ if f"&{tok.membname}" not in offsets:
+ offsets.append(f"&{tok.membname}")
+ for name in offsets:
+ name_prefix = f"offsetof{''.join('_'+m.membname for m in path.elems)}_"
+ if name == "end":
+ if not path.elems:
+ if max_size > cutil.UINT32_MAX:
+ ret += f"{'\t'*indent_lvl()}uint32_t {name_prefix}end = (uint32_t)needed_size;\n"
+ else:
+ ret += f"{'\t'*indent_lvl()}uint32_t {name_prefix}end = needed_size;\n"
+ continue
+ recurse: OffsetExprRecursion = go_to_end
+ else:
+ assert name.startswith("&")
+ name = name[1:]
+ recurse = go_to_tok(name)
+ expr = get_offset_expr(struct, recurse)
+ expr_prefix = path.c_str("val->", loopdepth)
+ if not expr_prefix.endswith(">"):
+ expr_prefix += "."
+ ret += expr.gen_c(
+ "uint32_t",
+ name_prefix + name,
+ expr_prefix,
+ indent_lvl(),
+ loopdepth,
+ )
+ if not path.elems:
+ return idlutil.WalkCmd.KEEP_GOING, pop
+
+ child = path.elems[-1]
+ parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
+ if child.in_versions < parent.in_versions:
+ if line := cutil.ifdef_push(
+ ifdef_lvl() + 1, c9util.ver_ifdef(child.in_versions)
+ ):
+ ret += line
+ ret += (
+ f"{'\t'*indent_lvl()}if ({c9util.ver_cond(child.in_versions)}) {{\n"
+ )
+ indent_stack.append(IndentLevel(ifdef=True))
+ if child.cnt:
+ if isinstance(child.cnt, int):
+ cnt_str = str(child.cnt)
+ cnt_typ = "size_t"
+ else:
+ cnt_str = path.parent().add(child.cnt).c_str("val->")
+ cnt_typ = c9util.typename(child.cnt.typ)
+ if child.typ.static_size == 1: # SPECIAL (zerocopy)
+ if path.root.typname == "stat": # SPECIAL (stat)
+ ret += f"{'\t'*indent_lvl()}MARSHAL_BYTES(ctx, {path.c_str('val->')[:-3]}, {cnt_str});\n"
+ else:
+ ret += f"{'\t'*indent_lvl()}MARSHAL_BYTES_ZEROCOPY(ctx, {path.c_str('val->')[:-3]}, {cnt_str});\n"
+ return idlutil.WalkCmd.KEEP_GOING, pop
+ loopvar = chr(ord("i") + loopdepth - 1)
+ ret += f"{'\t'*indent_lvl()}for ({cnt_typ} {loopvar} = 0; {loopvar} < {cnt_str}; {loopvar}++) {{\n"
+ indent_stack.append(IndentLevel(ifdef=False))
+ if not isinstance(child.typ, idl.Struct):
+ if child.val:
+
+ def lookup_sym(sym: str) -> str:
+ nonlocal path
+ if sym.startswith("&"):
+ sym = sym[1:]
+ return f"offsetof{''.join('_'+m.membname for m in path.elems[:-1])}_{sym}"
+
+ val = c9util.idl_expr(child.val, lookup_sym)
+ else:
+ val = path.c_str("val->")
+ if isinstance(child.typ, idl.Bitfield):
+ val += f" & {child.typ.typname}_masks[ctx->version]"
+ ret += f"{'\t'*indent_lvl()}MARSHAL_U{child.typ.static_size*8}LE(ctx, {val});\n"
+ return idlutil.WalkCmd.KEEP_GOING, pop
+
+ for typ in typs:
+ if not (
+ isinstance(typ, idl.Message) or typ.typname == "stat"
+ ): # SPECIAL (include stat)
+ continue
+ assert isinstance(typ, idl.Struct)
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ ret += f"static bool marshal_{typ.typname}(struct lib9p_ctx *ctx, {c9util.typename(typ)} *val, struct _marshal_ret *ret) {{\n"
+
+ # Pass 1 - check size
+ max_size = max(typ.max_size(v) for v in typ.in_versions)
+
+ if max_size > cutil.UINT32_MAX: # SPECIAL (9P2000.e)
+ ret += get_offset_expr(typ, go_to_end).gen_c(
+ "uint64_t", "needed_size", "val->", 1, 0
+ )
+ ret += "\tif (needed_size > (uint64_t)(ctx->max_msg_size)) {\n"
+ else:
+ ret += get_offset_expr(typ, go_to_end).gen_c(
+ "uint32_t", "needed_size", "val->", 1, 0
+ )
+ ret += "\tif (needed_size > ctx->max_msg_size) {\n"
+ if isinstance(typ, idl.Message): # SPECIAL (disable for stat)
+ ret += '\t\tlib9p_errorf(ctx, LINUX_ERANGE, "%s message too large to marshal into %s limit (limit=%"PRIu32")",\n'
+ ret += f'\t\t\t"{typ.typname}",\n'
+ ret += f'\t\t\tctx->version ? "negotiated" : "{'client' if typ.msgid % 2 == 0 else 'server'}",\n'
+ ret += "\t\t\tctx->max_msg_size);\n"
+ ret += "\t\treturn true;\n"
+ ret += "\t}\n"
+
+ # Pass 2 - write data
+ indent_stack = [IndentLevel(ifdef=True)]
+ idlutil.walk(typ, handle)
+ while len(indent_stack) > 1:
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+
+ # Return
+ ret += "\treturn false;\n"
+ ret += "}\n"
+ ret += cutil.ifdef_pop(0)
+ return ret
diff --git a/lib9p/protogen/c_unmarshal.py b/lib9p/protogen/c_unmarshal.py
new file mode 100644
index 0000000..34635f9
--- /dev/null
+++ b/lib9p/protogen/c_unmarshal.py
@@ -0,0 +1,138 @@
+# lib9p/protogen/c_unmarshal.py - Generate C unmarshal functions
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import typing
+
+import idl
+
+from . import c9util, cutil, idlutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+
+# pylint: disable=unused-variable
+__all__ = ["gen_c_unmarshal"]
+
+
+def gen_c_unmarshal(versions: set[str], typs: list[idl.UserType]) -> str:
+ ret = """
+/* unmarshal_* ****************************************************************/
+
+"""
+ ret += cutil.macro(
+ "#define UNMARSHAL_BYTES(ctx, data_lvalue, len)\n"
+ "\tdata_lvalue = (char *)&net_bytes[net_offset];\n"
+ "\tnet_offset += len;\n"
+ )
+ ret += cutil.macro(
+ "#define UNMARSHAL_U8LE(ctx, val_lvalue)\n"
+ "\tval_lvalue = net_bytes[net_offset];\n"
+ "\tnet_offset += 1;\n"
+ )
+ ret += cutil.macro(
+ "#define UNMARSHAL_U16LE(ctx, val_lvalue)\n"
+ "\tval_lvalue = uint16le_decode(&net_bytes[net_offset]);\n"
+ "\tnet_offset += 2;\n"
+ )
+ ret += cutil.macro(
+ "#define UNMARSHAL_U32LE(ctx, val_lvalue)\n"
+ "\tval_lvalue = uint32le_decode(&net_bytes[net_offset]);\n"
+ "\tnet_offset += 4;\n"
+ )
+ ret += cutil.macro(
+ "#define UNMARSHAL_U64LE(ctx, val_lvalue)\n"
+ "\tval_lvalue = uint64le_decode(&net_bytes[net_offset]);\n"
+ "\tnet_offset += 8;\n"
+ )
+
+ class IndentLevel(typing.NamedTuple):
+ ifdef: bool # whether this is both `{` and `#if`, or just `{`
+
+ indent_stack: list[IndentLevel]
+
+ def ifdef_lvl() -> int:
+ return sum(1 if lvl.ifdef else 0 for lvl in indent_stack)
+
+ def indent_lvl() -> int:
+ return len(indent_stack)
+
+ def handle(
+ path: idlutil.Path,
+ ) -> tuple[idlutil.WalkCmd, typing.Callable[[], None]]:
+ nonlocal ret
+ nonlocal indent_stack
+ indent_stack_len = len(indent_stack)
+
+ def pop() -> None:
+ nonlocal ret
+ nonlocal indent_stack
+ nonlocal indent_stack_len
+ while len(indent_stack) > indent_stack_len:
+ if len(indent_stack) == indent_stack_len + 1 and indent_stack[-1].ifdef:
+ break
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+
+ if not path.elems:
+ return idlutil.WalkCmd.KEEP_GOING, pop
+
+ child = path.elems[-1]
+ parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
+ if child.in_versions < parent.in_versions:
+ if line := cutil.ifdef_push(
+ ifdef_lvl() + 1, c9util.ver_ifdef(child.in_versions)
+ ):
+ ret += line
+ ret += (
+ f"{'\t'*indent_lvl()}if ({c9util.ver_cond(child.in_versions)}) {{\n"
+ )
+ indent_stack.append(IndentLevel(ifdef=True))
+ if child.cnt:
+ if isinstance(child.cnt, int):
+ cnt_str = str(child.cnt)
+ cnt_typ = "size_t"
+ else:
+ cnt_str = path.parent().add(child.cnt).c_str("out->")
+ cnt_typ = c9util.typename(child.cnt.typ)
+ if child.typ.static_size == 1: # SPECIAL (zerocopy)
+ ret += f"{'\t'*indent_lvl()}UNMARSHAL_BYTES(ctx, {path.c_str('out->')[:-3]}, {cnt_str});\n"
+ return idlutil.WalkCmd.KEEP_GOING, pop
+ ret += f"{'\t'*indent_lvl()}{path.c_str('out->')[:-3]} = extra;\n"
+ ret += f"{'\t'*indent_lvl()}extra += sizeof({path.c_str('out->')[:-3]}[0]) * {cnt_str};\n"
+ loopdepth = sum(1 for elem in path.elems if elem.cnt)
+ loopvar = chr(ord("i") + loopdepth - 1)
+ ret += f"{'\t'*indent_lvl()}for ({cnt_typ} {loopvar} = 0; {loopvar} < {cnt_str}; {loopvar}++) {{\n"
+ indent_stack.append(IndentLevel(ifdef=False))
+ if not isinstance(child.typ, idl.Struct):
+ if child.val:
+ ret += f"{'\t'*indent_lvl()}net_offset += {child.typ.static_size};\n"
+ else:
+ ret += f"{'\t'*indent_lvl()}UNMARSHAL_U{child.typ.static_size*8}LE(ctx, {path.c_str('out->')});\n"
+ return idlutil.WalkCmd.KEEP_GOING, pop
+
+ for typ in typs:
+ if not (
+ isinstance(typ, idl.Message) or typ.typname == "stat"
+ ): # SPECIAL (include stat)
+ continue
+ assert isinstance(typ, idl.Struct)
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ ret += f"static void unmarshal_{typ.typname}([[gnu::unused]] struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out_buf) {{\n"
+ ret += f"\t{c9util.typename(typ)} *out = out_buf;\n"
+ ret += "\t[[gnu::unused]] void *extra = &out[1];\n"
+ ret += "\tuint32_t net_offset = 0;\n"
+
+ indent_stack = [IndentLevel(ifdef=True)]
+ idlutil.walk(typ, handle)
+ while len(indent_stack) > 0:
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef and indent_stack:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+ ret += cutil.ifdef_pop(0)
+ return ret
diff --git a/lib9p/protogen/c_validate.py b/lib9p/protogen/c_validate.py
new file mode 100644
index 0000000..535a750
--- /dev/null
+++ b/lib9p/protogen/c_validate.py
@@ -0,0 +1,299 @@
+# lib9p/protogen/c_validate.py - Generate C validation functions
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import typing
+
+import idl
+
+from . import c9util, cutil, idlutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+
+# pylint: disable=unused-variable
+__all__ = ["gen_c_validate"]
+
+
+def should_save_offset(parent: idl.Struct, child: idl.StructMember) -> bool:
+ if child.val or child.max or isinstance(child.typ, idl.Bitfield):
+ return True
+ for sibling in parent.members:
+ if sibling.val:
+ for tok in sibling.val.tokens:
+ if isinstance(tok, idl.ExprOff) and tok.membname == child.membname:
+ return True
+ if sibling.max:
+ for tok in sibling.max.tokens:
+ if isinstance(tok, idl.ExprOff) and tok.membname == child.membname:
+ return True
+ return False
+
+
+def should_save_end_offset(struct: idl.Struct) -> bool:
+ for memb in struct.members:
+ if memb.val:
+ for tok in memb.val.tokens:
+ if isinstance(tok, idl.ExprSym) and tok.symname == "end":
+ return True
+ if memb.max:
+ for tok in memb.max.tokens:
+ if isinstance(tok, idl.ExprSym) and tok.symname == "end":
+ return True
+ return False
+
+
+def gen_c_validate(versions: set[str], typs: list[idl.UserType]) -> str:
+ ret = """
+/* validate_* *****************************************************************/
+
+"""
+ ret += cutil.macro(
+ "#define VALIDATE_NET_BYTES(n)\n"
+ "\tif (__builtin_add_overflow(net_offset, n, &net_offset))\n"
+ "\t\t/* If needed-net-size overflowed uint32_t, then\n"
+ "\t\t * there's no way that actual-net-size will live up to\n"
+ "\t\t * that. */\n"
+ '\t\treturn lib9p_error(ctx, LINUX_EBADMSG, "message is too short for content");\n'
+ "\tif (net_offset > net_size)\n"
+ '\t\treturn lib9p_errorf(ctx, LINUX_EBADMSG, "message is too short for content (%"PRIu32" > %"PRIu32") @ %d", net_offset, net_size, __LINE__);\n'
+ )
+ ret += cutil.macro(
+ "#define VALIDATE_NET_UTF8(n)\n"
+ "\t{\n"
+ "\t\tsize_t len = n;\n"
+ "\t\tVALIDATE_NET_BYTES(len);\n"
+ "\t\tif (!is_valid_utf8_without_nul(&net_bytes[net_offset-len], len))\n"
+ '\t\t\treturn lib9p_error(ctx, LINUX_EBADMSG, "message contains invalid UTF-8");\n'
+ "\t}\n"
+ )
+ ret += cutil.macro(
+ "#define RESERVE_HOST_BYTES(n)\n"
+ "\tif (__builtin_add_overflow(host_size, n, &host_size))\n"
+ "\t\t/* If needed-host-size overflowed ssize_t, then there's\n"
+ "\t\t * no way that actual-net-size will live up to\n"
+ "\t\t * that. */\n"
+ '\t\treturn lib9p_error(ctx, LINUX_EBADMSG, "message is too short for content");\n'
+ )
+
+ ret += "#define GET_U8LE(off) (net_bytes[off])\n"
+ ret += "#define GET_U16LE(off) uint16le_decode(&net_bytes[off])\n"
+ ret += "#define GET_U32LE(off) uint32le_decode(&net_bytes[off])\n"
+ ret += "#define GET_U64LE(off) uint64le_decode(&net_bytes[off])\n"
+
+ ret += "#define LAST_U8LE() GET_U8LE(net_offset-1)\n"
+ ret += "#define LAST_U16LE() GET_U16LE(net_offset-2)\n"
+ ret += "#define LAST_U32LE() GET_U32LE(net_offset-4)\n"
+ ret += "#define LAST_U64LE() GET_U64LE(net_offset-8)\n"
+
+ class IndentLevel(typing.NamedTuple):
+ ifdef: bool # whether this is both `{` and `#if`, or just `{`
+
+ indent_stack: list[IndentLevel]
+
+ def ifdef_lvl() -> int:
+ return sum(1 if lvl.ifdef else 0 for lvl in indent_stack)
+
+ def indent_lvl() -> int:
+ return len(indent_stack)
+
+ incr_buf: int
+
+ def incr_flush() -> None:
+ nonlocal ret
+ nonlocal incr_buf
+ if incr_buf:
+ ret += f"{'\t'*indent_lvl()}VALIDATE_NET_BYTES({incr_buf});\n"
+ incr_buf = 0
+
+ def gen_validate_size(path: idlutil.Path) -> None:
+ nonlocal ret
+ nonlocal incr_buf
+ nonlocal indent_stack
+
+ assert path.elems
+ child = path.elems[-1]
+ parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
+ assert isinstance(parent, idl.Struct)
+
+ if child.in_versions < parent.in_versions:
+ if line := cutil.ifdef_push(
+ ifdef_lvl() + 1, c9util.ver_ifdef(child.in_versions)
+ ):
+ incr_flush()
+ ret += line
+ ret += (
+ f"{'\t'*indent_lvl()}if ({c9util.ver_cond(child.in_versions)}) {{\n"
+ )
+ indent_stack.append(IndentLevel(ifdef=True))
+ if should_save_offset(parent, child):
+ ret += f"{'\t'*indent_lvl()}uint32_t offsetof{''.join('_'+m.membname for m in path.elems)} = net_offset + {incr_buf};\n"
+ if child.cnt:
+ if isinstance(child.cnt, int):
+ cnt_str = str(child.cnt)
+ cnt_typ = "size_t"
+ else:
+ assert child.cnt.typ.static_size
+ incr_flush()
+ cnt_str = f"LAST_U{child.cnt.typ.static_size*8}LE()"
+ cnt_typ = c9util.typename(child.cnt.typ)
+ if child.membname == "utf8": # SPECIAL (string)
+ assert child.typ.static_size == 1
+ # Yes, this is content-validation and "belongs" in
+ # gen_validate_content(), not here. But it's just
+ # easier this way.
+ incr_flush()
+ ret += f"{'\t'*indent_lvl()}VALIDATE_NET_UTF8({cnt_str});\n"
+ return
+ if child.typ.static_size == 1: # SPECIAL (zerocopy)
+ if isinstance(child.cnt, int):
+ incr_buf += child.cnt
+ return
+ incr_flush()
+ ret += f"{'\t'*indent_lvl()}VALIDATE_NET_BYTES({cnt_str});\n"
+ return
+ loopdepth = sum(1 for elem in path.elems if elem.cnt)
+ loopvar = chr(ord("i") + loopdepth - 1)
+ incr_flush()
+ ret += f"{'\t'*indent_lvl()}for ({cnt_typ} {loopvar} = 0, cnt = {cnt_str}; {loopvar} < cnt; {loopvar}++) {{\n"
+ indent_stack.append(IndentLevel(ifdef=False))
+ ret += f"{'\t'*indent_lvl()}RESERVE_HOST_BYTES(sizeof({c9util.typename(child.typ)}));\n"
+ if not isinstance(child.typ, idl.Struct):
+ incr_buf += child.typ.static_size
+
+ def gen_validate_content(path: idlutil.Path) -> None:
+ nonlocal ret
+ nonlocal incr_buf
+ nonlocal indent_stack
+
+ assert path.elems
+ child = path.elems[-1]
+ parent = path.elems[-2].typ if len(path.elems) > 1 else path.root
+ assert isinstance(parent, idl.Struct)
+
+ def lookup_sym(sym: str) -> str:
+ if sym.startswith("&"):
+ sym = sym[1:]
+ return f"offsetof{''.join('_'+m.membname for m in path.elems[:-1])}_{sym}"
+
+ if child.val:
+ incr_flush()
+ assert child.typ.static_size
+ nbits = child.typ.static_size * 8
+ nbits = child.typ.static_size * 8
+ if nbits < 32 and any(
+ isinstance(tok, idl.ExprSym)
+ and (tok.symname == "end" or tok.symname.startswith("&"))
+ for tok in child.val.tokens
+ ):
+ nbits = 32
+ act = f"(uint{nbits}_t)GET_U{nbits}LE({lookup_sym(f'&{child.membname}')})"
+ exp = f"(uint{nbits}_t)({c9util.idl_expr(child.val, lookup_sym)})"
+ ret += f"{'\t'*indent_lvl()}if ({act} != {exp})\n"
+ ret += f'{"\t"*(indent_lvl()+1)}return lib9p_errorf(ctx, LINUX_EBADMSG, "{path} value is wrong: actual: %"PRIu{nbits}" != correct:%"PRIu{nbits},\n'
+ ret += f"{'\t'*(indent_lvl()+2)}{act}, {exp});\n"
+ if child.max:
+ incr_flush()
+ assert child.typ.static_size
+ nbits = child.typ.static_size * 8
+ if nbits < 32 and any(
+ isinstance(tok, idl.ExprSym)
+ and (tok.symname == "end" or tok.symname.startswith("&"))
+ for tok in child.max.tokens
+ ):
+ nbits = 32
+ act = f"(uint{nbits}_t)GET_U{nbits}LE({lookup_sym(f'&{child.membname}')})"
+ exp = f"(uint{nbits}_t)({c9util.idl_expr(child.max, lookup_sym)})"
+ ret += f"{'\t'*indent_lvl()}if ({act} > {exp})\n"
+ ret += f'{"\t"*(indent_lvl()+1)}return lib9p_errorf(ctx, LINUX_EBADMSG, "{path} value is too large: %"PRIu{nbits}" > %"PRIu{nbits},\n'
+ ret += f"{'\t'*(indent_lvl()+2)}{act}, {exp});\n"
+ if isinstance(child.typ, idl.Bitfield):
+ incr_flush()
+ nbytes = child.typ.static_size
+ nbits = nbytes * 8
+ act = f"GET_U{nbits}LE({lookup_sym(f'&{child.membname}')})"
+ ret += f"{'\t'*indent_lvl()}if ({act} & ~{child.typ.typname}_masks[ctx->version])\n"
+ ret += f'{"\t"*(indent_lvl()+1)}return lib9p_errorf(ctx, LINUX_EBADMSG, "unknown bits in {child.typ.typname} bitfield: %#0{nbytes*2}"PRIx{nbits},\n'
+ ret += f"{'\t'*(indent_lvl()+2)}{act} & ~{child.typ.typname}_masks[ctx->version]);\n"
+
+ def handle(
+ path: idlutil.Path,
+ ) -> tuple[idlutil.WalkCmd, typing.Callable[[], None]]:
+ nonlocal ret
+ nonlocal incr_buf
+ nonlocal indent_stack
+ indent_stack_len = len(indent_stack)
+ pop_struct = path.elems[-1].typ if path.elems else path.root
+ pop_path = path
+ pop_indent_stack_len: int
+
+ def pop() -> None:
+ nonlocal ret
+ nonlocal indent_stack
+ nonlocal indent_stack_len
+ nonlocal pop_struct
+ nonlocal pop_path
+ nonlocal pop_indent_stack_len
+ if isinstance(pop_struct, idl.Struct):
+ while len(indent_stack) > pop_indent_stack_len:
+ incr_flush()
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+ parent = pop_struct
+ path = pop_path
+ if should_save_end_offset(parent):
+ ret += f"{'\t'*indent_lvl()}uint32_t offsetof{''.join('_'+m.membname for m in path.elems)}_end = net_offset + {incr_buf};\n"
+ for child in parent.members:
+ gen_validate_content(pop_path.add(child))
+ while len(indent_stack) > indent_stack_len:
+ if len(indent_stack) == indent_stack_len + 1 and indent_stack[-1].ifdef:
+ break
+ incr_flush()
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+
+ if path.elems:
+ gen_validate_size(path)
+
+ pop_indent_stack_len = len(indent_stack)
+
+ return idlutil.WalkCmd.KEEP_GOING, pop
+
+ for typ in typs:
+ if not (
+ isinstance(typ, idl.Message) or typ.typname == "stat"
+ ): # SPECIAL (include stat)
+ continue
+ assert isinstance(typ, idl.Struct)
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+ if typ.typname == "stat": # SPECIAL (stat)
+ ret += f"static ssize_t validate_{typ.typname}(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes, uint32_t *ret_net_size) {{\n"
+ else:
+ ret += f"static ssize_t validate_{typ.typname}(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes) {{\n"
+
+ ret += "\tuint32_t net_offset = 0;\n"
+ ret += f"\tssize_t host_size = sizeof({c9util.typename(typ)});\n"
+
+ incr_buf = 0
+ indent_stack = [IndentLevel(ifdef=True)]
+ idlutil.walk(typ, handle)
+ while len(indent_stack) > 1:
+ incr_flush()
+ ret += f"{'\t'*(indent_lvl()-1)}}}\n"
+ if indent_stack.pop().ifdef:
+ ret += cutil.ifdef_pop(ifdef_lvl())
+
+ incr_flush()
+ if typ.typname == "stat": # SPECIAL (stat)
+ ret += "\tif (ret_net_size)\n"
+ ret += "\t\t*ret_net_size = net_offset;\n"
+ ret += "\treturn (ssize_t)host_size;\n"
+ ret += "}\n"
+ ret += cutil.ifdef_pop(0)
+ return ret
diff --git a/lib9p/protogen/cutil.py b/lib9p/protogen/cutil.py
new file mode 100644
index 0000000..8df6db9
--- /dev/null
+++ b/lib9p/protogen/cutil.py
@@ -0,0 +1,84 @@
+# lib9p/protogen/cutil.py - Utilities for generating C code
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+# pylint: disable=unused-variable
+__all__ = [
+ "UINT32_MAX",
+ "UINT64_MAX",
+ "macro",
+ "ifdef_init",
+ "ifdef_push",
+ "ifdef_pop",
+ "ifdef_leaf_is_noop",
+]
+
+UINT32_MAX = (1 << 32) - 1
+UINT64_MAX = (1 << 64) - 1
+
+
+def tab_ljust(s: str, width: int) -> str:
+ cur = len(s.expandtabs(tabsize=8))
+ if cur >= width:
+ return s
+ return s + " " * (width - cur)
+
+
+def macro(full: str) -> str:
+ full = full.rstrip()
+ assert "\n" in full
+ lines = [l.rstrip() for l in full.split("\n")]
+ width = max(len(l.expandtabs(tabsize=8)) for l in lines[:-1])
+ lines = [tab_ljust(l, width) for l in lines]
+ return " \\\n".join(lines).rstrip() + "\n"
+
+
+_ifdef_stack: list[str | None] = []
+
+
+def ifdef_init() -> None:
+ global _ifdef_stack
+ _ifdef_stack = []
+
+
+def ifdef_push(n: int, _newval: str) -> str:
+ # Grow the stack as needed
+ while len(_ifdef_stack) < n:
+ _ifdef_stack.append(None)
+
+ # Set some variables
+ parentval: str | None = None
+ for x in _ifdef_stack[:-1]:
+ if x is not None:
+ parentval = x
+ oldval = _ifdef_stack[-1]
+ newval: str | None = _newval
+ if newval == parentval:
+ newval = None
+
+ # Put newval on the stack.
+ _ifdef_stack[-1] = newval
+
+ # Build output.
+ ret = ""
+ if newval != oldval:
+ if oldval is not None:
+ ret += f"#endif /* {oldval} */\n"
+ if newval is not None:
+ ret += f"#if {newval}\n"
+ return ret
+
+
+def ifdef_pop(n: int) -> str:
+ global _ifdef_stack
+ ret = ""
+ while len(_ifdef_stack) > n:
+ if _ifdef_stack[-1] is not None:
+ ret += f"#endif /* {_ifdef_stack[-1]} */\n"
+ _ifdef_stack = _ifdef_stack[:-1]
+ return ret
+
+
+def ifdef_leaf_is_noop() -> bool:
+ return not _ifdef_stack[-1]
diff --git a/lib9p/protogen/h.py b/lib9p/protogen/h.py
new file mode 100644
index 0000000..3b33419
--- /dev/null
+++ b/lib9p/protogen/h.py
@@ -0,0 +1,535 @@
+# lib9p/protogen/h.py - Generate 9p.generated.h
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import sys
+import typing
+
+import idl
+
+from . import c9util, cutil, idlutil
+
+# This strives to be "general-purpose" in that it just acts on the
+# *.9p inputs; but (unfortunately?) there are a few special-cases in
+# this script, marked with "SPECIAL".
+
+# pylint: disable=unused-variable
+__all__ = ["gen_h"]
+
+# get_buffer_size() ############################################################
+
+
+class BufferSize(typing.NamedTuple):
+ min_size: int # really just here to sanity-check against typ.min_size(version)
+ exp_size: int # "expected" or max-reasonable size
+ max_size: int # really just here to sanity-check against typ.max_size(version)
+ max_copy: int
+ max_copy_extra: str
+ max_iov: int
+ max_iov_extra: str
+
+
+class TmpBufferSize:
+ min_size: int
+ exp_size: int
+ max_size: int
+ max_copy: int
+ max_copy_extra: str
+ max_iov: int
+ max_iov_extra: str
+
+ tmp_starts_with_copy: bool
+ tmp_ends_with_copy: bool
+
+ def __init__(self) -> None:
+ self.min_size = 0
+ self.exp_size = 0
+ self.max_size = 0
+ self.max_copy = 0
+ self.max_copy_extra = ""
+ self.max_iov = 0
+ self.max_iov_extra = ""
+ self.tmp_starts_with_copy = False
+ self.tmp_ends_with_copy = False
+
+
+def _get_buffer_size(typ: idl.Type, version: str) -> TmpBufferSize:
+ assert isinstance(typ, idl.Primitive) or (version in typ.in_versions)
+
+ ret = TmpBufferSize()
+
+ if not isinstance(typ, idl.Struct):
+ assert typ.static_size
+ ret.min_size = typ.static_size
+ ret.exp_size = typ.static_size
+ ret.max_size = typ.static_size
+ ret.max_copy = typ.static_size
+ ret.max_iov = 1
+ ret.tmp_starts_with_copy = True
+ ret.tmp_ends_with_copy = True
+ return ret
+
+ def handle(path: idlutil.Path) -> tuple[idlutil.WalkCmd, None]:
+ nonlocal ret
+ if path.elems:
+ child = path.elems[-1]
+ if version not in child.in_versions:
+ return idlutil.WalkCmd.DONT_RECURSE, None
+ if child.cnt:
+ if child.typ.static_size == 1: # SPECIAL (zerocopy)
+ ret.max_iov += 1
+ # HEURISTIC: 27 for strings (max-strlen from 9P1), 8KiB for other data
+ ret.exp_size += 27 if child.membname == "utf8" else 8192
+ ret.max_size += child.max_cnt
+ ret.tmp_ends_with_copy = False
+ return idlutil.WalkCmd.DONT_RECURSE, None
+ sub = _get_buffer_size(child.typ, version)
+ ret.exp_size += sub.exp_size * 16 # HEURISTIC: MAXWELEM
+ ret.max_size += sub.max_size * child.max_cnt
+ if child.membname == "wname" and path.root.typname in (
+ "Tsread",
+ "Tswrite",
+ ): # SPECIAL (9P2000.e)
+ assert ret.tmp_ends_with_copy
+ assert sub.tmp_starts_with_copy
+ assert not sub.tmp_ends_with_copy
+ ret.max_copy_extra = (
+ f" + (CONFIG_9P_MAX_9P2000_e_WELEM * {sub.max_copy})"
+ )
+ ret.max_iov_extra = (
+ f" + (CONFIG_9P_MAX_9P2000_e_WELEM * {sub.max_iov})"
+ )
+ ret.max_iov -= 1
+ else:
+ ret.max_copy += sub.max_copy * child.max_cnt
+ if sub.max_iov == 1 and sub.tmp_starts_with_copy: # is purely copy
+ ret.max_iov += 1
+ else: # contains zero-copy segments
+ ret.max_iov += sub.max_iov * child.max_cnt
+ if ret.tmp_ends_with_copy and sub.tmp_starts_with_copy:
+ # we can merge this one
+ ret.max_iov -= 1
+ if (
+ sub.tmp_ends_with_copy
+ and sub.tmp_starts_with_copy
+ and sub.max_iov > 1
+ ):
+ # we can merge these
+ ret.max_iov -= child.max_cnt - 1
+ ret.tmp_ends_with_copy = sub.tmp_ends_with_copy
+ return idlutil.WalkCmd.DONT_RECURSE, None
+ if not isinstance(child.typ, idl.Struct):
+ assert child.typ.static_size
+ if not ret.tmp_ends_with_copy:
+ if ret.max_size == 0:
+ ret.tmp_starts_with_copy = True
+ ret.max_iov += 1
+ ret.tmp_ends_with_copy = True
+ ret.min_size += child.typ.static_size
+ ret.exp_size += child.typ.static_size
+ ret.max_size += child.typ.static_size
+ ret.max_copy += child.typ.static_size
+ return idlutil.WalkCmd.KEEP_GOING, None
+
+ idlutil.walk(typ, handle)
+ assert ret.min_size == typ.min_size(version)
+ assert ret.max_size == typ.max_size(version)
+ return ret
+
+
+def get_buffer_size(typ: idl.Type, version: str) -> BufferSize:
+ tmp = _get_buffer_size(typ, version)
+ return BufferSize(
+ min_size=tmp.min_size,
+ exp_size=tmp.exp_size,
+ max_size=tmp.max_size,
+ max_copy=tmp.max_copy,
+ max_copy_extra=tmp.max_copy_extra,
+ max_iov=tmp.max_iov,
+ max_iov_extra=tmp.max_iov_extra,
+ )
+
+
+# Generate .h ##################################################################
+
+
+def gen_h(versions: set[str], typs: list[idl.UserType]) -> str:
+ cutil.ifdef_init()
+
+ ret = f"""/* Generated by `{' '.join(sys.argv)}`. DO NOT EDIT! */
+
+#ifndef _LIB9P_9P_H_
+\t#error Do not include <lib9p/9p.generated.h> directly; include <lib9p/9p.h> instead
+#endif
+
+#include <stdint.h> /* for uint{{n}}_t types */
+
+#include <libfmt/fmt.h> /* for fmt_formatter */
+#include <libhw/generic/net.h> /* for struct iovec */
+"""
+
+ id2typ: dict[int, idl.Message] = {}
+ for msg in [msg for msg in typs if isinstance(msg, idl.Message)]:
+ id2typ[msg.msgid] = msg
+
+ ret += """
+/* config *********************************************************************/
+
+#include "config.h"
+"""
+ for ver in sorted(versions):
+ ret += "\n"
+ ret += f"#ifndef {c9util.ver_ifdef({ver})}\n"
+ ret += f"\t#error config.h must define {c9util.ver_ifdef({ver})}\n"
+ if ver == "9P2000.e": # SPECIAL (9P2000.e)
+ ret += "#else\n"
+ ret += f"\t#if {c9util.ver_ifdef({ver})}\n"
+ ret += "\t\t#ifndef CONFIG_9P_MAX_9P2000_e_WELEM\n"
+ ret += f"\t\t\t#error if {c9util.ver_ifdef({ver})} then config.h must define CONFIG_9P_MAX_9P2000_e_WELEM\n"
+ ret += "\t\t#endif\n"
+ ret += "\t\tstatic_assert(CONFIG_9P_MAX_9P2000_e_WELEM > 0);\n"
+ ret += "\t#endif\n"
+ ret += "#endif\n"
+
+ ret += f"""
+/* enum version ***************************************************************/
+
+enum {c9util.ident('version')} {{
+"""
+ fullversions = ["unknown = 0", *sorted(versions)]
+ verwidth = max(len(v) for v in fullversions)
+ for ver in fullversions:
+ if ver in versions:
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef({ver}))
+ ret += f"\t{c9util.ver_enum(ver)},"
+ ret += (" " * (verwidth - len(ver))) + ' /* "' + ver.split()[0] + '" */\n'
+ ret += cutil.ifdef_pop(0)
+ ret += f"\t{c9util.ver_enum('NUM')},\n"
+ ret += "};\n"
+ ret += f"LO_IMPLEMENTATION_H(fmt_formatter, enum {c9util.ident('version')}, {c9util.ident('version')});\n"
+
+ ret += """
+/* enum msg_type **************************************************************/
+
+"""
+ ret += f"enum {c9util.ident('msg_type')} {{ /* uint8_t */\n"
+ namewidth = max(len(msg.typname) for msg in typs if isinstance(msg, idl.Message))
+ for n in range(0x100):
+ if n not in id2typ:
+ continue
+ msg = id2typ[n]
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(msg.in_versions))
+ ret += f"\t{c9util.Ident(f'TYP_{msg.typname:<{namewidth}}')} = {msg.msgid},\n"
+ ret += cutil.ifdef_pop(0)
+ ret += "};\n"
+ ret += f"LO_IMPLEMENTATION_H(fmt_formatter, enum {c9util.ident('msg_type')}, {c9util.ident('msg_type')});\n"
+
+ ret += """
+/* payload types **************************************************************/
+"""
+
+ def per_version_comment(
+ typ: idl.UserType, fn: typing.Callable[[idl.UserType, str], str]
+ ) -> str:
+ lines: dict[str, str] = {}
+ for version in sorted(typ.in_versions):
+ lines[version] = fn(typ, version)
+ if len(set(lines.values())) == 1:
+ for _, line in lines.items():
+ return f"/* {line} */\n"
+ assert False
+ else:
+ ret = ""
+ v_width = max(len(c9util.ver_enum(v)) for v in typ.in_versions)
+ for version, line in lines.items():
+ ret += f"/* {c9util.ver_enum(version):<{v_width}}: {line} */\n"
+ return ret
+
+ for typ in idlutil.topo_sorted(typs):
+ ret += "\n"
+ ret += cutil.ifdef_push(1, c9util.ver_ifdef(typ.in_versions))
+
+ def sum_size(typ: idl.UserType, version: str) -> str:
+ sz = get_buffer_size(typ, version)
+ assert (
+ sz.min_size <= sz.exp_size
+ and sz.exp_size <= sz.max_size
+ and sz.max_size < cutil.UINT64_MAX
+ )
+ ret = ""
+ if sz.min_size == sz.max_size:
+ ret += f"size = {sz.min_size:,}"
+ else:
+ ret += f"min_size = {sz.min_size:,} ; exp_size = {sz.exp_size:,} ; max_size = {sz.max_size:,}"
+ if sz.max_size > cutil.UINT32_MAX:
+ ret += " (warning: >UINT32_MAX)"
+ ret += f" ; max_iov = {sz.max_iov:,}{sz.max_iov_extra} ; max_copy = {sz.max_copy:,}{sz.max_copy_extra}"
+ return ret
+
+ ret += per_version_comment(typ, sum_size)
+
+ match typ:
+ case idl.Number():
+ ret += gen_number(typ)
+ case idl.Bitfield():
+ ret += gen_bitfield(typ)
+ case idl.Struct(): # and idl.Message():
+ ret += gen_struct(typ)
+ ret += cutil.ifdef_pop(0)
+
+ ret += """
+/* containers *****************************************************************/
+"""
+ ret += "\n"
+ ret += f"#define {c9util.IDENT('_MAX')}(a, b) ((a) > (b)) ? (a) : (b)\n"
+
+ tmsg_max_iov: dict[str, int] = {}
+ tmsg_max_copy: dict[str, int] = {}
+ rmsg_max_iov: dict[str, int] = {}
+ rmsg_max_copy: dict[str, int] = {}
+ for typ in typs:
+ if not isinstance(typ, idl.Message):
+ continue
+ if typ.typname in ("Tsread", "Tswrite"): # SPECIAL (9P2000.e)
+ continue
+ max_iov = tmsg_max_iov if typ.msgid % 2 == 0 else rmsg_max_iov
+ max_copy = tmsg_max_copy if typ.msgid % 2 == 0 else rmsg_max_copy
+ for version in typ.in_versions:
+ if version not in max_iov:
+ max_iov[version] = 0
+ max_copy[version] = 0
+ sz = get_buffer_size(typ, version)
+ if sz.max_iov > max_iov[version]:
+ max_iov[version] = sz.max_iov
+ if sz.max_copy > max_copy[version]:
+ max_copy[version] = sz.max_copy
+
+ for name, table in [
+ ("tmsg_max_iov", tmsg_max_iov),
+ ("tmsg_max_copy", tmsg_max_copy),
+ ("rmsg_max_iov", rmsg_max_iov),
+ ("rmsg_max_copy", rmsg_max_copy),
+ ]:
+ inv: dict[int, set[str]] = {}
+ for version, maxval in table.items():
+ if maxval not in inv:
+ inv[maxval] = set()
+ inv[maxval].add(version)
+
+ ret += "\n"
+ directive = "if"
+ seen_e = False # SPECIAL (9P2000.e)
+ for maxval in sorted(inv, reverse=True):
+ ret += f"#{directive} {c9util.ver_ifdef(inv[maxval])}\n"
+ indent = 1
+ if name.startswith("tmsg") and not seen_e: # SPECIAL (9P2000.e)
+ typ = next(typ for typ in typs if typ.typname == "Tswrite")
+ sz = get_buffer_size(typ, "9P2000.e")
+ match name:
+ case "tmsg_max_iov":
+ maxexpr = f"{sz.max_iov}{sz.max_iov_extra}"
+ case "tmsg_max_copy":
+ maxexpr = f"{sz.max_copy}{sz.max_copy_extra}"
+ case _:
+ assert False
+ ret += f"\t#if {c9util.ver_ifdef({"9P2000.e"})}\n"
+ ret += f"\t\t#define {c9util.IDENT(name)} {c9util.IDENT('_MAX')}({maxval}, {maxexpr})\n"
+ ret += "\t#else\n"
+ indent += 1
+ ret += f"{'\t'*indent}#define {c9util.IDENT(name)} {maxval}\n"
+ if name.startswith("tmsg") and not seen_e: # SPECIAL (9P2000.e)
+ ret += "\t#endif\n"
+ if "9P2000.e" in inv[maxval]:
+ seen_e = True
+ directive = "elif"
+ ret += "#endif\n"
+
+ ret += "\n"
+ ret += f"struct {c9util.ident('Tmsg_send_buf')} {{\n"
+ ret += "\tsize_t iov_cnt;\n"
+ ret += f"\tstruct iovec iov[{c9util.IDENT('TMSG_MAX_IOV')}];\n"
+ ret += f"\tuint8_t copied[{c9util.IDENT('TMSG_MAX_COPY')}];\n"
+ ret += "};\n"
+
+ ret += "\n"
+ ret += f"struct {c9util.ident('Rmsg_send_buf')} {{\n"
+ ret += "\tsize_t iov_cnt;\n"
+ ret += f"\tstruct iovec iov[{c9util.IDENT('RMSG_MAX_IOV')}];\n"
+ ret += f"\tuint8_t copied[{c9util.IDENT('RMSG_MAX_COPY')}];\n"
+ ret += "};\n"
+
+ return ret
+
+
+def gen_number(typ: idl.Number) -> str:
+ ret = f"typedef {c9util.typename(typ.prim)} {c9util.typename(typ)};\n"
+ ret += f"LO_IMPLEMENTATION_H(fmt_formatter, {c9util.typename(typ)}, {c9util.basename(typ)});\n"
+
+ def lookup_sym(sym: str) -> str:
+ assert False
+
+ def cname(base: str) -> str:
+ prefix = f"{typ.typname}_".upper()
+ return c9util.Ident(c9util.add_prefix(prefix, base))
+
+ namewidth = max(len(cname(name)) for name in typ.vals)
+ for name, val in typ.vals.items():
+ c_name = cname(name)
+ c_val = c9util.idl_expr(val, lookup_sym)
+ ret += f"#define {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val}))\n"
+ return ret
+
+
+def gen_bitfield(typ: idl.Bitfield) -> str:
+ ret = f"typedef {c9util.typename(typ.prim)} {c9util.typename(typ)};\n"
+ ret += f"LO_IMPLEMENTATION_H(fmt_formatter, {c9util.typename(typ)}, {c9util.basename(typ)});\n"
+
+ def lookup_sym(sym: str) -> str:
+ assert False
+
+ # There are 4 parts here: bits, aliases, masks, and numbers.
+
+ # 1. bits
+
+ def bitname(bit: idl.Bit) -> str:
+ prefix = f"{typ.typname}_".upper()
+ base = bit.bitname
+ match bit:
+ case idl.Bit(cat="RESERVED"):
+ base = "_RESERVED_" + base
+ case idl.Bit(cat=idl.BitNum()):
+ base += "_*"
+ case idl.Bit(cat="UNUSED"):
+ base = f"_UNUSED_{bit.num}"
+ return c9util.Ident(c9util.add_prefix(prefix, base))
+
+ namewidth = max(len(bitname(bit)) for bit in typ.bits)
+
+ ret += "/* bits */\n"
+ for bit in reversed(typ.bits):
+ vers = bit.in_versions
+ if bit.cat == "UNUSED":
+ vers = typ.in_versions
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(vers))
+
+ # It is important all of the `beg` strings have
+ # the same length.
+ end = ""
+ match bit.cat:
+ case "USED" | "RESERVED" | "UNUSED":
+ if cutil.ifdef_leaf_is_noop():
+ beg = "#define "
+ else:
+ beg = "# define"
+ case idl.BitNum():
+ beg = "/* number"
+ end = " */"
+
+ c_name = bitname(bit)
+ c_val = f"UINT{typ.static_size*8}_C(1)<<{bit.num}"
+ ret += (
+ f"{beg} {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val})){end}\n"
+ )
+ ret += cutil.ifdef_pop(1)
+
+ # 2. aliases
+ if typ.aliases:
+
+ def aliasname(alias: idl.BitAlias) -> str:
+ prefix = f"{typ.typname}_".upper()
+ base = alias.bitname
+ return c9util.Ident(c9util.add_prefix(prefix, base))
+
+ ret += "/* aliases */\n"
+ for alias in typ.aliases.values():
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(alias.in_versions))
+
+ end = ""
+ if cutil.ifdef_leaf_is_noop():
+ beg = "#define "
+ else:
+ beg = "# define"
+
+ c_name = aliasname(alias)
+ c_val = c9util.idl_expr(alias.val, lookup_sym)
+ ret += f"{beg} {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val})){end}\n"
+
+ ret += cutil.ifdef_pop(1)
+
+ # 3. masks
+ if typ.masks:
+
+ def maskname(mask: idl.BitAlias) -> str:
+ prefix = f"{typ.typname}_".upper()
+ base = mask.bitname
+ return c9util.Ident(c9util.add_prefix(prefix, base) + "_MASK")
+
+ ret += "/* masks */\n"
+ for mask in typ.masks.values():
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(mask.in_versions))
+
+ end = ""
+ if cutil.ifdef_leaf_is_noop():
+ beg = "#define "
+ else:
+ beg = "# define"
+
+ c_name = maskname(mask)
+ c_val = c9util.idl_expr(mask.val, lookup_sym, bitwidth=typ.static_size * 8)
+ ret += f"{beg} {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val})){end}\n"
+
+ ret += cutil.ifdef_pop(1)
+
+ # 4. numbers
+ def numname(num: idl.BitNum, base: str) -> str:
+ prefix = f"{typ.typname}_{num.numname}_".upper()
+ return c9util.Ident(c9util.add_prefix(prefix, base))
+
+ for num in typ.nums.values():
+ namewidth = max(
+ len(numname(num, base))
+ for base in [
+ *[alias.bitname for alias in num.vals.values()],
+ "MASK",
+ ]
+ )
+ ret += f"/* number: {num.numname} */\n"
+ for alias in num.vals.values():
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(alias.in_versions))
+
+ end = ""
+ if cutil.ifdef_leaf_is_noop():
+ beg = "#define "
+ else:
+ beg = "# define"
+
+ c_name = numname(num, alias.bitname)
+ c_val = c9util.idl_expr(alias.val, lookup_sym)
+ ret += f"{beg} {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val})){end}\n"
+ ret += cutil.ifdef_pop(1)
+ c_name = numname(num, "MASK")
+ c_val = f"{num.mask:#0{typ.static_size*8}b}"
+ ret += (
+ f"{beg} {c_name:<{namewidth}} (({c9util.typename(typ)})({c_val})){end}\n"
+ )
+
+ return ret
+
+
+def gen_struct(typ: idl.Struct) -> str: # and idl.Message
+ ret = c9util.typename(typ) + " {"
+ if typ.members:
+ ret += "\n"
+
+ typewidth = max(len(c9util.typename(m.typ, m)) for m in typ.members)
+
+ for member in typ.members:
+ if member.val:
+ continue
+ ret += cutil.ifdef_push(2, c9util.ver_ifdef(member.in_versions))
+ ret += f"\t{c9util.typename(member.typ, member):<{typewidth}} {'*' if member.cnt else ' '}{member.membname};\n"
+ ret += cutil.ifdef_pop(1)
+ ret += "};\n"
+ ret += f"LO_IMPLEMENTATION_H(fmt_formatter, {c9util.typename(typ)}, {c9util.basename(typ)});\n"
+ return ret
diff --git a/lib9p/protogen/idlutil.py b/lib9p/protogen/idlutil.py
new file mode 100644
index 0000000..dc4d012
--- /dev/null
+++ b/lib9p/protogen/idlutil.py
@@ -0,0 +1,112 @@
+# lib9p/protogen/idlutil.py - Utilities for working with the 9P idl package
+#
+# Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+# SPDX-License-Identifier: AGPL-3.0-or-later
+
+import enum
+import graphlib
+import typing
+
+import idl
+
+# pylint: disable=unused-variable
+__all__ = [
+ "topo_sorted",
+ "Path",
+ "WalkCmd",
+ "WalkHandler",
+ "walk",
+]
+
+# topo_sorted() ################################################################
+
+
+def topo_sorted(typs: list[idl.UserType]) -> typing.Iterable[idl.UserType]:
+ ts: graphlib.TopologicalSorter[idl.UserType] = graphlib.TopologicalSorter()
+ for typ in typs:
+ match typ:
+ case idl.Number():
+ ts.add(typ)
+ case idl.Bitfield():
+ ts.add(typ)
+ case idl.Struct(): # and idl.Message():
+ deps = [
+ member.typ
+ for member in typ.members
+ if not isinstance(member.typ, idl.Primitive)
+ ]
+ ts.add(typ, *deps)
+ return ts.static_order()
+
+
+# walk() #######################################################################
+
+
+class Path:
+ root: idl.Type
+ elems: list[idl.StructMember]
+
+ def __init__(
+ self, root: idl.Type, elems: list[idl.StructMember] | None = None
+ ) -> None:
+ self.root = root
+ self.elems = elems if elems is not None else []
+
+ def add(self, elem: idl.StructMember) -> "Path":
+ return Path(self.root, self.elems + [elem])
+
+ def parent(self) -> "Path":
+ return Path(self.root, self.elems[:-1])
+
+ def c_str(self, base: str, loopdepth: int = 0) -> str:
+ ret = base
+ for i, elem in enumerate(self.elems):
+ if i > 0:
+ ret += "."
+ ret += elem.membname
+ if elem.cnt:
+ ret += f"[{chr(ord('i')+loopdepth)}]"
+ loopdepth += 1
+ return ret
+
+ def __str__(self) -> str:
+ return self.c_str(self.root.typname + "->")
+
+
+class WalkCmd(enum.Enum):
+ KEEP_GOING = 1
+ DONT_RECURSE = 2
+ ABORT = 3
+
+
+type WalkHandler = typing.Callable[
+ [Path], tuple[WalkCmd, typing.Callable[[], None] | None]
+]
+
+
+def _walk(path: Path, handle: WalkHandler) -> WalkCmd:
+ typ = path.elems[-1].typ if path.elems else path.root
+
+ ret, atexit = handle(path)
+
+ if isinstance(typ, idl.Struct):
+ match ret:
+ case WalkCmd.KEEP_GOING:
+ for member in typ.members:
+ if _walk(path.add(member), handle) == WalkCmd.ABORT:
+ ret = WalkCmd.ABORT
+ break
+ case WalkCmd.DONT_RECURSE:
+ ret = WalkCmd.KEEP_GOING
+ case WalkCmd.ABORT:
+ ret = WalkCmd.ABORT
+ case _:
+ assert False, f"invalid cmd: {ret}"
+
+ if atexit:
+ atexit()
+ return ret
+
+
+def walk(typ: idl.Type, handle: WalkHandler) -> None:
+ _walk(Path(typ), handle)
diff --git a/lib9p/srv.c b/lib9p/srv.c
index 2475baf..bfeb06f 100644
--- a/lib9p/srv.c
+++ b/lib9p/srv.c
@@ -6,12 +6,18 @@
#include <alloca.h>
#include <inttypes.h> /* for PRI* */
+#include <stddef.h> /* for size_t */
+#include <limits.h> /* for SSIZE_MAX, not set by newlib */
+#ifndef SSIZE_MAX
+#define SSIZE_MAX (SIZE_MAX >> 1)
+#endif
#include <libcr/coroutine.h>
#include <libcr_ipc/chan.h>
#include <libcr_ipc/mutex.h>
#include <libcr_ipc/select.h>
#include <libmisc/assert.h>
+#include <libmisc/endian.h>
#include <libhw/generic/net.h>
#define LOG_NAME 9P_SRV
@@ -20,7 +26,9 @@
#define IMPLEMENTATION_FOR_LIB9P_SRV_H YES
#include <lib9p/srv.h>
-#include "internal.h"
+/* config *********************************************************************/
+
+#include "config.h"
#ifndef CONFIG_9P_SRV_MAX_FIDS
#error config.h must define CONFIG_9P_SRV_MAX_FIDS
@@ -32,6 +40,14 @@
/* 1=just the root dir, 2=just files in the root dir, 3=1 subdir, ... */
#error config.h must define CONFIG_9P_SRV_MAX_DEPTH
#endif
+#ifndef CONFIG_9P_SRV_MAX_MSG_SIZE
+ #error config.h must define CONFIG_9P_SRV_MAX_MSG_SIZE
+#endif
+#ifndef CONFIG_9P_SRV_MAX_HOSTMSG_SIZE
+ #error config.h must define CONFIG_9P_SRV_MAX_HOSTMSG_SIZE
+#endif
+static_assert(CONFIG_9P_SRV_MAX_MSG_SIZE <= CONFIG_9P_SRV_MAX_HOSTMSG_SIZE);
+static_assert(CONFIG_9P_SRV_MAX_HOSTMSG_SIZE <= SSIZE_MAX);
/* context ********************************************************************/
@@ -60,8 +76,7 @@ struct srv_pathinfo {
* from FIDs. */
unsigned int gc_refcount;
/* References from fids with FIDFLAG_OPEN_R/FIDFLAG_OPEN_W. */
- unsigned int rd_refcount;
- unsigned int wr_refcount;
+ unsigned int io_refcount;
};
#define NAME pathmap
@@ -77,11 +92,18 @@ struct srv_pathinfo {
#define FIDFLAG_OPEN (FIDFLAG_OPEN_R|FIDFLAG_OPEN_W)
struct _srv_fidinfo {
- srv_path_t path;
- uint8_t flags;
- uint32_t iounit;
- size_t dir_idx;
- uint64_t dir_off;
+ srv_path_t path;
+ uint8_t flags;
+ union {
+ struct {
+ lo_interface lib9p_srv_fio io;
+ } file;
+ struct {
+ lo_interface lib9p_srv_dio io;
+ size_t idx;
+ uint64_t off;
+ } dir;
+ };
};
#define NAME fidmap
@@ -122,9 +144,9 @@ struct _srv_sess {
/* mutable */
bool initialized;
bool closing;
- struct pathmap paths;
- struct reqmap reqs;
- struct fidmap fids;
+ struct pathmap paths; /* srv_path_t => lib9p_srv_file + metadata */
+ struct fidmap fids; /* lib9p_fid_t => lib9p_srv_{fio,dio} + metadata */
+ struct reqmap reqs; /* lib9p_tag_t => *_lib9p_srv_req */
};
struct _lib9p_srv_req {
@@ -177,6 +199,7 @@ static void respond_error(struct _lib9p_srv_req *req) {
LIB9P_TYP_Rerror, &host,
&net);
+ infof("< %v", lo_box_lib9p_msg_Rerror_as_fmt_formatter(&host));
r = write_Rmsg(req, &net);
if (r < 0)
nonrespond_errorf("write: %s", net_strerror(-r));
@@ -212,7 +235,7 @@ static void handle_message(struct _lib9p_srv_req *ctx);
srv->readers++;
- uint32_t initial_rerror_overhead = _lib9p_table_msg_min_size[LIB9P_VER_unknown];
+ uint32_t initial_rerror_overhead = lib9p_version_min_msg_size(LIB9P_VER_unknown);
for (;;) {
struct _srv_conn conn = {
@@ -232,7 +255,7 @@ static void handle_message(struct _lib9p_srv_req *ctx);
struct _srv_sess sess = {
.parent_conn = &conn,
.version = LIB9P_VER_unknown,
- .max_msg_size = CONFIG_9P_MAX_MSG_SIZE,
+ .max_msg_size = CONFIG_9P_SRV_MAX_MSG_SIZE,
.rerror_overhead = initial_rerror_overhead,
.initialized = false,
};
@@ -391,17 +414,18 @@ static tmessage_handler tmessage_handlers[0x100] = {
static void handle_message(struct _lib9p_srv_req *ctx) {
uint8_t *host_req = NULL;
- uint8_t host_resp[CONFIG_9P_MAX_HOSTMSG_SIZE];
+ uint8_t host_resp[CONFIG_9P_SRV_MAX_HOSTMSG_SIZE];
/* Unmarshal it. */
ssize_t host_size = lib9p_Tmsg_validate(&ctx->ctx.basectx, ctx->net_bytes);
if (host_size < 0)
goto write;
- host_req = malloc(host_size);
+ host_req = calloc(1, host_size);
assert(host_req);
enum lib9p_msg_type typ;
lib9p_Tmsg_unmarshal(&ctx->ctx.basectx, ctx->net_bytes,
&typ, host_req);
+ infof("> %v", lo_box_lib9p_msg_as_fmt_formatter(&ctx->ctx.basectx, typ, host_req));
/* Handle it. */
tmessage_handlers[typ](ctx, (void *)host_req, (void *)host_resp);
@@ -415,6 +439,7 @@ static void handle_message(struct _lib9p_srv_req *ctx) {
typ+1, host_resp,
&net_resp))
goto write;
+ infof("< %v", lo_box_lib9p_msg_as_fmt_formatter(&ctx->ctx.basectx, typ+1, &host_resp));
write_Rmsg(ctx, &net_resp);
}
if (host_req)
@@ -463,8 +488,7 @@ static inline struct srv_pathinfo *srv_util_pathsave(struct _lib9p_srv_req *ctx,
.file = file,
.parent_dir = parent_path,
.gc_refcount = 0,
- .rd_refcount = 0,
- .wr_refcount = 0,
+ .io_refcount = 0,
});
assert(pathinfo);
if (parent_path != qid.path) {
@@ -515,6 +539,12 @@ static inline struct _srv_fidinfo *srv_util_fidsave(struct _lib9p_srv_req *ctx,
struct _srv_fidinfo *fidinfo = fidmap_load(&ctx->parent_sess->fids, fid);
if (fidinfo) {
if (overwrite) {
+ struct srv_pathinfo *old_pathinfo = pathmap_load(&ctx->parent_sess->paths, fidinfo->path);
+ assert(old_pathinfo);
+ if (srv_util_pathisdir(old_pathinfo))
+ LO_CALL(fidinfo->dir.io, iofree);
+ else
+ LO_CALL(fidinfo->file.io, iofree);
srv_util_pathfree(ctx, fidinfo->path);
} else {
lib9p_error(&ctx->ctx.basectx,
@@ -562,7 +592,7 @@ static void handle_Tversion(struct _lib9p_srv_req *ctx,
#endif
}
- uint32_t min_msg_size = _lib9p_table_msg_min_size[version];
+ uint32_t min_msg_size = lib9p_version_min_msg_size(version);
if (req->max_msg_size < min_msg_size) {
lib9p_errorf(&ctx->ctx.basectx,
LINUX_EDOM, "requested max_msg_size is less than minimum for %s (%"PRIu32" < %"PRIu32")",
@@ -571,8 +601,8 @@ static void handle_Tversion(struct _lib9p_srv_req *ctx,
}
resp->version = lib9p_str((char *)lib9p_version_str(version)); /* cast to discard "const" qualifier */
- resp->max_msg_size = (CONFIG_9P_MAX_MSG_SIZE < req->max_msg_size)
- ? CONFIG_9P_MAX_MSG_SIZE
+ resp->max_msg_size = (CONFIG_9P_SRV_MAX_MSG_SIZE < req->max_msg_size)
+ ? CONFIG_9P_SRV_MAX_MSG_SIZE
: req->max_msg_size;
/* Close the old session. */
@@ -748,7 +778,7 @@ static void handle_Twalk(struct _lib9p_srv_req *ctx,
break;
}
- lo_interface lib9p_srv_file member_file = LO_CALL(pathinfo->file, dopen, &ctx->ctx, req->wname[resp->nwqid]);
+ lo_interface lib9p_srv_file member_file = LO_CALL(pathinfo->file, dwalk, &ctx->ctx, req->wname[resp->nwqid]);
assert(LO_IS_NULL(member_file) == lib9p_ctx_has_error(&ctx->ctx.basectx));
if (lib9p_ctx_has_error(&ctx->ctx.basectx))
break;
@@ -774,6 +804,13 @@ static void handle_Twalk(struct _lib9p_srv_req *ctx,
pathinfo = new_pathinfo;
}
if (resp->nwqid == req->nwname) {
+ if (req->newfid == req->fid) {
+ if (srv_util_pathisdir(pathinfo))
+ LO_CALL(fidinfo->dir.io, iofree);
+ else
+ LO_CALL(fidinfo->file.io, iofree);
+ fidinfo->flags = 0;
+ }
if (!srv_util_fidsave(ctx, req->newfid, pathinfo, req->newfid == req->fid))
srv_util_pathfree(ctx, LO_CALL(pathinfo->file, qid).path);
} else {
@@ -804,7 +841,7 @@ static void handle_Topen(struct _lib9p_srv_req *ctx,
struct srv_pathinfo *pathinfo = pathmap_load(&ctx->parent_sess->paths, fidinfo->path);
assert(pathinfo);
if (srv_util_pathisdir(pathinfo)) {
- if ( ((req->mode & LIB9P_O_MODE_MASK) != LIB9P_O_READ) ||
+ if ( ((req->mode & LIB9P_O_MODE_MASK) != LIB9P_O_MODE_READ) ||
(req->mode & LIB9P_O_TRUNC) ||
(req->mode & LIB9P_O_RCLOSE) ) {
lib9p_error(&ctx->ctx.basectx,
@@ -816,7 +853,6 @@ static void handle_Topen(struct _lib9p_srv_req *ctx,
/* Variables. */
lib9p_o_t reqmode = req->mode;
uint8_t fidflags = fidinfo->flags;
- uint32_t iounit = fidinfo->iounit;
/* Check permissions. */
if (reqmode & LIB9P_O_RCLOSE) {
@@ -831,13 +867,13 @@ static void handle_Topen(struct _lib9p_srv_req *ctx,
LINUX_EACCES, "permission denied to remove-on-close");
return;
}
- fidflags = fidflags | FIDFLAG_RCLOSE;
+ fidflags |= FIDFLAG_RCLOSE;
}
struct lib9p_stat stat = LO_CALL(pathinfo->file, stat, &ctx->ctx);
if (lib9p_ctx_has_error(&ctx->ctx.basectx))
return;
lib9p_stat_assert(stat);
- if ((stat.file_mode & LIB9P_DM_EXCL) && (pathinfo->rd_refcount || pathinfo->wr_refcount)) {
+ if ((stat.file_mode & LIB9P_DM_EXCL) && pathinfo->io_refcount) {
lib9p_error(&ctx->ctx.basectx,
LINUX_EEXIST, "exclusive file is already opened");
return;
@@ -847,19 +883,19 @@ static void handle_Topen(struct _lib9p_srv_req *ctx,
uint8_t perm_bits = 0;
bool rd = false, wr = false;
switch (reqmode & LIB9P_O_MODE_MASK) {
- case LIB9P_O_READ:
+ case LIB9P_O_MODE_READ:
perm_bits = 0b100;
rd = true;
break;
- case LIB9P_O_WRITE:
+ case LIB9P_O_MODE_WRITE:
perm_bits = 0b010;
wr = true;
break;
- case LIB9P_O_RDWR:
+ case LIB9P_O_MODE_RDWR:
perm_bits = 0b110;
rd = wr = true;
break;
- case LIB9P_O_EXEC:
+ case LIB9P_O_MODE_EXEC:
perm_bits = 0b001;
rd = true;
break;
@@ -870,26 +906,36 @@ static void handle_Topen(struct _lib9p_srv_req *ctx,
}
/* Actually make the call. */
- if ((reqmode & LIB9P_O_TRUNC) || (rd && !pathinfo->rd_refcount) || (wr && !pathinfo->wr_refcount) ) {
- iounit = LO_CALL(pathinfo->file, chio, &ctx->ctx,
- fidflags & FIDFLAG_OPEN_R,
- fidflags & FIDFLAG_OPEN_W,
- reqmode & LIB9P_O_TRUNC);
+ uint32_t iounit;
+ struct lib9p_qid qid;
+ if (srv_util_pathisdir(pathinfo)) {
+ fidinfo->dir.io = LO_CALL(pathinfo->file, dopen, &ctx->ctx);
+ assert(LO_IS_NULL(fidinfo->dir.io) == lib9p_ctx_has_error(&ctx->ctx.basectx));
if (lib9p_ctx_has_error(&ctx->ctx.basectx))
return;
+ fidinfo->dir.idx = 0;
+ fidinfo->dir.off = 0;
+ qid = LO_CALL(fidinfo->dir.io, qid);
+ iounit = 0;
+ } else {
+ fidinfo->file.io = LO_CALL(pathinfo->file, fopen, &ctx->ctx,
+ rd, wr,
+ reqmode & LIB9P_O_TRUNC);
+ assert(LO_IS_NULL(fidinfo->file.io) == lib9p_ctx_has_error(&ctx->ctx.basectx));
+ if (lib9p_ctx_has_error(&ctx->ctx.basectx))
+ return;
+ qid = LO_CALL(fidinfo->file.io, qid);
+ iounit = LO_CALL(fidinfo->file.io, iounit);
}
/* Success. */
- if (rd) {
- fidflags = fidflags | FIDFLAG_OPEN_R;
- pathinfo->rd_refcount++;
- }
- if (wr) {
- fidflags = fidflags | FIDFLAG_OPEN_W;
- pathinfo->wr_refcount++;
- }
+ if (rd)
+ fidflags |= FIDFLAG_OPEN_R;
+ if (wr)
+ fidflags |= FIDFLAG_OPEN_W;
+ pathinfo->io_refcount++;
fidinfo->flags = fidflags;
- resp->qid = stat.file_qid;
+ resp->qid = qid;
resp->iounit = iounit;
}
@@ -923,7 +969,6 @@ static void handle_Tread(struct _lib9p_srv_req *ctx,
/* Variables. */
struct srv_pathinfo *pathinfo = pathmap_load(&ctx->parent_sess->paths, fidinfo->path);
assert(pathinfo);
- resp->data = (char *)(&resp[1]);
/* Do it. */
if (srv_util_pathisdir(pathinfo)) {
@@ -931,16 +976,17 @@ static void handle_Tread(struct _lib9p_srv_req *ctx,
size_t idx;
if (req->offset == 0)
idx = 0;
- else if (req->offset == fidinfo->dir_off)
- idx = fidinfo->dir_idx;
+ else if (req->offset == fidinfo->dir.off)
+ idx = fidinfo->dir.idx;
else {
lib9p_errorf(&ctx->ctx.basectx,
LINUX_EINVAL, "invalid offset (must be 0 or %"PRIu64"): %"PRIu64,
- fidinfo->dir_off, req->offset);
+ fidinfo->dir.off, req->offset);
return;
}
/* Do it. */
- size_t num = LO_CALL(pathinfo->file, dread, &ctx->ctx, (uint8_t *)resp->data, req->count, idx);
+ resp->data = (char *)(&resp[1]);
+ size_t num = LO_CALL(fidinfo->dir.io, dread, &ctx->ctx, (uint8_t *)resp->data, req->count, idx);
/* Translate object-count back to byte-count. */
uint32_t len = 0;
for (size_t i = 0; i < num; i++) {
@@ -950,10 +996,18 @@ static void handle_Tread(struct _lib9p_srv_req *ctx,
}
resp->count = len;
/* Remember. */
- fidinfo->dir_idx = idx+num;
- fidinfo->dir_off = req->offset + len;
- } else
- resp->count = LO_CALL(pathinfo->file, pread, &ctx->ctx, resp->data, req->count, req->offset);
+ fidinfo->dir.idx = idx+num;
+ fidinfo->dir.off = req->offset + len;
+ } else {
+ struct iovec iov;
+ LO_CALL(fidinfo->file.io, pread, &ctx->ctx, req->count, req->offset, &iov);
+ if (!lib9p_ctx_has_error(&ctx->ctx.basectx)) {
+ resp->count = iov.iov_len;
+ resp->data = iov.iov_base;
+ if (resp->count > req->count)
+ resp->count = req->count;
+ }
+ }
}
static void handle_Twrite(struct _lib9p_srv_req *ctx,
@@ -979,7 +1033,7 @@ static void handle_Twrite(struct _lib9p_srv_req *ctx,
assert(pathinfo);
/* Do it. */
- resp->count = LO_CALL(pathinfo->file, pwrite, &ctx->ctx, req->data, req->count, req->offset);
+ resp->count = LO_CALL(fidinfo->file.io, pwrite, &ctx->ctx, req->data, req->count, req->offset);
}
static void clunkremove(struct _lib9p_srv_req *ctx, lib9p_fid_t fid, bool remove) {
@@ -1012,6 +1066,13 @@ static void clunkremove(struct _lib9p_srv_req *ctx, lib9p_fid_t fid, bool remove
}
clunk:
+ if (fidinfo->flags & FIDFLAG_OPEN) {
+ if (srv_util_pathisdir(pathinfo))
+ LO_CALL(fidinfo->dir.io, iofree);
+ else
+ LO_CALL(fidinfo->file.io, iofree);
+ pathinfo->io_refcount--;
+ }
srv_util_pathfree(ctx, LO_CALL(pathinfo->file, qid).path);
fidmap_del(&ctx->parent_sess->fids, fid);
}
diff --git a/lib9p/tables.c b/lib9p/tables.c
new file mode 100644
index 0000000..271b17b
--- /dev/null
+++ b/lib9p/tables.c
@@ -0,0 +1,186 @@
+/* lib9p/tables.c - Access tables of version and message information
+ *
+ * Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+ * SPDX-License-Identifier: AGPL-3.0-or-later
+ */
+
+#include <string.h>
+
+#include <libmisc/endian.h>
+#include <libmisc/log.h> /* for const_byte_str() */
+
+#include "tables.h"
+
+/* bounds checks **************************************************************/
+
+static inline void assert_ver(enum lib9p_version ver) {
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wtype-limits"
+ assert(0 <= ver && ver < LIB9P_VER_NUM);
+#pragma GCC diagnostic pop
+}
+
+static inline void assert_typ(enum lib9p_msg_type typ) {
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wtype-limits"
+ assert(0 <= typ && typ < 0xFF);
+#pragma GCC diagnostic pop
+}
+
+/* simple lookups *************************************************************/
+
+const char *lib9p_version_str(enum lib9p_version ver) {
+ assert_ver(ver);
+ return _lib9p_table_ver[ver].name;
+}
+
+uint32_t lib9p_version_min_msg_size(enum lib9p_version ver) {
+ assert_ver(ver);
+ return _lib9p_table_ver[ver].min_msg_size;
+}
+
+const char *lib9p_msgtype_str(enum lib9p_version ver, enum lib9p_msg_type typ) {
+ assert_ver(ver);
+ assert_typ(typ);
+ return _lib9p_table_msg[ver][typ].name ?: const_byte_str(typ);
+}
+
+lo_interface fmt_formatter lo_box_lib9p_msg_as_fmt_formatter(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body) {
+ assert(ctx);
+ assert_ver(ctx->version);
+ assert_typ(typ);
+ assert(_lib9p_table_msg[ctx->version][typ].box_as_fmt_formatter);
+ return _lib9p_table_msg[ctx->version][typ].box_as_fmt_formatter(body);
+}
+
+/* main message functions *****************************************************/
+
+static
+ssize_t _lib9p_validate(uint8_t xxx_low_typ_bit,
+ const char *xxx_errmsg,
+ const struct _lib9p_recv_tentry xxx_table[LIB9P_VER_NUM][0x80],
+ struct lib9p_ctx *ctx, uint8_t *net_bytes) {
+ assert_ver(ctx->version);
+ /* Inspect the first 5 bytes ourselves. */
+ uint32_t net_size = uint32le_decode(net_bytes);
+ if (net_size < 5)
+ return lib9p_error(ctx, LINUX_EBADMSG, "message is impossibly short");
+ uint8_t typ = net_bytes[4];
+ if (typ % 2 != xxx_low_typ_bit)
+ return lib9p_errorf(ctx, LINUX_EOPNOTSUPP, "%s: message_type=%s", xxx_errmsg,
+ lib9p_msgtype_str(ctx->version, typ));
+ struct _lib9p_recv_tentry tentry = xxx_table[ctx->version][typ/2];
+ if (!tentry.validate)
+ return lib9p_errorf(ctx, LINUX_EOPNOTSUPP, "unknown message type: %s (protocol_version=%s)",
+ lib9p_msgtype_str(ctx->version, typ), lib9p_version_str(ctx->version));
+
+ /* Now use the message-type-specific tentry to process the whole thing. */
+ return tentry.validate(ctx, net_size, net_bytes);
+}
+
+ssize_t lib9p_Tmsg_validate(struct lib9p_ctx *ctx, uint8_t *net_bytes) {
+ return _lib9p_validate(0, "expected a T-message but got an R-message", _lib9p_table_Tmsg_recv,
+ ctx, net_bytes);
+}
+
+ssize_t lib9p_Rmsg_validate(struct lib9p_ctx *ctx, uint8_t *net_bytes) {
+ return _lib9p_validate(1, "expected an R-message but got a T-message", _lib9p_table_Rmsg_recv,
+ ctx, net_bytes);
+}
+
+static
+void _lib9p_unmarshal(const struct _lib9p_recv_tentry xxx_table[LIB9P_VER_NUM][0x80],
+ struct lib9p_ctx *ctx, uint8_t *net_bytes,
+ enum lib9p_msg_type *ret_typ, void *ret_body) {
+ assert_ver(ctx->version);
+ enum lib9p_msg_type typ = net_bytes[4];
+ *ret_typ = typ;
+ struct _lib9p_recv_tentry tentry = xxx_table[ctx->version][typ/2];
+
+ tentry.unmarshal(ctx, net_bytes, ret_body);
+}
+
+void lib9p_Tmsg_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
+ enum lib9p_msg_type *ret_typ, void *ret_body) {
+ _lib9p_unmarshal(_lib9p_table_Tmsg_recv,
+ ctx, net_bytes, ret_typ, ret_body);
+}
+
+void lib9p_Rmsg_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
+ enum lib9p_msg_type *ret_typ, void *ret_body) {
+ _lib9p_unmarshal(_lib9p_table_Rmsg_recv,
+ ctx, net_bytes, ret_typ, ret_body);
+}
+
+static
+bool _lib9p_marshal(const struct _lib9p_send_tentry xxx_table[LIB9P_VER_NUM][0x80],
+ struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
+ size_t *ret_iov_cnt, struct iovec *ret_iov, uint8_t *ret_copied) {
+ assert_ver(ctx->version);
+ assert_typ(typ);
+ struct _marshal_ret ret = {
+ .net_iov_cnt = 1,
+ .net_iov = ret_iov,
+ .net_copied_size = 0,
+ .net_copied = ret_copied,
+ };
+
+ struct _lib9p_send_tentry tentry = xxx_table[ctx->version][typ/2];
+ bool ret_erred = tentry.marshal(ctx, body, &ret);
+ if (ret_iov[ret.net_iov_cnt-1].iov_len == 0)
+ ret.net_iov_cnt--;
+ *ret_iov_cnt = ret.net_iov_cnt;
+ return ret_erred;
+}
+
+bool lib9p_Tmsg_marshal(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
+ struct lib9p_Tmsg_send_buf *ret) {
+ assert(typ % 2 == 0);
+ memset(ret, 0, sizeof(*ret));
+ return _lib9p_marshal(_lib9p_table_Tmsg_send,
+ ctx, typ, body,
+ &ret->iov_cnt, ret->iov, ret->copied);
+}
+
+bool lib9p_Rmsg_marshal(struct lib9p_ctx *ctx, enum lib9p_msg_type typ, void *body,
+ struct lib9p_Rmsg_send_buf *ret) {
+ assert(typ % 2 == 1);
+ memset(ret, 0, sizeof(*ret));
+ return _lib9p_marshal(_lib9p_table_Rmsg_send,
+ ctx, typ, body,
+ &ret->iov_cnt, ret->iov, ret->copied);
+}
+
+/* `struct lib9p_stat` helpers ************************************************/
+
+bool lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes,
+ uint32_t *ret_net_size, ssize_t *ret_host_size) {
+ ssize_t host_size = _lib9p_stat_validate(ctx, net_size, net_bytes, ret_net_size);
+ if (host_size < 0)
+ return true;
+ if (ret_host_size)
+ *ret_host_size = host_size;
+ return false;
+}
+
+void lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes,
+ struct lib9p_stat *ret) {
+ _lib9p_stat_unmarshal(ctx, net_bytes, ret);
+}
+
+uint32_t lib9p_stat_marshal(struct lib9p_ctx *ctx, uint32_t max_net_size, struct lib9p_stat *obj,
+ uint8_t *ret_bytes) {
+ struct lib9p_ctx _ctx = *ctx;
+ _ctx.max_msg_size = max_net_size;
+
+ struct iovec iov = {0};
+ struct _marshal_ret ret = {
+ .net_iov_cnt = 1,
+ .net_iov = &iov,
+ .net_copied_size = 0,
+ .net_copied = ret_bytes,
+ };
+ if (_lib9p_stat_marshal(&_ctx, obj, &ret))
+ return 0;
+ return ret.net_iov[0].iov_len;
+}
diff --git a/lib9p/tables.h b/lib9p/tables.h
new file mode 100644
index 0000000..edb402a
--- /dev/null
+++ b/lib9p/tables.h
@@ -0,0 +1,59 @@
+/* lib9p/tables.h - Declare tables of version and message information
+ *
+ * Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+ * SPDX-License-Identifier: AGPL-3.0-or-later
+ */
+
+#ifndef _LIB9P_TABLES_H_
+#define _LIB9P_TABLES_H_
+
+#include <lib9p/9p.h>
+
+/* version ********************************************************************/
+
+struct _lib9p_ver_tentry {
+ const char *name;
+ uint32_t min_msg_size;
+};
+
+extern const struct _lib9p_ver_tentry _lib9p_table_ver[LIB9P_VER_NUM];
+
+/* message ********************************************************************/
+
+typedef lo_interface fmt_formatter (*_box_as_fmt_formatter_fn_t)(void *host_val);
+struct _lib9p_msg_tentry {
+ const char *name;
+ _box_as_fmt_formatter_fn_t box_as_fmt_formatter;
+};
+
+typedef ssize_t (*_validate_fn_t)(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes);
+typedef void (*_unmarshal_fn_t)(struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out);
+struct _lib9p_recv_tentry {
+ _validate_fn_t validate;
+ _unmarshal_fn_t unmarshal;
+};
+
+struct _marshal_ret {
+ size_t net_iov_cnt;
+ struct iovec *net_iov;
+ size_t net_copied_size;
+ uint8_t *net_copied;
+};
+typedef bool (*_marshal_fn_t)(struct lib9p_ctx *ctx, void *host_val, struct _marshal_ret *ret);
+struct _lib9p_send_tentry {
+ _marshal_fn_t marshal;
+};
+
+extern const struct _lib9p_msg_tentry _lib9p_table_msg[LIB9P_VER_NUM][0x100];
+extern const struct _lib9p_recv_tentry _lib9p_table_Tmsg_recv[LIB9P_VER_NUM][0x80];
+extern const struct _lib9p_recv_tentry _lib9p_table_Rmsg_recv[LIB9P_VER_NUM][0x80];
+extern const struct _lib9p_send_tentry _lib9p_table_Tmsg_send[LIB9P_VER_NUM][0x80];
+extern const struct _lib9p_send_tentry _lib9p_table_Rmsg_send[LIB9P_VER_NUM][0x80];
+
+/* stat ***********************************************************************/
+
+ssize_t _lib9p_stat_validate(struct lib9p_ctx *ctx, uint32_t net_size, uint8_t *net_bytes, uint32_t *ret_net_size);
+void _lib9p_stat_unmarshal(struct lib9p_ctx *ctx, uint8_t *net_bytes, void *out);
+bool _lib9p_stat_marshal(struct lib9p_ctx *ctx, struct lib9p_stat *val, struct _marshal_ret *ret);
+
+#endif /* _LIB9P_TABLES_H_ */
diff --git a/lib9p/tests/test_compile.c b/lib9p/tests/test_compile.c
index 6abee05..8f2445d 100644
--- a/lib9p/tests/test_compile.c
+++ b/lib9p/tests/test_compile.c
@@ -8,14 +8,26 @@ int main(void) {
x = LIB9P_DM_DIR;
x = LIB9P_DM_APPEND;
x = LIB9P_DM_EXCL;
- x = _LIB9P_DM_RESERVED_PLAN9_MOUNT;
+ x = _LIB9P_DM_PLAN9_MOUNT;
x = LIB9P_DM_AUTH;
x = LIB9P_DM_TMP;
+ x = _LIB9P_DM_UNUSED_25;
+ x = _LIB9P_DM_UNUSED_24;
x = LIB9P_DM_DEVICE;
- x = LIB9P_DM_NAMEDPIPE;
+ x = _LIB9P_DM_UNUSED_22;
+ x = LIB9P_DM_PIPE;
x = LIB9P_DM_SOCKET;
x = LIB9P_DM_SETUID;
x = LIB9P_DM_SETGID;
+ x = _LIB9P_DM_UNUSED_17;
+ x = _LIB9P_DM_UNUSED_16;
+ x = _LIB9P_DM_UNUSED_15;
+ x = _LIB9P_DM_UNUSED_14;
+ x = _LIB9P_DM_UNUSED_13;
+ x = _LIB9P_DM_UNUSED_12;
+ x = _LIB9P_DM_UNUSED_11;
+ x = _LIB9P_DM_UNUSED_10;
+ x = _LIB9P_DM_UNUSED_9;
x = LIB9P_DM_OWNER_R;
x = LIB9P_DM_OWNER_W;
x = LIB9P_DM_OWNER_X;
@@ -29,25 +41,38 @@ int main(void) {
x = LIB9P_QT_DIR;
x = LIB9P_QT_APPEND;
x = LIB9P_QT_EXCL;
- x = _LIB9P_QT_RESERVED_PLAN9_MOUNT;
+ x = _LIB9P_QT_PLAN9_MOUNT;
x = LIB9P_QT_AUTH;
x = LIB9P_QT_TMP;
x = LIB9P_QT_SYMLINK;
+ x = _LIB9P_QT_UNUSED_0;
x = LIB9P_QT_FILE;
x = LIB9P_NUID_NONUID;
+ x = _LIB9P_O_UNUSED_7;
x = LIB9P_O_RCLOSE;
x = _LIB9P_O_RESERVED_CEXEC;
x = LIB9P_O_TRUNC;
- x = _LIB9P_O_mode_1;
- x = _LIB9P_O_mode_0;
- x = LIB9P_O_READ;
- x = LIB9P_O_WRITE;
- x = LIB9P_O_RDWR;
- x = LIB9P_O_EXEC;
- x = LIB9P_O_MODE_MASK;
+ x = _LIB9P_O_UNUSED_3;
+ x = _LIB9P_O_UNUSED_2;
x = LIB9P_O_FLAG_MASK;
+ x = LIB9P_O_MODE_READ;
+ x = LIB9P_O_MODE_WRITE;
+ x = LIB9P_O_MODE_RDWR;
+ x = LIB9P_O_MODE_EXEC;
+ x = LIB9P_O_MODE_MASK;
x = LIB9P_ERRNO_NOERROR;
x = LIB9P_SUPER_MAGIC_V9FS_MAGIC;
+ x = _LIB9P_LO_UNUSED_31;
+ x = _LIB9P_LO_UNUSED_30;
+ x = _LIB9P_LO_UNUSED_29;
+ x = _LIB9P_LO_UNUSED_28;
+ x = _LIB9P_LO_UNUSED_27;
+ x = _LIB9P_LO_UNUSED_26;
+ x = _LIB9P_LO_UNUSED_25;
+ x = _LIB9P_LO_UNUSED_24;
+ x = _LIB9P_LO_UNUSED_23;
+ x = _LIB9P_LO_UNUSED_22;
+ x = _LIB9P_LO_UNUSED_21;
x = LIB9P_LO_SYNC;
x = LIB9P_LO_CLOEXEC;
x = LIB9P_LO_NOATIME;
@@ -63,27 +88,41 @@ int main(void) {
x = LIB9P_LO_NOCTTY;
x = LIB9P_LO_EXCL;
x = LIB9P_LO_CREATE;
- x = _LIB9P_LO_mode_1;
- x = _LIB9P_LO_mode_0;
- x = LIB9P_LO_RDONLY;
- x = LIB9P_LO_WRONLY;
- x = LIB9P_LO_RDWR;
- x = LIB9P_LO_NOACCESS;
- x = LIB9P_LO_MODE_MASK;
+ x = _LIB9P_LO_UNUSED_5;
+ x = _LIB9P_LO_UNUSED_4;
+ x = _LIB9P_LO_UNUSED_3;
+ x = _LIB9P_LO_UNUSED_2;
x = LIB9P_LO_FLAG_MASK;
+ x = LIB9P_LO_MODE_RDONLY;
+ x = LIB9P_LO_MODE_WRONLY;
+ x = LIB9P_LO_MODE_RDWR;
+ x = LIB9P_LO_MODE_NOACCESS;
+ x = LIB9P_LO_MODE_MASK;
x = LIB9P_DT_UNKNOWN;
- x = LIB9P_DT_NAMED_PIPE;
+ x = LIB9P_DT_PIPE;
x = LIB9P_DT_CHAR_DEV;
x = LIB9P_DT_DIRECTORY;
x = LIB9P_DT_BLOCK_DEV;
x = LIB9P_DT_REGULAR;
x = LIB9P_DT_SYMLINK;
x = LIB9P_DT_SOCKET;
- x = LIB9P_DT_WHITEOUT;
- x = _LIB9P_MODE_fmt_3;
- x = _LIB9P_MODE_fmt_2;
- x = _LIB9P_MODE_fmt_1;
- x = _LIB9P_MODE_fmt_0;
+ x = _LIB9P_DT_WHITEOUT;
+ x = _LIB9P_MODE_UNUSED_31;
+ x = _LIB9P_MODE_UNUSED_30;
+ x = _LIB9P_MODE_UNUSED_29;
+ x = _LIB9P_MODE_UNUSED_28;
+ x = _LIB9P_MODE_UNUSED_27;
+ x = _LIB9P_MODE_UNUSED_26;
+ x = _LIB9P_MODE_UNUSED_25;
+ x = _LIB9P_MODE_UNUSED_24;
+ x = _LIB9P_MODE_UNUSED_23;
+ x = _LIB9P_MODE_UNUSED_22;
+ x = _LIB9P_MODE_UNUSED_21;
+ x = _LIB9P_MODE_UNUSED_20;
+ x = _LIB9P_MODE_UNUSED_19;
+ x = _LIB9P_MODE_UNUSED_18;
+ x = _LIB9P_MODE_UNUSED_17;
+ x = _LIB9P_MODE_UNUSED_16;
x = LIB9P_MODE_PERM_SETGROUP;
x = LIB9P_MODE_PERM_SETUSER;
x = LIB9P_MODE_PERM_STICKY;
@@ -96,17 +135,67 @@ int main(void) {
x = LIB9P_MODE_PERM_OTHER_R;
x = LIB9P_MODE_PERM_OTHER_W;
x = LIB9P_MODE_PERM_OTHER_X;
- x = LIB9P_MODE_FMT_NAMED_PIPE;
+ x = LIB9P_MODE_PERM_MASK;
+ x = LIB9P_MODE_FMT_PIPE;
x = LIB9P_MODE_FMT_CHAR_DEV;
x = LIB9P_MODE_FMT_DIRECTORY;
x = LIB9P_MODE_FMT_BLOCK_DEV;
x = LIB9P_MODE_FMT_REGULAR;
x = LIB9P_MODE_FMT_SYMLINK;
x = LIB9P_MODE_FMT_SOCKET;
- x = LIB9P_MODE_PERM_MASK;
x = LIB9P_MODE_FMT_MASK;
x = LIB9P_B4_FALSE;
x = LIB9P_B4_TRUE;
+ x = _LIB9P_GETATTR_UNUSED_63;
+ x = _LIB9P_GETATTR_UNUSED_62;
+ x = _LIB9P_GETATTR_UNUSED_61;
+ x = _LIB9P_GETATTR_UNUSED_60;
+ x = _LIB9P_GETATTR_UNUSED_59;
+ x = _LIB9P_GETATTR_UNUSED_58;
+ x = _LIB9P_GETATTR_UNUSED_57;
+ x = _LIB9P_GETATTR_UNUSED_56;
+ x = _LIB9P_GETATTR_UNUSED_55;
+ x = _LIB9P_GETATTR_UNUSED_54;
+ x = _LIB9P_GETATTR_UNUSED_53;
+ x = _LIB9P_GETATTR_UNUSED_52;
+ x = _LIB9P_GETATTR_UNUSED_51;
+ x = _LIB9P_GETATTR_UNUSED_50;
+ x = _LIB9P_GETATTR_UNUSED_49;
+ x = _LIB9P_GETATTR_UNUSED_48;
+ x = _LIB9P_GETATTR_UNUSED_47;
+ x = _LIB9P_GETATTR_UNUSED_46;
+ x = _LIB9P_GETATTR_UNUSED_45;
+ x = _LIB9P_GETATTR_UNUSED_44;
+ x = _LIB9P_GETATTR_UNUSED_43;
+ x = _LIB9P_GETATTR_UNUSED_42;
+ x = _LIB9P_GETATTR_UNUSED_41;
+ x = _LIB9P_GETATTR_UNUSED_40;
+ x = _LIB9P_GETATTR_UNUSED_39;
+ x = _LIB9P_GETATTR_UNUSED_38;
+ x = _LIB9P_GETATTR_UNUSED_37;
+ x = _LIB9P_GETATTR_UNUSED_36;
+ x = _LIB9P_GETATTR_UNUSED_35;
+ x = _LIB9P_GETATTR_UNUSED_34;
+ x = _LIB9P_GETATTR_UNUSED_33;
+ x = _LIB9P_GETATTR_UNUSED_32;
+ x = _LIB9P_GETATTR_UNUSED_31;
+ x = _LIB9P_GETATTR_UNUSED_30;
+ x = _LIB9P_GETATTR_UNUSED_29;
+ x = _LIB9P_GETATTR_UNUSED_28;
+ x = _LIB9P_GETATTR_UNUSED_27;
+ x = _LIB9P_GETATTR_UNUSED_26;
+ x = _LIB9P_GETATTR_UNUSED_25;
+ x = _LIB9P_GETATTR_UNUSED_24;
+ x = _LIB9P_GETATTR_UNUSED_23;
+ x = _LIB9P_GETATTR_UNUSED_22;
+ x = _LIB9P_GETATTR_UNUSED_21;
+ x = _LIB9P_GETATTR_UNUSED_20;
+ x = _LIB9P_GETATTR_UNUSED_19;
+ x = _LIB9P_GETATTR_UNUSED_18;
+ x = _LIB9P_GETATTR_UNUSED_17;
+ x = _LIB9P_GETATTR_UNUSED_16;
+ x = _LIB9P_GETATTR_UNUSED_15;
+ x = _LIB9P_GETATTR_UNUSED_14;
x = LIB9P_GETATTR_DATA_VERSION;
x = LIB9P_GETATTR_GEN;
x = LIB9P_GETATTR_BTIME;
@@ -123,6 +212,29 @@ int main(void) {
x = LIB9P_GETATTR_MODE;
x = LIB9P_GETATTR_BASIC;
x = LIB9P_GETATTR_ALL;
+ x = _LIB9P_SETATTR_UNUSED_31;
+ x = _LIB9P_SETATTR_UNUSED_30;
+ x = _LIB9P_SETATTR_UNUSED_29;
+ x = _LIB9P_SETATTR_UNUSED_28;
+ x = _LIB9P_SETATTR_UNUSED_27;
+ x = _LIB9P_SETATTR_UNUSED_26;
+ x = _LIB9P_SETATTR_UNUSED_25;
+ x = _LIB9P_SETATTR_UNUSED_24;
+ x = _LIB9P_SETATTR_UNUSED_23;
+ x = _LIB9P_SETATTR_UNUSED_22;
+ x = _LIB9P_SETATTR_UNUSED_21;
+ x = _LIB9P_SETATTR_UNUSED_20;
+ x = _LIB9P_SETATTR_UNUSED_19;
+ x = _LIB9P_SETATTR_UNUSED_18;
+ x = _LIB9P_SETATTR_UNUSED_17;
+ x = _LIB9P_SETATTR_UNUSED_16;
+ x = _LIB9P_SETATTR_UNUSED_15;
+ x = _LIB9P_SETATTR_UNUSED_14;
+ x = _LIB9P_SETATTR_UNUSED_13;
+ x = _LIB9P_SETATTR_UNUSED_12;
+ x = _LIB9P_SETATTR_UNUSED_11;
+ x = _LIB9P_SETATTR_UNUSED_10;
+ x = _LIB9P_SETATTR_UNUSED_9;
x = LIB9P_SETATTR_MTIME_SET;
x = LIB9P_SETATTR_ATIME_SET;
x = LIB9P_SETATTR_CTIME;
@@ -135,6 +247,36 @@ int main(void) {
x = LIB9P_LOCK_TYPE_RDLCK;
x = LIB9P_LOCK_TYPE_WRLCK;
x = LIB9P_LOCK_TYPE_UNLCK;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_31;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_30;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_29;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_28;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_27;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_26;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_25;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_24;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_23;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_22;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_21;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_20;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_19;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_18;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_17;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_16;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_15;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_14;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_13;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_12;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_11;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_10;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_9;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_8;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_7;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_6;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_5;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_4;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_3;
+ x = _LIB9P_LOCK_FLAGS_UNUSED_2;
x = LIB9P_LOCK_FLAGS_RECLAIM;
x = LIB9P_LOCK_FLAGS_BLOCK;
x = LIB9P_LOCK_STATUS_SUCCESS;
diff --git a/lib9p/tests/test_compile_config/config.h b/lib9p/tests/test_compile_config/config.h
index 38ab0c0..cc8eec1 100644
--- a/lib9p/tests/test_compile_config/config.h
+++ b/lib9p/tests/test_compile_config/config.h
@@ -9,20 +9,20 @@
/* 9P *************************************************************************/
-#define CONFIG_9P_MAX_MSG_SIZE ((4*1024)+24)
-#define CONFIG_9P_MAX_HOSTMSG_SIZE CONFIG_9P_MAX_MSG_SIZE+16
-#define CONFIG_9P_MAX_ERR_SIZE 128
-#define CONFIG_9P_MAX_9P2000_e_WELEM 16
-
-#define CONFIG_9P_SRV_MAX_FIDS 16
-#define CONFIG_9P_SRV_MAX_REQS 2
-#define CONFIG_9P_SRV_MAX_DEPTH 3
-
-#define CONFIG_9P_ENABLE_9P2000 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_u 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_e 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_L 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_p9p 1 /* bool */
+#define CONFIG_9P_MAX_ERR_SIZE 128
+#define CONFIG_9P_MAX_9P2000_e_WELEM 16
+
+#define CONFIG_9P_SRV_MAX_MSG_SIZE ((4*1024)+24)
+#define CONFIG_9P_SRV_MAX_HOSTMSG_SIZE CONFIG_9P_SRV_MAX_MSG_SIZE+16
+#define CONFIG_9P_SRV_MAX_FIDS 16
+#define CONFIG_9P_SRV_MAX_REQS 2
+#define CONFIG_9P_SRV_MAX_DEPTH 3
+
+#define CONFIG_9P_ENABLE_9P2000 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_u 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_e 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_L 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_p9p 1 /* bool */
/* COROUTINE ******************************************************************/
diff --git a/lib9p/tests/test_server/CMakeLists.txt b/lib9p/tests/test_server/CMakeLists.txt
index 74a759d..5313917 100644
--- a/lib9p/tests/test_server/CMakeLists.txt
+++ b/lib9p/tests/test_server/CMakeLists.txt
@@ -18,7 +18,7 @@ target_link_libraries(test_server_objs
libmisc
lib9p
lib9p_util
- libhw
+ libhw_cr
)
# Analyze the stack ############################################################
diff --git a/lib9p/tests/test_server/config/config.h b/lib9p/tests/test_server/config/config.h
index 67960ca..03143e1 100644
--- a/lib9p/tests/test_server/config/config.h
+++ b/lib9p/tests/test_server/config/config.h
@@ -1,4 +1,4 @@
-/* config.h - Compile-time configuration for srv9p
+/* config.h - Compile-time configuration for lib9p/test/test_server
*
* Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
* SPDX-License-Identifier: AGPL-3.0-or-later
@@ -12,7 +12,8 @@
/* 9P *************************************************************************/
-#define CONFIG_9P_PORT LIB9P_DEFAULT_PORT_9FS
+#define CONFIG_9P_MAX_ERR_SIZE 128 /* 128 is what Plan 9 4e uses */
+
/**
* This max-msg-size is sized so that a Twrite message can return
* 8KiB of data.
@@ -30,22 +31,22 @@
* negotiated. In Plan 9 1e it was (8*1024)+128, and was bumped to
* (8*1024)+160 in 2e and 3e.
*/
-#define CONFIG_9P_MAX_MSG_SIZE ((4*1024)+24)
+#define CONFIG_9P_SRV_MAX_MSG_SIZE ((4*1024)+24)
/**
* Maximum host-data-structure size. A message may be larger in
* unmarshaled-host-structures than marshaled-net-bytes due to (1)
* struct padding, (2) array pointers.
*/
-#define CONFIG_9P_MAX_HOSTMSG_SIZE CONFIG_9P_MAX_MSG_SIZE+16
-#define CONFIG_9P_MAX_ERR_SIZE 128 /* 128 is what Plan 9 4e uses */
-#define CONFIG_9P_SRV_MAX_FIDS 16
-#define CONFIG_9P_SRV_MAX_REQS 2
-#define CONFIG_9P_SRV_MAX_DEPTH 3
-#define CONFIG_9P_ENABLE_9P2000 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_u 1 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_e 0 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_L 0 /* bool */
-#define CONFIG_9P_ENABLE_9P2000_p9p 0 /* bool */
+#define CONFIG_9P_SRV_MAX_HOSTMSG_SIZE CONFIG_9P_SRV_MAX_MSG_SIZE+16
+#define CONFIG_9P_SRV_MAX_FIDS 16
+#define CONFIG_9P_SRV_MAX_REQS 2
+#define CONFIG_9P_SRV_MAX_DEPTH 3
+
+#define CONFIG_9P_ENABLE_9P2000 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_u 1 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_e 0 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_L 0 /* bool */
+#define CONFIG_9P_ENABLE_9P2000_p9p 0 /* bool */
/* COROUTINE ******************************************************************/
diff --git a/lib9p/tests/test_server/main.c b/lib9p/tests/test_server/main.c
index 074dbe7..c759029 100644
--- a/lib9p/tests/test_server/main.c
+++ b/lib9p/tests/test_server/main.c
@@ -48,7 +48,10 @@ struct api_file {
uint64_t pathnum;
};
LO_IMPLEMENTATION_H(lib9p_srv_file, struct api_file, api)
+LO_IMPLEMENTATION_H(lib9p_srv_fio, struct api_file, api)
+
LO_IMPLEMENTATION_C(lib9p_srv_file, struct api_file, api, static)
+LO_IMPLEMENTATION_C(lib9p_srv_fio, struct api_file, api, static)
static void api_free(struct api_file *self) {
assert(self);
@@ -61,11 +64,6 @@ static struct lib9p_qid api_qid(struct api_file *self) {
.path = self->pathnum,
};
}
-static uint32_t api_chio(struct api_file *self, struct lib9p_srv_ctx *ctx, bool, bool, bool) {
- assert(self);
- assert(ctx);
- return 0;
-}
static struct lib9p_stat api_stat(struct api_file *self, struct lib9p_srv_ctx *ctx) {
assert(self);
@@ -101,6 +99,21 @@ static void api_remove(struct api_file *self, struct lib9p_srv_ctx *ctx) {
LIB9P_SRV_NOTDIR(struct api_file, api)
+static lo_interface lib9p_srv_fio api_fopen(struct api_file *self, struct lib9p_srv_ctx *ctx, bool, bool, bool) {
+ assert(self);
+ assert(ctx);
+ return lo_box_api_as_lib9p_srv_fio(self);
+}
+
+static void api_iofree(struct api_file *self) {
+ assert(self);
+}
+
+static uint32_t api_iounit(struct api_file *self) {
+ assert(self);
+ return 0;
+}
+
static uint32_t api_pwrite(struct api_file *self, struct lib9p_srv_ctx *ctx, void *buf, uint32_t byte_count, uint64_t LM_UNUSED(offset)) {
assert(self);
assert(ctx);
@@ -111,7 +124,9 @@ static uint32_t api_pwrite(struct api_file *self, struct lib9p_srv_ctx *ctx, voi
LO_CALL(lo_box_hostnet_tcplist_as_net_stream_listener(&globals.listeners[i]), close);
return byte_count;
}
-static uint32_t api_pread(struct api_file *, struct lib9p_srv_ctx *, void *, uint32_t, uint64_t) {
+static void api_pread(struct api_file *LM_UNUSED(self), struct lib9p_srv_ctx *LM_UNUSED(ctx),
+ uint32_t LM_UNUSED(byte_count), uint64_t LM_UNUSED(byte_offset),
+ struct iovec *LM_UNUSED(ret)) {
assert_notreached("not readable");
}
diff --git a/lib9p/utf8.h b/lib9p/utf8.h
new file mode 100644
index 0000000..5ffd674
--- /dev/null
+++ b/lib9p/utf8.h
@@ -0,0 +1,34 @@
+/* lib9p/utf8.h - Internal UTF-8 validation
+ *
+ * Copyright (C) 2024-2025 Luke T. Shumaker <lukeshu@lukeshu.com>
+ * SPDX-License-Identifier: AGPL-3.0-or-later
+ */
+
+#ifndef _LIB9P_UTF8_H_
+#define _LIB9P_UTF8_H_
+
+static inline bool _is_valid_utf8(uint8_t *str, size_t len, bool forbid_nul) {
+ uint32_t ch;
+ uint8_t chlen;
+ assert(str);
+ for (size_t pos = 0; pos < len;) {
+ if ((str[pos] & 0b10000000) == 0b00000000) { ch = str[pos] & 0b01111111; chlen = 1; }
+ else if ((str[pos] & 0b11100000) == 0b11000000) { ch = str[pos] & 0b00011111; chlen = 2; }
+ else if ((str[pos] & 0b11110000) == 0b11100000) { ch = str[pos] & 0b00001111; chlen = 3; }
+ else if ((str[pos] & 0b11111000) == 0b11110000) { ch = str[pos] & 0b00000111; chlen = 4; }
+ else return false;
+ if ((ch == 0 && (chlen != 1 || forbid_nul)) || pos + chlen > len) return false;
+ for (uint8_t i = 1; i < chlen; i++) {
+ if ((str[pos+i] & 0b11000000) != 0b10000000) return false;
+ ch = (ch << 6) | (str[pos+i] & 0b00111111);
+ }
+ if (ch > 0x10FFFF) return false;
+ pos += chlen;
+ }
+ return true;
+}
+
+#define is_valid_utf8(str, len) _is_valid_utf8(str, len, false)
+#define is_valid_utf8_without_nul(str, len) _is_valid_utf8(str, len, true)
+
+#endif /* _LIB9P_UTF8_H_ */