diff --git a/dpfs_fuse/dpfs_fuse.cpp b/dpfs_fuse/dpfs_fuse.cpp index 61b8f186..d2061cc2 100644 --- a/dpfs_fuse/dpfs_fuse.cpp +++ b/dpfs_fuse/dpfs_fuse.cpp @@ -36,6 +36,7 @@ #include "dpfs_hal.h" #include "dpfs_fuse.h" #include "rpc.h" +using namespace erpc; struct fuse_ll; typedef int (*fuse_handler_t) (struct fuse_ll *, @@ -1782,6 +1783,11 @@ static int fuse_handle_req(void *u, } } + +void erpc_handler(ReqHandle *req_handle, void *context) { + +} + int dpfs_fuse_main(struct fuse_ll_operations *ops, struct virtiofs_emu_params *emu_params, void *user_data, bool debug) { @@ -1822,6 +1828,7 @@ int dpfs_fuse_main(struct fuse_ll_operations *ops, struct virtiofs_emu_params *e dpfs_hal_loop(emu); dpfs_hal_destroy(emu); #elif defined(DPFS_FUSE_ERPC) + // init eRPC // allocate some eRPC buffers // plug eRPC into dpfs_fuse diff --git a/dpfs_rpc_dpu/.gitignore b/dpfs_rpc_dpu/.gitignore new file mode 100644 index 00000000..94fdddbd --- /dev/null +++ b/dpfs_rpc_dpu/.gitignore @@ -0,0 +1 @@ +dpfs_rpc_dpu diff --git a/dpfs_rpc_dpu/README.md b/dpfs_rpc_dpu/README.md new file mode 100644 index 00000000..c8b93f73 --- /dev/null +++ b/dpfs_rpc_dpu/README.md @@ -0,0 +1,41 @@ +# dpfs_rpc_dpu +This binary consumes the dpfs_hal virtio-fs abstraction layer and sends requests directly over the wire to a remote server +using eRPC with the RVFS binary format. + +# RVFS binary format +This format will describe the Remote Virtual File System protocol, i.e. virtio-fs directly over the wire via RPC. + +The format is subject to change and work in progress. This protocol is not directly exposed to a consumer/cloud tenant, +the consumer/cloud tenant consumes virtio-fs. Therefore we do not build in any backwards compatibility into the wire format. + +### Format +| Bytes | Data type | Name | Description | +| --- | --- | --- | -- | +| 0..4 | int32 | num_descs | The amount of descriptors in this message | +| 5..12 | uint64 | desc_len | The number of bytes in the descriptor following this uint64 | +| 13.. | raw data | desc_data | Descriptor data bytes | + +Where multiple descriptors will follow each other in a single message. +## Example read request (Bytes are off!) +See linux/fuse.h for the FUSE struct definitions + +| Bytes | Data type | Name | Contents | +| --- | --- | --- | -- | +| 0..4 | int32 | num_descs | 3 | +| 5..12 | uint64 | desc_len | `sizeof(fuse_in_header)` | +| 13..44 | raw data | desc_data | FUSE input header `fuse_in_header` | +| 45..52 | uint64 | desc_len | `sizeof(fuse_read_in)` | +| 53..84 | raw data | desc_data | FUSE read input header (`fuse_read_in`) | + +## Example read reply (Bytes are off!) +See linux/fuse.h for the FUSE struct definitions + +| Bytes | Data type | Name | Contents | +| --- | --- | --- | -- | +| 0..4 | int32 | num_descs | 3 | +| 5..12 | uint64 | desc_len | `sizeof(fuse_out_header)` | +| 13..44 | raw data | desc_data | FUSE out header `fuse_out_header` | +| 45..52 | uint64 | desc_len | Number of bytes read (here 32) | +| 53..84 | raw data | desc_data | Data | + + diff --git a/dpfs_rpc_dpu/dpfs_rpc_dpu b/dpfs_rpc_dpu/dpfs_rpc_dpu index d91944be..a93fbd37 100755 Binary files a/dpfs_rpc_dpu/dpfs_rpc_dpu and b/dpfs_rpc_dpu/dpfs_rpc_dpu differ diff --git a/dpfs_rpc_dpu/main.cpp b/dpfs_rpc_dpu/main.cpp index 330d5690..78abfb04 100644 --- a/dpfs_rpc_dpu/main.cpp +++ b/dpfs_rpc_dpu/main.cpp @@ -48,16 +48,25 @@ struct rpc_state { void response_func(void *context, void *tag) { rpc_state *state = (rpc_state *) context; rpc_msg *msg = (rpc_msg *) tag; - // Copy the resp to the output buffers - size_t msg_len = 0; - for (size_t i = 0; i < msg->out_iovcnt; i++) { - memcpy(msg->out_iov[i].iov_base, ((char *) msg->resp.buf_) + msg_len, msg->out_iov[i].iov_len); - msg_len += msg->out_iov[i].iov_len; + uint8_t *req_buf = msg->req.buf_; + + int out_iovcnt = *((int *) msg->req.buf_); + req_buf += sizeof(out_iovcnt); + + for (size_t i = 0; i < out_iovcnt; i++) { + size_t iov_len = *((size_t *) req_buf); + req_buf += sizeof(iov_len); + + memcpy(msg->out_iov[i].iov_base, (void *) req_buf, iov_len); + req_buf += iov_len; } + + dpfs_hal_async_complete(msg->completion_context, DPFS_HAL_COMPLETION_SUCCES); + state->avail.push_back(msg); } -// The remote doesn't send us messages +// The session management callback that is invoked when sessions are successfully created or destroyed. void sm_handler(int, SmEventType, SmErrType, void *) {} static int fuse_handler(void *user_data, @@ -68,12 +77,20 @@ static int fuse_handler(void *user_data, rpc_state *state = (rpc_state *) user_data; // Send it via eRPC to the remote side rpc_msg *msg = state->avail.back(); + uint8_t *req_buf = msg->req.buf_; state->avail.pop_back(); - size_t msg_len = 0; + *((int *) req_buf) = in_iovcnt; + req_buf += sizeof(in_iovcnt); + for (size_t i = 0; i < in_iovcnt; i++) { - memcpy(msg->req.buf_, ((char *) in_iov[i].iov_base) + msg_len, in_iov[i].iov_len); - msg_len += in_iov[i].iov_len; + // Set the iov_len into the request buffer + *(size_t *) req_buf = in_iov[i].iov_len; + req_buf += sizeof(in_iov[i].iov_len); + + // Fill the request buffer with iov_base data + memcpy(req_buf, in_iov[i].iov_base, in_iov[i].iov_len); + req_buf += in_iov[i].iov_len; } state->rpc->enqueue_request(state->session_num, 0, &msg->req, &msg->resp, response_func, (void *) state);