From cc3a585e37cf58b61cbea599cc4de93cf713834b Mon Sep 17 00:00:00 2001 From: "Luke T. Shumaker" Date: Sat, 5 Oct 2024 08:14:27 -0600 Subject: compiles --- lib9p/include/lib9p/srv.h | 4 ++-- lib9p/map.h | 4 ++-- lib9p/srv.c | 44 +++++++++++++++++++++++++++++--------------- 3 files changed, 33 insertions(+), 19 deletions(-) (limited to 'lib9p') diff --git a/lib9p/include/lib9p/srv.h b/lib9p/include/lib9p/srv.h index d2ada62..6a6fed0 100644 --- a/lib9p/include/lib9p/srv.h +++ b/lib9p/include/lib9p/srv.h @@ -16,14 +16,14 @@ struct lib9p_srv_reqctx { static inline bool flush_requested(struct lib9p_srv_reqctx *ctx) { assert(ctx); - return cr_chan_can_write(&ctx->_flushch); + return cr_chan_can_send(&ctx->_flushch); } static inline int acknowledge_flush(struct lib9p_srv_reqctx *ctx) { assert(ctx); assert(cr_chan_can_send(&ctx->_flushch)); lib9p_error(ctx->base, LINUX_ECANCELED, "request canceled by flush"); - cr_chan_send(&ctx->_flushch, true); + cr_chan_send(&ctx->_flushch, (bool)true); return -1; } diff --git a/lib9p/map.h b/lib9p/map.h index ea9cdb6..833f4f5 100644 --- a/lib9p/map.h +++ b/lib9p/map.h @@ -28,8 +28,8 @@ #define MAP_KV(TNAME) CAT3(_,TNAME,_kv) #define MAP_METHOD(TNAME, MNAME) CAT3(TNAME,_,MNAME) #define MAP_FOREACH(m, k, v) \ - for (size_t i = 0, typeof(m->items[0].key) k, typeof(&m->items[0].val) v; i < ARRAY_LEN(m->items); i++) \ - if ( ({ k = m->items[i].key; v = &m->items[i].val; m->items[i].set; }) ) + for (size_t i = 0; i < ARRAY_LEN((m)->items); i++) \ + if ( ({ k = (m)->items[i].key; v = &(m)->items[i].val; (m)->items[i].set; }) ) #endif /* This implementation is just an array that we brute-force search diff --git a/lib9p/srv.c b/lib9p/srv.c index 3d990aa..9bfe19e 100644 --- a/lib9p/srv.c +++ b/lib9p/srv.c @@ -21,7 +21,7 @@ #define NAME reqmap #define KEY_T uint32_t -#define VAL_T struct lib9p_reqctx +#define VAL_T struct lib9p_srv_reqctx #define CAP CONFIG_9P_MAX_REQS #include "map.h" @@ -50,6 +50,7 @@ struct lib9p_sess { uint32_t rerror_overhead; /* mutable */ bool initialized; + bool closing; struct reqmap reqs; struct fidmap fids; }; @@ -157,7 +158,6 @@ COROUTINE lib9p_srv_read_cr(void *_srv) { .max_msg_size = CONFIG_9P_MAX_MSG_SIZE, .rerror_overhead = initial_rerror_overhead, .initialized = false, - .refcount = 1, }; for (;;) { /* Read the message. */ @@ -190,15 +190,15 @@ COROUTINE lib9p_srv_read_cr(void *_srv) { goto close; /* Handle the message... in another coroutine. */ - sess.refcount++; cr_chan_send(&srv->reqch, &req); cr_pause_and_yield(); /* wait for it to have copied req */ } close: - netio_close(conn.fd, true, (--sess.refcount) == 0); - if (sess.refcount) { + netio_close(conn.fd, true, sess.reqs.len == 0); + if (sess.reqs.len) { + sess.closing = true; cr_pause_and_yield(); - assert(sess.refcount == 0); + assert(sess.reqs.len == 0); netio_close(conn.fd, false, true); } } @@ -244,7 +244,8 @@ COROUTINE lib9p_srv_write_cr(void *_srv) { handle_Tmessage(&req); - if ((--req.parent_sess->refcount) == 0) + reqmap_del(&req.parent_sess->reqs, req.tag); + if (req.parent_sess->closing && !req.parent_sess->reqs.len) cr_unpause(req.parent_sess->parent_conn->reader); } @@ -327,14 +328,16 @@ static bool handle_Tmessage(struct lib9p_req *req) { } write: - if (lib9p_ctx_has_error(&req->ctx)) + if (lib9p_ctx_has_error(&req->ctx)) { respond_error(req); - else { + return true; + } else { if (lib9p_marshal(&req->ctx, typ+1, req->tag, host_resp, req->net_bytes)) goto write; cr_mutex_lock(&req->parent_sess->parent_conn->writelock); netio_write(req->parent_sess->parent_conn->fd, req->net_bytes, decode_u32le(req->net_bytes)); cr_mutex_unlock(&req->parent_sess->parent_conn->writelock); + return false; } } @@ -364,13 +367,24 @@ static void handle_Tversion(struct lib9p_req *ctx, struct lib9p_msg_Tversion *re return; } - - ctx->parent_sess--; - MAP_FOREACH(&ctx->parent_sess->fids, fid, fptr) { - fptr->vtable.free(subctx, fptr->impldata); - fidmap_del(&ctx->parent_sess->fids, fid); + struct lib9p_srv_reqctx subctx = { + .base = &ctx->ctx, + }; + if (ctx->parent_sess->reqs.len) { + ctx->parent_sess->closing = true; + // TODO: send flush events + cr_pause_and_yield(); + assert(ctx->parent_sess->reqs.len == 0); } -} + if (ctx->parent_sess->fids.len) { + uint32_t fid; + struct lib9p_srv_file *fptr; + MAP_FOREACH(&ctx->parent_sess->fids, fid, fptr) { + fptr->vtable.free(&subctx, fptr->impldata); + fidmap_del(&ctx->parent_sess->fids, fid); + } + } + // TODO: replace session with a new one? #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wdiscarded-qualifiers" -- cgit v1.2.3-2-g168b