All of lore.kernel.org
 help / color / mirror / Atom feed
From: Juergen Gross <jgross@suse.com>
To: xen-devel@lists.xenproject.org
Cc: Juergen Gross <jgross@suse.com>,
	Stefano Stabellini <sstabellini@kernel.org>,
	Julien Grall <julien@xen.org>, Wei Liu <wl@xen.org>,
	Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>,
	George Dunlap <George.Dunlap@eu.citrix.com>,
	Andrew Cooper <andrew.cooper3@citrix.com>,
	Ian Jackson <ian.jackson@eu.citrix.com>,
	Jan Beulich <jbeulich@suse.com>
Subject: [Xen-devel] [PATCH v5 4/8] libs: add libxenhypfs
Date: Wed, 19 Feb 2020 09:11:22 +0100	[thread overview]
Message-ID: <20200219081126.29534-5-jgross@suse.com> (raw)
In-Reply-To: <20200219081126.29534-1-jgross@suse.com>

Add the new library libxenhypfs for access to the hypervisor filesystem.

Signed-off-by: Juergen Gross <jgross@suse.com>
Acked-by: Wei Liu <wl@xen.org>
---
V1:
- rename to libxenhypfs
- add xenhypfs_write()

V3:
- major rework due to new hypervisor interface
- add decompression capability

V4:
- add dependency to libz in pkgconfig file (Wei Liu)
---
 .gitignore                          |   2 +
 tools/Rules.mk                      |   6 +
 tools/libs/Makefile                 |   1 +
 tools/libs/hypfs/Makefile           |  16 ++
 tools/libs/hypfs/core.c             | 533 ++++++++++++++++++++++++++++++++++++
 tools/libs/hypfs/include/xenhypfs.h |  75 +++++
 tools/libs/hypfs/libxenhypfs.map    |  10 +
 tools/libs/hypfs/xenhypfs.pc.in     |  10 +
 8 files changed, 653 insertions(+)
 create mode 100644 tools/libs/hypfs/Makefile
 create mode 100644 tools/libs/hypfs/core.c
 create mode 100644 tools/libs/hypfs/include/xenhypfs.h
 create mode 100644 tools/libs/hypfs/libxenhypfs.map
 create mode 100644 tools/libs/hypfs/xenhypfs.pc.in

diff --git a/.gitignore b/.gitignore
index b2624df79a..e98c3f056d 100644
--- a/.gitignore
+++ b/.gitignore
@@ -109,6 +109,8 @@ tools/libs/evtchn/headers.chk
 tools/libs/evtchn/xenevtchn.pc
 tools/libs/gnttab/headers.chk
 tools/libs/gnttab/xengnttab.pc
+tools/libs/hypfs/headers.chk
+tools/libs/hypfs/xenhypfs.pc
 tools/libs/call/headers.chk
 tools/libs/call/xencall.pc
 tools/libs/foreignmemory/headers.chk
diff --git a/tools/Rules.mk b/tools/Rules.mk
index 52f47be3f8..a04697a33c 100644
--- a/tools/Rules.mk
+++ b/tools/Rules.mk
@@ -19,6 +19,7 @@ XEN_LIBXENGNTTAB   = $(XEN_ROOT)/tools/libs/gnttab
 XEN_LIBXENCALL     = $(XEN_ROOT)/tools/libs/call
 XEN_LIBXENFOREIGNMEMORY = $(XEN_ROOT)/tools/libs/foreignmemory
 XEN_LIBXENDEVICEMODEL = $(XEN_ROOT)/tools/libs/devicemodel
+XEN_LIBXENHYPFS    = $(XEN_ROOT)/tools/libs/hypfs
 XEN_LIBXC          = $(XEN_ROOT)/tools/libxc
 XEN_XENLIGHT       = $(XEN_ROOT)/tools/libxl
 # Currently libxlutil lives in the same directory as libxenlight
@@ -134,6 +135,11 @@ SHDEPS_libxendevicemodel = $(SHLIB_libxentoollog) $(SHLIB_libxentoolcore) $(SHLI
 LDLIBS_libxendevicemodel = $(SHDEPS_libxendevicemodel) $(XEN_LIBXENDEVICEMODEL)/libxendevicemodel$(libextension)
 SHLIB_libxendevicemodel  = $(SHDEPS_libxendevicemodel) -Wl,-rpath-link=$(XEN_LIBXENDEVICEMODEL)
 
+CFLAGS_libxenhypfs = -I$(XEN_LIBXENHYPFS)/include $(CFLAGS_xeninclude)
+SHDEPS_libxenhypfs = $(SHLIB_libxentoollog) $(SHLIB_libxentoolcore) $(SHLIB_xencall)
+LDLIBS_libxenhypfs = $(SHDEPS_libxenhypfs) $(XEN_LIBXENHYPFS)/libxenhypfs$(libextension)
+SHLIB_libxenhypfs  = $(SHDEPS_libxenhypfs) -Wl,-rpath-link=$(XEN_LIBXENHYPFS)
+
 # code which compiles against libxenctrl get __XEN_TOOLS__ and
 # therefore sees the unstable hypercall interfaces.
 CFLAGS_libxenctrl = -I$(XEN_LIBXC)/include $(CFLAGS_libxentoollog) $(CFLAGS_libxenforeignmemory) $(CFLAGS_libxendevicemodel) $(CFLAGS_xeninclude) -D__XEN_TOOLS__
diff --git a/tools/libs/Makefile b/tools/libs/Makefile
index 88901e7341..69cdfb5975 100644
--- a/tools/libs/Makefile
+++ b/tools/libs/Makefile
@@ -9,6 +9,7 @@ SUBDIRS-y += gnttab
 SUBDIRS-y += call
 SUBDIRS-y += foreignmemory
 SUBDIRS-y += devicemodel
+SUBDIRS-y += hypfs
 
 ifeq ($(CONFIG_RUMP),y)
 SUBDIRS-y := toolcore
diff --git a/tools/libs/hypfs/Makefile b/tools/libs/hypfs/Makefile
new file mode 100644
index 0000000000..06dd449929
--- /dev/null
+++ b/tools/libs/hypfs/Makefile
@@ -0,0 +1,16 @@
+XEN_ROOT = $(CURDIR)/../../..
+include $(XEN_ROOT)/tools/Rules.mk
+
+MAJOR    = 1
+MINOR    = 0
+LIBNAME  := hypfs
+USELIBS  := toollog toolcore call
+
+APPEND_LDFLAGS += -lz
+
+SRCS-y                 += core.c
+
+include ../libs.mk
+
+$(PKG_CONFIG_LOCAL): PKG_CONFIG_INCDIR = $(XEN_LIBXENHYPFS)/include
+$(PKG_CONFIG_LOCAL): PKG_CONFIG_CFLAGS_LOCAL = $(CFLAGS_xeninclude)
diff --git a/tools/libs/hypfs/core.c b/tools/libs/hypfs/core.c
new file mode 100644
index 0000000000..ced616c879
--- /dev/null
+++ b/tools/libs/hypfs/core.c
@@ -0,0 +1,533 @@
+/*
+ * Copyright (c) 2019 SUSE Software Solutions Germany GmbH
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#define __XEN_TOOLS__ 1
+
+#define _GNU_SOURCE
+
+#include <errno.h>
+#include <inttypes.h>
+#include <stdlib.h>
+#include <string.h>
+#include <zlib.h>
+
+#include <xentoollog.h>
+#include <xenhypfs.h>
+#include <xencall.h>
+#include <xentoolcore_internal.h>
+
+#include <xen/xen.h>
+#include <xen/hypfs.h>
+
+#define BUF_SIZE 4096
+
+struct xenhypfs_handle {
+    xentoollog_logger *logger, *logger_tofree;
+    unsigned int flags;
+    xencall_handle *xcall;
+};
+
+xenhypfs_handle *xenhypfs_open(xentoollog_logger *logger,
+                               unsigned open_flags)
+{
+    xenhypfs_handle *fshdl = calloc(1, sizeof(*fshdl));
+
+    if (!fshdl)
+        return NULL;
+
+    fshdl->flags = open_flags;
+    fshdl->logger = logger;
+    fshdl->logger_tofree = NULL;
+
+    if (!fshdl->logger) {
+        fshdl->logger = fshdl->logger_tofree =
+            (xentoollog_logger*)
+            xtl_createlogger_stdiostream(stderr, XTL_PROGRESS, 0);
+        if (!fshdl->logger)
+            goto err;
+    }
+
+    fshdl->xcall = xencall_open(fshdl->logger, 0);
+    if (!fshdl->xcall)
+        goto err;
+
+    /* No need to remember supported version, we only support V1. */
+    if (xencall1(fshdl->xcall, __HYPERVISOR_hypfs_op,
+                 XEN_HYPFS_OP_get_version) < 0)
+        goto err;
+
+    return fshdl;
+
+err:
+    xtl_logger_destroy(fshdl->logger_tofree);
+    xencall_close(fshdl->xcall);
+    free(fshdl);
+    return NULL;
+}
+
+int xenhypfs_close(xenhypfs_handle *fshdl)
+{
+    if (!fshdl)
+        return 0;
+
+    xencall_close(fshdl->xcall);
+    xtl_logger_destroy(fshdl->logger_tofree);
+    free(fshdl);
+    return 0;
+}
+
+static int xenhypfs_get_pathbuf(xenhypfs_handle *fshdl, const char *path,
+                                char **path_buf)
+{
+    int ret = -1;
+    int path_sz;
+
+    if (!fshdl) {
+        errno = EBADF;
+        goto out;
+    }
+
+    path_sz = strlen(path) + 1;
+    if (path_sz > XEN_HYPFS_MAX_PATHLEN)
+    {
+        errno = ENAMETOOLONG;
+        goto out;
+    }
+
+    *path_buf = xencall_alloc_buffer(fshdl->xcall, path_sz);
+    if (!*path_buf) {
+        errno = ENOMEM;
+        goto out;
+    }
+    strcpy(*path_buf, path);
+
+    ret = path_sz;
+
+ out:
+    return ret;
+}
+
+static void *xenhypfs_inflate(void *in_data, size_t *sz)
+{
+    unsigned char *workbuf;
+    void *content = NULL;
+    unsigned int out_sz;
+    z_stream z = { .opaque = NULL };
+    int ret;
+
+    workbuf = malloc(BUF_SIZE);
+    if (!workbuf)
+        return NULL;
+
+    z.next_in = in_data;
+    z.avail_in = *sz;
+    ret = inflateInit2(&z, MAX_WBITS + 32); /* 32 == gzip */
+
+    for (*sz = 0; ret == Z_OK; *sz += out_sz) {
+        z.next_out = workbuf;
+        z.avail_out = BUF_SIZE;
+        ret = inflate(&z, Z_SYNC_FLUSH);
+        if (ret != Z_OK && ret != Z_STREAM_END)
+            break;
+
+        out_sz = z.next_out - workbuf;
+        content = realloc(content, *sz + out_sz);
+        if (!content) {
+            ret = Z_MEM_ERROR;
+            break;
+        }
+        memcpy(content + *sz, workbuf, out_sz);
+    }
+
+    inflateEnd(&z);
+    if (ret != Z_STREAM_END) {
+        free(content);
+        content = NULL;
+        errno = EIO;
+    }
+    free(workbuf);
+    return content;
+}
+
+static void xenhypfs_set_attrs(struct xen_hypfs_direntry *entry,
+                               struct xenhypfs_dirent *dirent)
+{
+    dirent->size = entry->content_len;
+
+    switch(entry->type) {
+    case XEN_HYPFS_TYPE_DIR:
+        dirent->type = xenhypfs_type_dir;
+        break;
+    case XEN_HYPFS_TYPE_BLOB:
+        dirent->type = xenhypfs_type_blob;
+        break;
+    case XEN_HYPFS_TYPE_STRING:
+        dirent->type = xenhypfs_type_string;
+        break;
+    case XEN_HYPFS_TYPE_UINT:
+        dirent->type = xenhypfs_type_uint;
+        break;
+    case XEN_HYPFS_TYPE_INT:
+        dirent->type = xenhypfs_type_int;
+        break;
+    case XEN_HYPFS_TYPE_BOOL:
+        dirent->type = xenhypfs_type_bool;
+        break;
+    default:
+        dirent->type = xenhypfs_type_blob;
+    }
+
+    switch (entry->encoding) {
+    case XEN_HYPFS_ENC_PLAIN:
+        dirent->encoding = xenhypfs_enc_plain;
+        break;
+    case XEN_HYPFS_ENC_GZIP:
+        dirent->encoding = xenhypfs_enc_gzip;
+        break;
+    default:
+        dirent->encoding = xenhypfs_enc_plain;
+        dirent->type = xenhypfs_type_blob;
+    }
+
+    dirent->is_writable = entry->flags & XEN_HYPFS_WRITEABLE;
+}
+
+void *xenhypfs_read_raw(xenhypfs_handle *fshdl, const char *path,
+                        struct xenhypfs_dirent **dirent)
+{
+    void *retbuf = NULL, *content = NULL;
+    char *path_buf = NULL;
+    const char *name;
+    struct xen_hypfs_direntry *entry;
+    int ret;
+    int sz, path_sz;
+
+    *dirent = NULL;
+    ret = xenhypfs_get_pathbuf(fshdl, path, &path_buf);
+    if (ret < 0)
+        goto out;
+
+    path_sz = ret;
+
+    for (sz = BUF_SIZE;; sz = sizeof(*entry) + entry->content_len) {
+        if (retbuf)
+            xencall_free_buffer(fshdl->xcall, retbuf);
+
+        retbuf = xencall_alloc_buffer(fshdl->xcall, sz);
+        if (!retbuf) {
+            errno = ENOMEM;
+            goto out;
+        }
+        entry = retbuf;
+
+        ret = xencall5(fshdl->xcall, __HYPERVISOR_hypfs_op, XEN_HYPFS_OP_read,
+                       (unsigned long)path_buf, path_sz,
+                       (unsigned long)retbuf, sz);
+        if (!ret)
+            break;
+
+        if (ret != ENOBUFS) {
+            errno = -ret;
+            goto out;
+        }
+    }
+
+    content = malloc(entry->content_len);
+    if (!content)
+        goto out;
+    memcpy(content, entry + 1, entry->content_len);
+
+    name = strrchr(path, '/');
+    if (!name)
+        name = path;
+    else {
+        name++;
+        if (!*name)
+            name--;
+    }
+    *dirent = calloc(1, sizeof(struct xenhypfs_dirent) + strlen(name) + 1);
+    if (!*dirent) {
+        free(content);
+        content = NULL;
+        errno = ENOMEM;
+        goto out;
+    }
+    (*dirent)->name = (char *)(*dirent + 1);
+    strcpy((*dirent)->name, name);
+    xenhypfs_set_attrs(entry, *dirent);
+
+ out:
+    ret = errno;
+    xencall_free_buffer(fshdl->xcall, path_buf);
+    xencall_free_buffer(fshdl->xcall, retbuf);
+    errno = ret;
+
+    return content;
+}
+
+char *xenhypfs_read(xenhypfs_handle *fshdl, const char *path)
+{
+    char *buf, *ret_buf = NULL;
+    struct xenhypfs_dirent *dirent;
+    int ret;
+
+    buf = xenhypfs_read_raw(fshdl, path, &dirent);
+    if (!buf)
+        goto out;
+
+    switch (dirent->encoding) {
+    case xenhypfs_enc_plain:
+        break;
+    case xenhypfs_enc_gzip:
+        ret_buf = xenhypfs_inflate(buf, &dirent->size);
+        if (!ret_buf)
+            goto out;
+        free(buf);
+        buf = ret_buf;
+        ret_buf = NULL;
+        break;
+    }
+
+    switch (dirent->type) {
+    case xenhypfs_type_dir:
+        errno = EISDIR;
+        break;
+    case xenhypfs_type_blob:
+        errno = EDOM;
+        break;
+    case xenhypfs_type_string:
+        ret_buf = buf;
+        buf = NULL;
+        break;
+    case xenhypfs_type_uint:
+    case xenhypfs_type_bool:
+        switch (dirent->size) {
+        case 1:
+            ret = asprintf(&ret_buf, "%"PRIu8, *(uint8_t *)buf);
+            break;
+        case 2:
+            ret = asprintf(&ret_buf, "%"PRIu16, *(uint16_t *)buf);
+            break;
+        case 4:
+            ret = asprintf(&ret_buf, "%"PRIu32, *(uint32_t *)buf);
+            break;
+        case 8:
+            ret = asprintf(&ret_buf, "%"PRIu64, *(uint64_t *)buf);
+            break;
+        default:
+            ret = -1;
+            errno = EDOM;
+        }
+        if (ret < 0)
+            ret_buf = NULL;
+        break;
+    case xenhypfs_type_int:
+        switch (dirent->size) {
+        case 1:
+            ret = asprintf(&ret_buf, "%"PRId8, *(int8_t *)buf);
+            break;
+        case 2:
+            ret = asprintf(&ret_buf, "%"PRId16, *(int16_t *)buf);
+            break;
+        case 4:
+            ret = asprintf(&ret_buf, "%"PRId32, *(int32_t *)buf);
+            break;
+        case 8:
+            ret = asprintf(&ret_buf, "%"PRId64, *(int64_t *)buf);
+            break;
+        default:
+            ret = -1;
+            errno = EDOM;
+        }
+        if (ret < 0)
+            ret_buf = NULL;
+        break;
+    }
+
+ out:
+    ret = errno;
+    free(buf);
+    free(dirent);
+    errno = ret;
+
+    return ret_buf;
+}
+
+struct xenhypfs_dirent *xenhypfs_readdir(xenhypfs_handle *fshdl,
+                                         const char *path,
+                                         unsigned int *num_entries)
+{
+    void *buf, *curr;
+    int ret;
+    char *names;
+    struct xenhypfs_dirent *ret_buf = NULL, *dirent;
+    unsigned int n = 0, name_sz = 0;
+    struct xen_hypfs_dirlistentry *entry;
+
+    buf = xenhypfs_read_raw(fshdl, path, &dirent);
+    if (!buf)
+        goto out;
+
+    if (dirent->type != xenhypfs_type_dir ||
+        dirent->encoding != xenhypfs_enc_plain) {
+        errno = ENOTDIR;
+        goto out;
+    }
+
+    if (dirent->size) {
+        curr = buf;
+        for (n = 1;; n++) {
+            entry = curr;
+            name_sz += strlen(entry->name) + 1;
+            if (!entry->off_next)
+                break;
+
+            curr += entry->off_next;
+        }
+    }
+
+    ret_buf = malloc(n * sizeof(*ret_buf) + name_sz);
+    if (!ret_buf)
+        goto out;
+
+    *num_entries = n;
+    names = (char *)(ret_buf + n);
+    curr = buf;
+    for (n = 0; n < *num_entries; n++) {
+        entry = curr;
+        xenhypfs_set_attrs(&entry->e, ret_buf + n);
+        ret_buf[n].name = names;
+        strcpy(names, entry->name);
+        names += strlen(entry->name) + 1;
+        curr += entry->off_next;
+    }
+
+ out:
+    ret = errno;
+    free(buf);
+    free(dirent);
+    errno = ret;
+
+    return ret_buf;
+}
+
+int xenhypfs_write(xenhypfs_handle *fshdl, const char *path, const char *val)
+{
+    void *buf = NULL;
+    char *path_buf = NULL, *val_end;
+    int ret, saved_errno;
+    int sz, path_sz;
+    struct xen_hypfs_direntry *entry;
+    uint64_t mask;
+
+    ret = xenhypfs_get_pathbuf(fshdl, path, &path_buf);
+    if (ret < 0)
+        goto out;
+
+    path_sz = ret;
+    ret = -1;
+
+    sz = BUF_SIZE;
+    buf = xencall_alloc_buffer(fshdl->xcall, sz);
+    if (!buf) {
+        errno = ENOMEM;
+        goto out;
+    }
+
+    ret = xencall5(fshdl->xcall, __HYPERVISOR_hypfs_op, XEN_HYPFS_OP_read,
+                   (unsigned long)path_buf, path_sz,
+                   (unsigned long)buf, sizeof(*entry));
+    if (ret)
+        goto out;
+    ret = -1;
+    entry = buf;
+    if (!(entry->flags & XEN_HYPFS_WRITEABLE)) {
+        errno = EACCES;
+        goto out;
+    }
+    if (entry->encoding != XEN_HYPFS_ENC_PLAIN) {
+        /* Writing compressed data currently not supported. */
+        errno = EDOM;
+        goto out;
+    }
+
+    switch (entry->type) {
+    case XEN_HYPFS_TYPE_STRING:
+        if (sz < strlen(val) + 1) {
+            sz = strlen(val) + 1;
+            xencall_free_buffer(fshdl->xcall, buf);
+            buf = xencall_alloc_buffer(fshdl->xcall, sz);
+            if (!buf) {
+                errno = ENOMEM;
+                goto out;
+            }
+        }
+        strcpy(buf, val);
+        break;
+    case XEN_HYPFS_TYPE_UINT:
+        sz = entry->content_len;
+        errno = 0;
+        *(unsigned long long *)buf = strtoull(val, &val_end, 0);
+        if (errno || !*val || *val_end)
+            goto out;
+        mask = ~0ULL << (8 * sz);
+        if ((*(uint64_t *)buf & mask) && ((*(uint64_t *)buf & mask) != mask)) {
+            errno = ERANGE;
+            goto out;
+        }
+        break;
+    case XEN_HYPFS_TYPE_INT:
+        sz = entry->content_len;
+        errno = 0;
+        *(unsigned long long *)buf = strtoll(val, &val_end, 0);
+        if (errno || !*val || *val_end)
+            goto out;
+        mask = (sz == 8) ? 0 : ~0ULL << (8 * sz);
+        if ((*(uint64_t *)buf & mask) && ((*(uint64_t *)buf & mask) != mask)) {
+            errno = ERANGE;
+            goto out;
+        }
+        break;
+    case XEN_HYPFS_TYPE_BOOL:
+        *(unsigned long long *)buf = 0;
+        if (!strcmp(val, "1") || !strcmp(val, "on") || !strcmp(val, "yes") ||
+            !strcmp(val, "true") || !strcmp(val, "enable"))
+            *(unsigned long long *)buf = 1;
+        else if (strcmp(val, "0") && strcmp(val, "no") && strcmp(val, "off") &&
+                 strcmp(val, "false") && strcmp(val, "disable")) {
+            errno = EDOM;
+            goto out;
+        }
+        break;
+    default:
+        /* No support for other types (yet). */
+        errno = EDOM;
+        goto out;
+    }
+
+    ret = xencall5(fshdl->xcall, __HYPERVISOR_hypfs_op,
+                   XEN_HYPFS_OP_write_contents,
+                   (unsigned long)path_buf, path_sz,
+                   (unsigned long)buf, sz);
+
+ out:
+    saved_errno = errno;
+    xencall_free_buffer(fshdl->xcall, path_buf);
+    xencall_free_buffer(fshdl->xcall, buf);
+    errno = saved_errno;
+    return ret;
+}
diff --git a/tools/libs/hypfs/include/xenhypfs.h b/tools/libs/hypfs/include/xenhypfs.h
new file mode 100644
index 0000000000..29c69712ce
--- /dev/null
+++ b/tools/libs/hypfs/include/xenhypfs.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2019 SUSE Software Solutions Germany GmbH
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; If not, see <http://www.gnu.org/licenses/>.
+ */
+#ifndef XENHYPFS_H
+#define XENHYPFS_H
+
+#include <stdbool.h>
+#include <stdint.h>
+#include <sys/types.h>
+
+/* Callers who don't care don't need to #include <xentoollog.h> */
+struct xentoollog_logger;
+
+typedef struct xenhypfs_handle xenhypfs_handle;
+
+struct xenhypfs_dirent {
+    char *name;
+    size_t size;
+    enum {
+        xenhypfs_type_dir,
+        xenhypfs_type_blob,
+        xenhypfs_type_string,
+        xenhypfs_type_uint,
+        xenhypfs_type_int,
+        xenhypfs_type_bool
+    } type;
+    enum {
+        xenhypfs_enc_plain,
+        xenhypfs_enc_gzip
+    } encoding;
+    bool is_writable;
+};
+
+xenhypfs_handle *xenhypfs_open(struct xentoollog_logger *logger,
+                               unsigned int open_flags);
+int xenhypfs_close(xenhypfs_handle *fshdl);
+
+/* Returned buffer and dirent should be freed via free(). */
+void *xenhypfs_read_raw(xenhypfs_handle *fshdl, const char *path,
+                        struct xenhypfs_dirent **dirent);
+
+/* Returned buffer should be freed via free(). */
+char *xenhypfs_read(xenhypfs_handle *fshdl, const char *path);
+
+/* Returned buffer should be freed via free(). */
+struct xenhypfs_dirent *xenhypfs_readdir(xenhypfs_handle *fshdl,
+                                         const char *path,
+                                         unsigned int *num_entries);
+
+int xenhypfs_write(xenhypfs_handle *fshdl, const char *path, const char *val);
+
+#endif /* XENHYPFS_H */
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
diff --git a/tools/libs/hypfs/libxenhypfs.map b/tools/libs/hypfs/libxenhypfs.map
new file mode 100644
index 0000000000..47f1edda3e
--- /dev/null
+++ b/tools/libs/hypfs/libxenhypfs.map
@@ -0,0 +1,10 @@
+VERS_1.0 {
+	global:
+		xenhypfs_open;
+		xenhypfs_close;
+		xenhypfs_read_raw;
+		xenhypfs_read;
+		xenhypfs_readdir;
+		xenhypfs_write;
+	local: *; /* Do not expose anything by default */
+};
diff --git a/tools/libs/hypfs/xenhypfs.pc.in b/tools/libs/hypfs/xenhypfs.pc.in
new file mode 100644
index 0000000000..92a262c7a2
--- /dev/null
+++ b/tools/libs/hypfs/xenhypfs.pc.in
@@ -0,0 +1,10 @@
+prefix=@@prefix@@
+includedir=@@incdir@@
+libdir=@@libdir@@
+
+Name: Xenhypfs
+Description: The Xenhypfs library for Xen hypervisor
+Version: @@version@@
+Cflags: -I${includedir} @@cflagslocal@@
+Libs: @@libsflag@@${libdir} -lxenhypfs
+Requires.private: xentoolcore,xentoollog,xencall,z
-- 
2.16.4


_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xenproject.org
https://lists.xenproject.org/mailman/listinfo/xen-devel

  parent reply	other threads:[~2020-02-19  8:12 UTC|newest]

Thread overview: 24+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-02-19  8:11 [Xen-devel] [PATCH v5 0/8] Add hypervisor sysfs-like support Juergen Gross
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 1/8] xen: add a generic way to include binary files as variables Juergen Gross
2020-02-19 12:05   ` Wei Liu
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 2/8] docs: add feature document for Xen hypervisor sysfs-like support Juergen Gross
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 3/8] xen: add basic hypervisor filesystem support Juergen Gross
2020-02-19 15:49   ` Jan Beulich
2020-02-19 16:19     ` Julien Grall
2020-02-20  7:27     ` Jürgen Groß
2020-02-20  8:43       ` Jan Beulich
2020-02-20  9:07         ` Jürgen Groß
2020-02-19 16:26   ` Julien Grall
2020-02-19 16:47     ` Julien Grall
2020-02-20  7:29     ` Jürgen Groß
2020-02-19  8:11 ` Juergen Gross [this message]
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 5/8] tools: add xenfs tool Juergen Gross
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 6/8] xen: provide version information in hypfs Juergen Gross
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 7/8] xen: add /buildinfo/config entry to hypervisor filesystem Juergen Gross
2020-02-19 15:57   ` Jan Beulich
2020-02-20  6:13     ` Jürgen Groß
2020-02-19  8:11 ` [Xen-devel] [PATCH v5 8/8] xen: add runtime parameter access support to hypfs Juergen Gross
2020-02-19 16:44   ` Jan Beulich
2020-02-20  8:22     ` Jürgen Groß
2020-02-20  8:49       ` Jan Beulich
2020-02-20  9:11         ` Jürgen Groß

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20200219081126.29534-5-jgross@suse.com \
    --to=jgross@suse.com \
    --cc=George.Dunlap@eu.citrix.com \
    --cc=andrew.cooper3@citrix.com \
    --cc=ian.jackson@eu.citrix.com \
    --cc=jbeulich@suse.com \
    --cc=julien@xen.org \
    --cc=konrad.wilk@oracle.com \
    --cc=sstabellini@kernel.org \
    --cc=wl@xen.org \
    --cc=xen-devel@lists.xenproject.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.