Patchwork [RFC,v2,01/19] virtproxy: base data structures and constants

login
register
mail settings
Submitter Michael Roth
Date Nov. 10, 2010, 10:27 p.m.
Message ID <1289428095-5059-2-git-send-email-mdroth@linux.vnet.ibm.com>
Download mbox | patch
Permalink /patch/70710/
State New
Headers show

Comments

Michael Roth - Nov. 10, 2010, 10:27 p.m.
Signed-off-by: Michael Roth <mdroth@linux.vnet.ibm.com>
---
 virtproxy.c |  136 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 virtproxy.h |   34 +++++++++++++++
 2 files changed, 170 insertions(+), 0 deletions(-)
 create mode 100644 virtproxy.c
 create mode 100644 virtproxy.h

Patch

diff --git a/virtproxy.c b/virtproxy.c
new file mode 100644
index 0000000..8f18d83
--- /dev/null
+++ b/virtproxy.c
@@ -0,0 +1,136 @@ 
+/*
+ * virt-proxy - host/guest communication layer
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Michael Roth      <mdroth@linux.vnet.ibm.com>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ *
+ */
+
+#include "virtproxy.h"
+
+#define VP_SERVICE_ID_LEN 32    /* max length of service id string */
+#define VP_PKT_DATA_LEN 1024    /* max proxied bytes per VPPacket */
+#define VP_CONN_DATA_LEN 1024   /* max bytes conns can send at a time */
+#define VP_MAGIC 0x1F374059
+
+/* listening fd, one for each service we're forwarding to remote end */
+typedef struct VPOForward {
+    VPDriver *drv;
+    int listen_fd;
+    char service_id[VP_SERVICE_ID_LEN];
+    QLIST_ENTRY(VPOForward) next;
+} VPOForward;
+
+/* service_id->path/port mapping of each service forwarded from remote end */
+typedef struct VPIForward {
+    VPDriver *drv;
+    char service_id[VP_SERVICE_ID_LEN];
+    QemuOpts *socket_opts;
+    QLIST_ENTRY(VPIForward) next;
+} VPIForward;
+
+/* proxied client/server connected states */
+typedef struct VPConn {
+    VPDriver *drv;
+    int client_fd;
+    int server_fd;
+    enum {
+        VP_CONN_CLIENT = 1,
+        VP_CONN_SERVER,
+    } type;
+    enum {
+        VP_STATE_NEW = 1,   /* accept()'d and registered fd */
+        VP_STATE_INIT,      /* sent init pkt to remote end, waiting for ack */
+        VP_STATE_CONNECTED, /* client and server connected */
+    } state;
+    QLIST_ENTRY(VPConn) next;
+} VPConn;
+
+typedef struct VPControlMsg {
+    enum {
+        VP_CONTROL_CONNECT_INIT = 1,
+        VP_CONTROL_CONNECT_ACK,
+        VP_CONTROL_CLOSE,
+    } type;
+    union {
+        /* tell remote end connect to server and map client_fd to it */
+        struct {
+            int client_fd;
+            char service_id[VP_SERVICE_ID_LEN];
+        } connect_init;
+        /* tell remote end we've created the connection to the server,
+         * and give them the corresponding fd to use so we don't have
+         * to do a reverse lookup everytime
+         */
+        struct {
+            int client_fd;
+            int server_fd;
+        } connect_ack;
+        /* tell remote end to close fd in question, presumably because
+         * connection was closed on our end
+         */
+        struct {
+            int client_fd;
+            int server_fd;
+        } close;
+    } args;
+} VPControlMsg;
+
+typedef struct VPPacket {
+    enum {
+        VP_PKT_CONTROL = 1,
+        VP_PKT_CLIENT,
+        VP_PKT_SERVER,
+    } type;
+    union {
+        VPControlMsg msg;
+        struct {
+            int client_fd;
+            int server_fd;
+            int bytes;
+            char data[VP_PKT_DATA_LEN];
+        } proxied;
+    } payload;
+    int magic;
+} __attribute__((__packed__)) VPPacket;
+
+struct VPDriver {
+    enum vp_context ctx;
+    int channel_fd;
+    int listen_fd;
+    CharDriverState *chr;
+    char buf[sizeof(VPPacket)];
+    int buflen;
+    QLIST_HEAD(, VPOForward) oforwards;
+    QLIST_HEAD(, VPIForward) iforwards;
+    QLIST_HEAD(, VPConn) conns;
+};
+
+static QemuOptsList vp_socket_opts = {
+    .name = "vp_socket_opts",
+    .head = QTAILQ_HEAD_INITIALIZER(vp_socket_opts.head),
+    .desc = {
+        {
+            .name = "path",
+            .type = QEMU_OPT_STRING,
+        },{
+            .name = "host",
+            .type = QEMU_OPT_STRING,
+        },{
+            .name = "port",
+            .type = QEMU_OPT_STRING,
+        },{
+            .name = "ipv4",
+            .type = QEMU_OPT_BOOL,
+        },{
+            .name = "ipv6",
+            .type = QEMU_OPT_BOOL,
+        },
+        { /* end if list */ }
+    },
+};
diff --git a/virtproxy.h b/virtproxy.h
new file mode 100644
index 0000000..0203421
--- /dev/null
+++ b/virtproxy.h
@@ -0,0 +1,34 @@ 
+/*
+ * virt-proxy - host/guest communication layer
+ *
+ * Copyright IBM Corp. 2010
+ *
+ * Authors:
+ *  Michael Roth      <mdroth@linux.vnet.ibm.com>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ *
+ */
+
+#ifndef VIRTPROXY_H
+#define VIRTPROXY_H
+
+#include "qemu-common.h"
+#include "qemu-queue.h"
+
+typedef struct VPDriver VPDriver;
+
+/* wrappers for s/vp/qemu/ functions we need */
+int vp_send_all(int fd, const void *buf, int len1);
+int vp_set_fd_handler2(int fd,
+                         IOCanReadHandler *fd_read_poll,
+                         IOHandler *fd_read,
+                         IOHandler *fd_write,
+                         void *opaque);
+int vp_set_fd_handler(int fd,
+                        IOHandler *fd_read,
+                        IOHandler *fd_write,
+                        void *opaque);
+
+#endif /* VIRTPROXY_H */