[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [UNIKRAFT PATCH v2 2/9] lib/uk9p: Switch to using the new serialization
This patch migrates 9p.c and 9pfs to use the new serialization implementation. Signed-off-by: Cristian Banu <cristb@xxxxxxxxx> --- lib/9pfs/9pfs_vnops.c | 2 +- lib/uk9p/9p.c | 302 +++++++++++++++++++++++++----------------- lib/uk9p/9preq.c | 27 ++-- 3 files changed, 192 insertions(+), 139 deletions(-) diff --git a/lib/9pfs/9pfs_vnops.c b/lib/9pfs/9pfs_vnops.c index 5e6a7bb..6d3ece3 100644 --- a/lib/9pfs/9pfs_vnops.c +++ b/lib/9pfs/9pfs_vnops.c @@ -409,7 +409,7 @@ again: fake_request.recv.size = fd->readdir_sz; fake_request.recv.offset = fd->readdir_off; fake_request.state = UK_9PREQ_RECEIVED; - rc = uk_9preq_deserialize(&fake_request, "S", &stat); + rc = uk_9preq_readstat(&fake_request, &stat); if (rc == -ENOBUFS) { /* diff --git a/lib/uk9p/9p.c b/lib/uk9p/9p.c index eb4c2dc..638555b 100644 --- a/lib/uk9p/9p.c +++ b/lib/uk9p/9p.c @@ -40,28 +40,49 @@ #include <uk/9preq.h> #include <uk/9pfid.h> +static inline int send_and_wait_zc(struct uk_9pdev *dev, struct uk_9preq *req, + enum uk_9preq_zcdir zc_dir, void *zc_buf, uint32_t zc_size, + uint32_t zc_offset) +{ + int rc; + + if ((rc = uk_9preq_ready(req, zc_dir, zc_buf, zc_size, zc_offset)) || + (rc = uk_9pdev_request(dev, req)) || + (rc = uk_9preq_waitreply(req))) + return rc; + + return 0; +} + +static inline int send_and_wait_no_zc(struct uk_9pdev *dev, + struct uk_9preq *req) +{ + return send_and_wait_zc(dev, req, UK_9PREQ_ZCDIR_NONE, NULL, 0, 0); +} + struct uk_9preq *uk_9p_version(struct uk_9pdev *dev, const char *requested, struct uk_9p_str *received) { struct uk_9p_str requested_str; struct uk_9preq *req; - int rc; + int rc = 0; uint32_t new_msize; uk_9p_str_init(&requested_str, requested); - uk_pr_debug("TVERSION msize %u version %s\n", - dev->msize, requested); - - req = uk_9pdev_call(dev, UK_9P_TVERSION, __PAGE_SIZE, "ds", - dev->msize, &requested_str); + req = uk_9pdev_req_create(dev, UK_9P_TVERSION, __PAGE_SIZE); if (PTRISERR(req)) return req; - rc = uk_9preq_deserialize(req, "ds", &new_msize, received); + uk_pr_debug("TVERSION msize %u version %s\n", + dev->msize, requested); - if (rc) - return ERR2PTR(rc); + if ((rc = uk_9preq_write32(req, dev->msize)) || + (rc = uk_9preq_writestr(req, &requested_str)) || + (rc = send_and_wait_no_zc(dev, req)) || + (rc = uk_9preq_read32(req, &new_msize)) || + (rc = uk_9preq_readstr(req, received))) + goto free; uk_pr_debug("RVERSION msize %u version %.*s\n", new_msize, received->size, received->data); @@ -76,6 +97,10 @@ struct uk_9preq *uk_9p_version(struct uk_9pdev *dev, uk_pr_debug("Invalid new message size.\n"); return req; + +free: + uk_9pdev_req_remove(dev, req); + return ERR2PTR(rc); } struct uk_9pfid *uk_9p_attach(struct uk_9pdev *dev, uint32_t afid, @@ -94,43 +119,56 @@ struct uk_9pfid *uk_9p_attach(struct uk_9pdev *dev, uint32_t afid, if (PTRISERR(fid)) return fid; - uk_pr_debug("TATTACH fid %u afid %u uname %s aname %s n_uname %u\n", - fid->fid, afid, uname, aname, n_uname); - - req = uk_9pdev_call(dev, UK_9P_TATTACH, __PAGE_SIZE, "ddssd", - fid->fid, afid, &uname_str, &aname_str, n_uname); + req = uk_9pdev_req_create(dev, UK_9P_TATTACH, __PAGE_SIZE); if (PTRISERR(req)) { uk_9pdev_fid_release(fid); return (void *)req; } - rc = uk_9preq_deserialize(req, "Q", &fid->qid); + uk_pr_debug("TATTACH fid %u afid %u uname %s aname %s n_uname %u\n", + fid->fid, afid, uname, aname, n_uname); + + rc = 0; + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write32(req, afid)) || + (rc = uk_9preq_writestr(req, &uname_str)) || + (rc = uk_9preq_writestr(req, &aname_str)) || + (rc = uk_9preq_write32(req, n_uname)) || + (rc = send_and_wait_no_zc(dev, req)) || + (rc = uk_9preq_readqid(req, &fid->qid))) + goto free; + uk_9pdev_req_remove(dev, req); uk_pr_debug("RATTACH qid type %u version %u path %lu\n", fid->qid.type, fid->qid.version, fid->qid.path); - if (rc < 0) { - uk_9pdev_fid_release(fid); - return ERR2PTR(rc); - } - return fid; + +free: + uk_9pdev_fid_release(fid); + uk_9pdev_req_remove(dev, req); + return ERR2PTR(rc); } int uk_9p_flush(struct uk_9pdev *dev, uint16_t oldtag) { struct uk_9preq *req; + int rc = 0; - uk_pr_debug("TFLUSH oldtag %u\n", oldtag); - req = uk_9pdev_call(dev, UK_9P_TFLUSH, __PAGE_SIZE, "w", oldtag); + req = uk_9pdev_req_create(dev, UK_9P_TFLUSH, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); + uk_pr_debug("TFLUSH oldtag %u\n", oldtag); + if ((rc = uk_9preq_write16(req, oldtag)) || + (rc = send_and_wait_no_zc(dev, req))) + goto out; uk_pr_debug("RFLUSH\n"); - uk_9pdev_req_remove(dev, req); - return 0; +out: + uk_9pdev_req_remove(dev, req); + return rc; } struct uk_9pfid *uk_9p_walk(struct uk_9pdev *dev, struct uk_9pfid *fid, @@ -141,7 +179,7 @@ struct uk_9pfid *uk_9p_walk(struct uk_9pdev *dev, struct uk_9pfid *fid, struct uk_9p_str name_str; uint16_t nwqid; uint16_t nwname; - int rc; + int rc = 0; uk_9p_str_init(&name_str, name); @@ -151,51 +189,56 @@ struct uk_9pfid *uk_9p_walk(struct uk_9pdev *dev, struct uk_9pfid *fid, nwname = name ? 1 : 0; + req = uk_9pdev_req_create(dev, UK_9P_TWALK, __PAGE_SIZE); + if (PTRISERR(req)) { + rc = PTR2ERR(req); + goto out; + } + if (name) { uk_pr_debug("TWALK fid %u newfid %u nwname %d name %s\n", fid->fid, newfid->fid, nwname, name); - req = uk_9pdev_call(dev, UK_9P_TWALK, __PAGE_SIZE, "ddws", - fid->fid, newfid->fid, nwname, &name_str); + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write32(req, newfid->fid)) || + (rc = uk_9preq_write16(req, nwname)) || + (rc = uk_9preq_writestr(req, &name_str))) + goto out; } else { uk_pr_debug("TWALK fid %u newfid %u nwname %d\n", fid->fid, newfid->fid, nwname); - req = uk_9pdev_call(dev, UK_9P_TWALK, __PAGE_SIZE, "ddw", - fid->fid, newfid->fid, nwname); + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write32(req, newfid->fid)) || + (rc = uk_9preq_write16(req, nwname))) + goto out; } - if (PTRISERR(req)) { + if ((rc = send_and_wait_no_zc(dev, req))) { /* * Don't clunk if request has finished with error, as the fid * is invalid. */ newfid->was_removed = 1; - rc = PTR2ERR(req); goto out; } - rc = uk_9preq_deserialize(req, "w", &nwqid); - if (rc < 0) - goto out_req; + if ((rc = uk_9preq_read16(req, &nwqid))) + goto out; uk_pr_debug("RWALK nwqid %u\n", nwqid); if (nwqid != nwname) { rc = -ENOENT; - goto out_req; + goto out; } - if (nwname) { - rc = uk_9preq_deserialize(req, "Q", &newfid->qid); - if (rc < 0) - goto out_req; + if ((rc = uk_9preq_readqid(req, &newfid->qid))) + goto out; } else newfid->qid = fid->qid; - rc = 0; -out_req: - uk_9pdev_req_remove(dev, req); out: + uk_9pdev_req_remove(dev, req); if (rc) { uk_9pdev_fid_release(newfid); return ERR2PTR(rc); @@ -207,22 +250,27 @@ out: int uk_9p_open(struct uk_9pdev *dev, struct uk_9pfid *fid, uint8_t mode) { struct uk_9preq *req; - int rc; - - uk_pr_debug("TOPEN fid %u mode %u\n", fid->fid, mode); + int rc = 0; - req = uk_9pdev_call(dev, UK_9P_TOPEN, __PAGE_SIZE, "db", - fid->fid, mode); + req = uk_9pdev_req_create(dev, UK_9P_TOPEN, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); - rc = uk_9preq_deserialize(req, "Qd", &fid->qid, &fid->iounit); - uk_9pdev_req_remove(dev, req); + uk_pr_debug("TOPEN fid %u mode %u\n", fid->fid, mode); + + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write8(req, mode)) || + (rc = send_and_wait_no_zc(dev, req)) || + (rc = uk_9preq_readqid(req, &fid->qid)) || + (rc = uk_9preq_read32(req, &fid->iounit))) + goto out; uk_pr_debug("ROPEN qid type %u version %u path %lu iounit %u\n", fid->qid.type, fid->qid.version, fid->qid.path, fid->iounit); +out: + uk_9pdev_req_remove(dev, req); return rc; } @@ -233,63 +281,80 @@ int uk_9p_create(struct uk_9pdev *dev, struct uk_9pfid *fid, struct uk_9preq *req; struct uk_9p_str name_str; struct uk_9p_str extension_str; - int rc; + int rc = 0; uk_9p_str_init(&name_str, name); uk_9p_str_init(&extension_str, extension); - uk_pr_debug("TCREATE fid %u name %s perm %u mode %u ext %s\n", - fid->fid, name, perm, mode, extension); - - req = uk_9pdev_call(dev, UK_9P_TCREATE, __PAGE_SIZE, "dsdbs", - fid->fid, &name_str, perm, mode, &extension_str); + req = uk_9pdev_req_create(dev, UK_9P_TCREATE, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); - rc = uk_9preq_deserialize(req, "Qd", &fid->qid, &fid->iounit); - uk_9pdev_req_remove(dev, req); + uk_pr_debug("TOPEN fid %u mode %u\n", fid->fid, mode); + + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_writestr(req, &name_str)) || + (rc = uk_9preq_write32(req, perm)) || + (rc = uk_9preq_write8(req, mode)) || + (rc = uk_9preq_writestr(req, &extension_str)) || + (rc = send_and_wait_no_zc(dev, req)) || + (rc = uk_9preq_readqid(req, &fid->qid)) || + (rc = uk_9preq_read32(req, &fid->iounit))) + goto out; uk_pr_debug("RCREATE qid type %u version %u path %lu iounit %u\n", fid->qid.type, fid->qid.version, fid->qid.path, fid->iounit); +out: + uk_9pdev_req_remove(dev, req); return rc; } int uk_9p_remove(struct uk_9pdev *dev, struct uk_9pfid *fid) { struct uk_9preq *req; + int rc = 0; /* The fid is considered invalid even if the remove fails. */ fid->was_removed = 1; - uk_pr_debug("TREMOVE fid %u\n", fid->fid); - req = uk_9pdev_call(dev, UK_9P_TREMOVE, __PAGE_SIZE, "d", fid->fid); + req = uk_9pdev_req_create(dev, UK_9P_TREMOVE, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); - uk_9pdev_req_remove(dev, req); + uk_pr_debug("TREMOVE fid %u\n", fid->fid); + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = send_and_wait_no_zc(dev, req))) + goto out; uk_pr_debug("RREMOVE\n"); - return 0; +out: + uk_9pdev_req_remove(dev, req); + return rc; } int uk_9p_clunk(struct uk_9pdev *dev, struct uk_9pfid *fid) { struct uk_9preq *req; + int rc = 0; if (fid->was_removed) return 0; - uk_pr_debug("TCLUNK fid %u\n", fid->fid); - req = uk_9pdev_call(dev, UK_9P_TCLUNK, __PAGE_SIZE, "d", fid->fid); + req = uk_9pdev_req_create(dev, UK_9P_TCLUNK, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); - uk_9pdev_req_remove(dev, req); + uk_pr_debug("TCLUNK fid %u\n", fid->fid); + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = send_and_wait_no_zc(dev, req))) + goto out; uk_pr_debug("RCLUNK\n"); - return 0; +out: + uk_9pdev_req_remove(dev, req); + return rc; } int64_t uk_9p_read(struct uk_9pdev *dev, struct uk_9pfid *fid, @@ -309,24 +374,12 @@ int64_t uk_9p_read(struct uk_9pdev *dev, struct uk_9pfid *fid, if (PTRISERR(req)) return PTR2ERR(req); - rc = uk_9preq_serialize(req, "dqd", fid->fid, offset, count); - if (rc < 0) - goto out; - - rc = uk_9preq_ready(req, UK_9PREQ_ZCDIR_READ, buf, count, 11); - if (rc < 0) - goto out; - - rc = uk_9pdev_request(dev, req); - if (rc < 0) - goto out; - - rc = uk_9preq_waitreply(req); - if (rc < 0) - goto out; - - rc = uk_9preq_deserialize(req, "d", &count); - if (rc < 0) + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write64(req, offset)) || + (rc = uk_9preq_write32(req, count)) || + (rc = send_and_wait_zc(dev, req, UK_9PREQ_ZCDIR_READ, buf, + count, 11)) || + (rc = uk_9preq_read32(req, &count))) goto out; uk_pr_debug("RREAD count %u\n", count); @@ -353,24 +406,12 @@ int64_t uk_9p_write(struct uk_9pdev *dev, struct uk_9pfid *fid, if (PTRISERR(req)) return PTR2ERR(req); - rc = uk_9preq_serialize(req, "dqd", fid->fid, offset, count); - if (rc < 0) - goto out; - - rc = uk_9preq_ready(req, UK_9PREQ_ZCDIR_WRITE, (void *)buf, count, 23); - if (rc < 0) - goto out; - - rc = uk_9pdev_request(dev, req); - if (rc < 0) - goto out; - - rc = uk_9preq_waitreply(req); - if (rc < 0) - goto out; - - rc = uk_9preq_deserialize(req, "d", &count); - if (rc < 0) + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = uk_9preq_write64(req, offset)) || + (rc = uk_9preq_write32(req, count)) || + (rc = send_and_wait_zc(dev, req, UK_9PREQ_ZCDIR_WRITE, + (void *)buf, count, 23)) || + (rc = uk_9preq_read32(req, &count))) goto out; uk_pr_debug("RWRITE count %u\n", count); @@ -386,45 +427,58 @@ struct uk_9preq *uk_9p_stat(struct uk_9pdev *dev, struct uk_9pfid *fid, struct uk_9p_stat *stat) { struct uk_9preq *req; - int rc; + int rc = 0; uint16_t dummy; - uk_pr_debug("TSTAT fid %u\n", fid->fid); - req = uk_9pdev_call(dev, UK_9P_TSTAT, __PAGE_SIZE, "d", fid->fid); + req = uk_9pdev_req_create(dev, UK_9P_TSTAT, __PAGE_SIZE); if (PTRISERR(req)) return req; - rc = uk_9preq_deserialize(req, "wS", &dummy, stat); - if (rc) - return ERR2PTR(rc); + uk_pr_debug("TSTAT fid %u\n", fid->fid); + + if ((rc = uk_9preq_write32(req, fid->fid)) || + (rc = send_and_wait_no_zc(dev, req)) || + (rc = uk_9preq_read16(req, &dummy)) || + (rc = uk_9preq_readstat(req, stat))) + goto out; + uk_pr_debug("RSTAT\n"); return req; + +out: + uk_9pdev_req_remove(dev, req); + return ERR2PTR(rc); } int uk_9p_wstat(struct uk_9pdev *dev, struct uk_9pfid *fid, struct uk_9p_stat *stat) { struct uk_9preq *req; + int rc = 0; + uint16_t *dummy; - /* - * The packed size of stat is 61 bytes + the size occupied by the - * strings. - */ - stat->size = 61; - stat->size += stat->name.size; - stat->size += stat->uid.size; - stat->size += stat->gid.size; - stat->size += stat->muid.size; - stat->size += stat->extension.size; - - uk_pr_debug("TWSTAT fid %u\n", fid->fid); - req = uk_9pdev_call(dev, UK_9P_TWSTAT, __PAGE_SIZE, "dwS", fid->fid, - stat->size + 2, stat); + req = uk_9pdev_req_create(dev, UK_9P_TWSTAT, __PAGE_SIZE); if (PTRISERR(req)) return PTR2ERR(req); - uk_9pdev_req_remove(dev, req); - uk_pr_debug("RWSTAT"); - return 0; + uk_pr_debug("TWSTAT fid %u\n", fid->fid); + + if ((rc = uk_9preq_write32(req, fid->fid))) + goto out; + + dummy = (uint16_t *)(req->xmit.buf + req->xmit.offset); + if ((rc = uk_9preq_write16(req, 0)) || + (rc = uk_9preq_writestat(req, stat))) + goto out; + *dummy = stat->size + 2; + + if ((rc = send_and_wait_no_zc(dev, req))) + goto out; + + uk_pr_debug("RWSTAT\n"); + +out: + uk_9pdev_req_remove(dev, req); + return rc; } diff --git a/lib/uk9p/9preq.c b/lib/uk9p/9preq.c index 0fc4b1e..8d787e7 100644 --- a/lib/uk9p/9preq.c +++ b/lib/uk9p/9preq.c @@ -434,10 +434,8 @@ int uk_9preq_ready(struct uk_9preq *req, enum uk_9preq_zcdir zc_dir, UK_ASSERT(req); - if (UK_READ_ONCE(req->state) != UK_9PREQ_INITIALIZED) { - rc = -EIO; - goto out; - } + if (UK_READ_ONCE(req->state) != UK_9PREQ_INITIALIZED) + return -EIO; /* Save current offset as the size of the message. */ total_size = req->xmit.offset; @@ -448,10 +446,10 @@ int uk_9preq_ready(struct uk_9preq *req, enum uk_9preq_zcdir zc_dir, /* Serialize the header. */ req->xmit.offset = 0; - rc = uk_9preq_serialize(req, "dbw", total_size_with_zc, req->xmit.type, - req->tag); - if (rc < 0) - goto out; + if ((rc = uk_9preq_write32(req, total_size_with_zc)) < 0 || + (rc = uk_9preq_write8(req, req->xmit.type)) < 0 || + (rc = uk_9preq_write16(req, req->tag)) < 0) + return rc; /* Reset offset and size to sane values. */ req->xmit.offset = 0; @@ -474,8 +472,7 @@ int uk_9preq_ready(struct uk_9preq *req, enum uk_9preq_zcdir zc_dir, /* Update the state. */ UK_WRITE_ONCE(req->state, UK_9PREQ_READY); -out: - return rc; + return 0; } int uk_9preq_receive_cb(struct uk_9preq *req, uint32_t recv_size) @@ -495,8 +492,10 @@ int uk_9preq_receive_cb(struct uk_9preq *req, uint32_t recv_size) /* Deserialize the header into request fields. */ req->recv.offset = 0; req->recv.size = recv_size; - rc = _fcall_deserialize(&req->recv, "dbw", &size, - &req->recv.type, &tag); + if ((rc = uk_9preq_read32(req, &size)) < 0 || + (rc = uk_9preq_read8(req, &req->recv.type)) < 0 || + (rc = uk_9preq_read16(req, &tag)) < 0) + return rc; /* Check sanity of deserialized values. */ if (rc < 0) @@ -557,8 +556,8 @@ int uk_9preq_error(struct uk_9preq *req) */ UK_BUGON(req->recv.offset != UK_9P_HEADER_SIZE); - rc = uk_9preq_deserialize(req, "sd", &error, &errcode); - if (rc < 0) + if ((rc = uk_9preq_readstr(req, &error)) < 0 || + (rc = uk_9preq_read32(req, &errcode)) < 0) return rc; uk_pr_debug("RERROR %.*s %d\n", error.size, error.data, errcode); -- 2.26.2
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |