dcavalca / rpms / qemu

Forked from rpms/qemu a year ago
Clone

Blame 0052-virtiofsd-add-fuse_mbuf_iter-API.patch

1d442b
From: Stefan Hajnoczi <stefanha@redhat.com>
1d442b
Date: Mon, 27 Jan 2020 19:01:21 +0000
1d442b
Subject: [PATCH] virtiofsd: add fuse_mbuf_iter API
1d442b
1d442b
Introduce an API for consuming bytes from a buffer with size checks.
1d442b
All FUSE operations will be converted to use this safe API instead of
1d442b
void *inarg.
1d442b
1d442b
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
1d442b
Signed-off-by: Dr. David Alan Gilbert <dgilbert@redhat.com>
1d442b
(cherry picked from commit dad157e880416ab3a0e45beaa0e81977516568bc)
1d442b
---
1d442b
 tools/virtiofsd/buffer.c      | 28 ++++++++++++++++++++
1d442b
 tools/virtiofsd/fuse_common.h | 49 ++++++++++++++++++++++++++++++++++-
1d442b
 2 files changed, 76 insertions(+), 1 deletion(-)
1d442b
1d442b
diff --git a/tools/virtiofsd/buffer.c b/tools/virtiofsd/buffer.c
1d442b
index 772efa922d..42a608f6bd 100644
1d442b
--- a/tools/virtiofsd/buffer.c
1d442b
+++ b/tools/virtiofsd/buffer.c
1d442b
@@ -267,3 +267,31 @@ ssize_t fuse_buf_copy(struct fuse_bufvec *dstv, struct fuse_bufvec *srcv)
1d442b
 
1d442b
     return copied;
1d442b
 }
1d442b
+
1d442b
+void *fuse_mbuf_iter_advance(struct fuse_mbuf_iter *iter, size_t len)
1d442b
+{
1d442b
+    void *ptr;
1d442b
+
1d442b
+    if (len > iter->size - iter->pos) {
1d442b
+        return NULL;
1d442b
+    }
1d442b
+
1d442b
+    ptr = iter->mem + iter->pos;
1d442b
+    iter->pos += len;
1d442b
+    return ptr;
1d442b
+}
1d442b
+
1d442b
+const char *fuse_mbuf_iter_advance_str(struct fuse_mbuf_iter *iter)
1d442b
+{
1d442b
+    const char *str = iter->mem + iter->pos;
1d442b
+    size_t remaining = iter->size - iter->pos;
1d442b
+    size_t i;
1d442b
+
1d442b
+    for (i = 0; i < remaining; i++) {
1d442b
+        if (str[i] == '\0') {
1d442b
+            iter->pos += i + 1;
1d442b
+            return str;
1d442b
+        }
1d442b
+    }
1d442b
+    return NULL;
1d442b
+}
1d442b
diff --git a/tools/virtiofsd/fuse_common.h b/tools/virtiofsd/fuse_common.h
1d442b
index 0cb33acc2f..f8f6433743 100644
1d442b
--- a/tools/virtiofsd/fuse_common.h
1d442b
+++ b/tools/virtiofsd/fuse_common.h
1d442b
@@ -703,10 +703,57 @@ size_t fuse_buf_size(const struct fuse_bufvec *bufv);
1d442b
  */
1d442b
 ssize_t fuse_buf_copy(struct fuse_bufvec *dst, struct fuse_bufvec *src);
1d442b
 
1d442b
+/**
1d442b
+ * Memory buffer iterator
1d442b
+ *
1d442b
+ */
1d442b
+struct fuse_mbuf_iter {
1d442b
+    /**
1d442b
+     * Data pointer
1d442b
+     */
1d442b
+    void *mem;
1d442b
+
1d442b
+    /**
1d442b
+     * Total length, in bytes
1d442b
+     */
1d442b
+    size_t size;
1d442b
+
1d442b
+    /**
1d442b
+     * Offset from start of buffer
1d442b
+     */
1d442b
+    size_t pos;
1d442b
+};
1d442b
+
1d442b
+/* Initialize memory buffer iterator from a fuse_buf */
1d442b
+#define FUSE_MBUF_ITER_INIT(fbuf) \
1d442b
+    ((struct fuse_mbuf_iter){     \
1d442b
+        .mem = fbuf->mem,         \
1d442b
+        .size = fbuf->size,       \
1d442b
+        .pos = 0,                 \
1d442b
+    })
1d442b
+
1d442b
+/**
1d442b
+ * Consume bytes from a memory buffer iterator
1d442b
+ *
1d442b
+ * @param iter memory buffer iterator
1d442b
+ * @param len number of bytes to consume
1d442b
+ * @return pointer to start of consumed bytes or
1d442b
+ *         NULL if advancing beyond end of buffer
1d442b
+ */
1d442b
+void *fuse_mbuf_iter_advance(struct fuse_mbuf_iter *iter, size_t len);
1d442b
+
1d442b
+/**
1d442b
+ * Consume a NUL-terminated string from a memory buffer iterator
1d442b
+ *
1d442b
+ * @param iter memory buffer iterator
1d442b
+ * @return pointer to the string or
1d442b
+ *         NULL if advancing beyond end of buffer or there is no NUL-terminator
1d442b
+ */
1d442b
+const char *fuse_mbuf_iter_advance_str(struct fuse_mbuf_iter *iter);
1d442b
+
1d442b
 /*
1d442b
  * Signal handling
1d442b
  */
1d442b
-
1d442b
 /**
1d442b
  * Exit session on HUP, TERM and INT signals and ignore PIPE signal
1d442b
  *