qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Qemu-devel] [PULL 31/50] char: remaining switch to CharBackend in front


From: Paolo Bonzini
Subject: [Qemu-devel] [PULL 31/50] char: remaining switch to CharBackend in frontend
Date: Mon, 24 Oct 2016 15:47:16 +0200

From: Marc-André Lureau <address@hidden>

Similar to previous change, for the remaining CharDriverState front ends
users.

Signed-off-by: Marc-André Lureau <address@hidden>
Message-Id: <address@hidden>
Signed-off-by: Paolo Bonzini <address@hidden>
---
 backends/rng-egd.c      | 29 ++++++++++++++-----------
 gdbstub.c               | 22 +++++++++++--------
 hw/arm/omap2.c          | 11 +++++-----
 hw/char/mcf_uart.c      | 12 +++++-----
 hw/char/sh_serial.c     | 10 ++++-----
 hw/char/xen_console.c   | 39 +++++++++++++++++++--------------
 hw/mips/mips_malta.c    | 32 +++++++++++++++------------
 monitor.c               | 19 ++++++++--------
 net/colo-compare.c      | 46 +++++++++++++++++++--------------------
 net/filter-mirror.c     | 58 +++++++++++++++++++++++++++++--------------------
 net/slirp.c             | 23 ++++++++++++++------
 net/vhost-user.c        | 27 +++++++++++++----------
 qtest.c                 |  8 +++----
 tests/vhost-user-test.c | 39 ++++++++++++++++++---------------
 14 files changed, 211 insertions(+), 164 deletions(-)

diff --git a/backends/rng-egd.c b/backends/rng-egd.c
index 0f6d0af..e2f8189 100644
--- a/backends/rng-egd.c
+++ b/backends/rng-egd.c
@@ -23,7 +23,7 @@ typedef struct RngEgd
 {
     RngBackend parent;
 
-    CharDriverState *chr;
+    CharBackend chr;
     char *chr_name;
 } RngEgd;
 
@@ -42,7 +42,7 @@ static void rng_egd_request_entropy(RngBackend *b, RngRequest 
*req)
 
         /* XXX this blocks entire thread. Rewrite to use
          * qemu_chr_fe_write and background I/O callbacks */
-        qemu_chr_fe_write_all(s->chr, header, sizeof(header));
+        qemu_chr_fe_write_all(s->chr.chr, header, sizeof(header));
 
         size -= len;
     }
@@ -86,6 +86,7 @@ static void rng_egd_chr_read(void *opaque, const uint8_t 
*buf, int size)
 static void rng_egd_opened(RngBackend *b, Error **errp)
 {
     RngEgd *s = RNG_EGD(b);
+    CharDriverState *chr;
 
     if (s->chr_name == NULL) {
         error_setg(errp, QERR_INVALID_PARAMETER_VALUE,
@@ -93,21 +94,23 @@ static void rng_egd_opened(RngBackend *b, Error **errp)
         return;
     }
 
-    s->chr = qemu_chr_find(s->chr_name);
-    if (s->chr == NULL) {
+    chr = qemu_chr_find(s->chr_name);
+    if (chr == NULL) {
         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
                   "Device '%s' not found", s->chr_name);
         return;
     }
-
-    if (qemu_chr_fe_claim(s->chr) != 0) {
+    if (qemu_chr_fe_claim(chr) != 0) {
         error_setg(errp, QERR_DEVICE_IN_USE, s->chr_name);
         return;
     }
+    if (!qemu_chr_fe_init(&s->chr, chr, errp)) {
+        return;
+    }
 
     /* FIXME we should resubmit pending requests when the CDS reconnects. */
-    qemu_chr_add_handlers(s->chr, rng_egd_chr_can_read, rng_egd_chr_read,
-                          NULL, s);
+    qemu_chr_add_handlers(s->chr.chr, rng_egd_chr_can_read,
+                          rng_egd_chr_read, NULL, s);
 }
 
 static void rng_egd_set_chardev(Object *obj, const char *value, Error **errp)
@@ -127,8 +130,8 @@ static char *rng_egd_get_chardev(Object *obj, Error **errp)
 {
     RngEgd *s = RNG_EGD(obj);
 
-    if (s->chr && s->chr->label) {
-        return g_strdup(s->chr->label);
+    if (s->chr.chr && s->chr.chr->label) {
+        return g_strdup(s->chr.chr->label);
     }
 
     return NULL;
@@ -145,9 +148,9 @@ static void rng_egd_finalize(Object *obj)
 {
     RngEgd *s = RNG_EGD(obj);
 
-    if (s->chr) {
-        qemu_chr_add_handlers(s->chr, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(s->chr);
+    if (s->chr.chr) {
+        qemu_chr_add_handlers(s->chr.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(s->chr.chr);
     }
 
     g_free(s->chr_name);
diff --git a/gdbstub.c b/gdbstub.c
index 2fe71ca..347bd4d 100644
--- a/gdbstub.c
+++ b/gdbstub.c
@@ -303,7 +303,7 @@ typedef struct GDBState {
     int fd;
     int running_state;
 #else
-    CharDriverState *chr;
+    CharBackend chr;
     CharDriverState *mon_chr;
 #endif
     char syscall_buf[256];
@@ -404,7 +404,7 @@ static void put_buffer(GDBState *s, const uint8_t *buf, int 
len)
 #else
     /* XXX this blocks entire thread. Rewrite to use
      * qemu_chr_fe_write and background I/O callbacks */
-    qemu_chr_fe_write_all(s->chr, buf, len);
+    qemu_chr_fe_write_all(s->chr.chr, buf, len);
 #endif
 }
 
@@ -1481,7 +1481,7 @@ void gdb_exit(CPUArchState *env, int code)
       return;
   }
 #else
-  if (!s->chr) {
+  if (!s->chr.chr) {
       return;
   }
 #endif
@@ -1490,7 +1490,7 @@ void gdb_exit(CPUArchState *env, int code)
   put_packet(s, buf);
 
 #ifndef CONFIG_USER_ONLY
-  qemu_chr_delete(s->chr);
+  qemu_chr_delete(s->chr.chr);
 #endif
 }
 
@@ -1750,8 +1750,6 @@ int gdbserver_start(const char *device)
             return -1;
 
         qemu_chr_fe_claim_no_fail(chr);
-        qemu_chr_add_handlers(chr, gdb_chr_can_receive, gdb_chr_receive,
-                              gdb_chr_event, NULL);
     }
 
     s = gdbserver_state;
@@ -1766,14 +1764,20 @@ int gdbserver_start(const char *device)
         mon_chr->chr_write = gdb_monitor_write;
         monitor_init(mon_chr, 0);
     } else {
-        if (s->chr)
-            qemu_chr_delete(s->chr);
+        if (s->chr.chr) {
+            qemu_chr_delete(s->chr.chr);
+        }
         mon_chr = s->mon_chr;
         memset(s, 0, sizeof(GDBState));
+        s->mon_chr = mon_chr;
     }
     s->c_cpu = first_cpu;
     s->g_cpu = first_cpu;
-    s->chr = chr;
+    if (chr) {
+        qemu_chr_fe_init(&s->chr, chr, &error_abort);
+        qemu_chr_add_handlers(s->chr.chr, gdb_chr_can_receive, gdb_chr_receive,
+                              gdb_chr_event, NULL);
+    }
     s->state = chr ? RS_IDLE : RS_INACTIVE;
     s->mon_chr = mon_chr;
     s->current_syscall_cb = NULL;
diff --git a/hw/arm/omap2.c b/hw/arm/omap2.c
index 0b2a355..43d9c4b 100644
--- a/hw/arm/omap2.c
+++ b/hw/arm/omap2.c
@@ -621,7 +621,7 @@ struct omap_sti_s {
     qemu_irq irq;
     MemoryRegion iomem;
     MemoryRegion iomem_fifo;
-    CharDriverState *chr;
+    CharBackend chr;
 
     uint32_t sysconfig;
     uint32_t systest;
@@ -771,14 +771,14 @@ static void omap_sti_fifo_write(void *opaque, hwaddr addr,
         /* Flush channel <i>value</i>.  */
         /* XXX this blocks entire thread. Rewrite to use
          * qemu_chr_fe_write and background I/O callbacks */
-        qemu_chr_fe_write_all(s->chr, (const uint8_t *) "\r", 1);
+        qemu_chr_fe_write_all(s->chr.chr, (const uint8_t *) "\r", 1);
     } else if (ch == STI_TRACE_CONSOLE_CHANNEL || 1) {
         if (value == 0xc0 || value == 0xc3) {
             /* Open channel <i>ch</i>.  */
         } else if (value == 0x00)
-            qemu_chr_fe_write_all(s->chr, (const uint8_t *) "\n", 1);
+            qemu_chr_fe_write_all(s->chr.chr, (const uint8_t *) "\n", 1);
         else
-            qemu_chr_fe_write_all(s->chr, &byte, 1);
+            qemu_chr_fe_write_all(s->chr.chr, &byte, 1);
     }
 }
 
@@ -798,7 +798,8 @@ static struct omap_sti_s *omap_sti_init(struct 
omap_target_agent_s *ta,
     s->irq = irq;
     omap_sti_reset(s);
 
-    s->chr = chr ?: qemu_chr_new("null", "null");
+    qemu_chr_fe_init(&s->chr, chr ?: qemu_chr_new("null", "null"),
+                     &error_abort);
 
     memory_region_init_io(&s->iomem, NULL, &omap_sti_ops, s, "omap.sti",
                           omap_l4_region_size(ta, 0));
diff --git a/hw/char/mcf_uart.c b/hw/char/mcf_uart.c
index c184859..436e1b0 100644
--- a/hw/char/mcf_uart.c
+++ b/hw/char/mcf_uart.c
@@ -10,6 +10,7 @@
 #include "hw/m68k/mcf.h"
 #include "sysemu/char.h"
 #include "exec/address-spaces.h"
+#include "qapi/error.h"
 
 typedef struct {
     MemoryRegion iomem;
@@ -26,7 +27,7 @@ typedef struct {
     int tx_enabled;
     int rx_enabled;
     qemu_irq irq;
-    CharDriverState *chr;
+    CharBackend chr;
 } mcf_uart_state;
 
 /* UART Status Register bits.  */
@@ -92,7 +93,7 @@ uint64_t mcf_uart_read(void *opaque, hwaddr addr,
             if (s->fifo_len == 0)
                 s->sr &= ~MCF_UART_RxRDY;
             mcf_uart_update(s);
-            qemu_chr_accept_input(s->chr);
+            qemu_chr_accept_input(s->chr.chr);
             return val;
         }
     case 0x10:
@@ -113,10 +114,11 @@ uint64_t mcf_uart_read(void *opaque, hwaddr addr,
 static void mcf_uart_do_tx(mcf_uart_state *s)
 {
     if (s->tx_enabled && (s->sr & MCF_UART_TxEMP) == 0) {
-        if (s->chr)
+        if (s->chr.chr) {
             /* XXX this blocks entire thread. Rewrite to use
              * qemu_chr_fe_write and background I/O callbacks */
-            qemu_chr_fe_write_all(s->chr, (unsigned char *)&s->tb, 1);
+            qemu_chr_fe_write_all(s->chr.chr, (unsigned char *)&s->tb, 1);
+        }
         s->sr |= MCF_UART_TxEMP;
     }
     if (s->tx_enabled) {
@@ -280,9 +282,9 @@ void *mcf_uart_init(qemu_irq irq, CharDriverState *chr)
     mcf_uart_state *s;
 
     s = g_malloc0(sizeof(mcf_uart_state));
-    s->chr = chr;
     s->irq = irq;
     if (chr) {
+        qemu_chr_fe_init(&s->chr, chr, &error_abort);
         qemu_chr_fe_claim_no_fail(chr);
         qemu_chr_add_handlers(chr, mcf_uart_can_receive, mcf_uart_receive,
                               mcf_uart_event, s);
diff --git a/hw/char/sh_serial.c b/hw/char/sh_serial.c
index 97ce562..c8b91bb 100644
--- a/hw/char/sh_serial.c
+++ b/hw/char/sh_serial.c
@@ -29,6 +29,7 @@
 #include "hw/sh4/sh.h"
 #include "sysemu/char.h"
 #include "exec/address-spaces.h"
+#include "qapi/error.h"
 
 //#define DEBUG_SERIAL
 
@@ -62,7 +63,7 @@ typedef struct {
     int flags;
     int rtrg;
 
-    CharDriverState *chr;
+    CharBackend chr;
 
     qemu_irq eri;
     qemu_irq rxi;
@@ -109,11 +110,11 @@ static void sh_serial_write(void *opaque, hwaddr offs,
         }
         return;
     case 0x0c: /* FTDR / TDR */
-        if (s->chr) {
+        if (s->chr.chr) {
             ch = val;
             /* XXX this blocks entire thread. Rewrite to use
              * qemu_chr_fe_write and background I/O callbacks */
-            qemu_chr_fe_write_all(s->chr, &ch, 1);
+            qemu_chr_fe_write_all(s->chr.chr, &ch, 1);
        }
        s->dr = val;
        s->flags &= ~SH_SERIAL_FLAG_TDE;
@@ -395,10 +396,9 @@ void sh_serial_init(MemoryRegion *sysmem,
                              0, 0x28);
     memory_region_add_subregion(sysmem, A7ADDR(base), &s->iomem_a7);
 
-    s->chr = chr;
-
     if (chr) {
         qemu_chr_fe_claim_no_fail(chr);
+        qemu_chr_fe_init(&s->chr, chr, &error_abort);
         qemu_chr_add_handlers(chr, sh_serial_can_receive1, sh_serial_receive1,
                              sh_serial_event, s);
     }
diff --git a/hw/char/xen_console.c b/hw/char/xen_console.c
index 11bf6a4..c1d36dc 100644
--- a/hw/char/xen_console.c
+++ b/hw/char/xen_console.c
@@ -26,6 +26,7 @@
 #include "hw/hw.h"
 #include "sysemu/char.h"
 #include "hw/xen/xen_backend.h"
+#include "qapi/error.h"
 
 #include <xen/io/console.h>
 
@@ -43,7 +44,7 @@ struct XenConsole {
     char              console[XEN_BUFSIZE];
     int               ring_ref;
     void              *sring;
-    CharDriverState   *chr;
+    CharBackend       chr;
     int               backlog;
 };
 
@@ -148,11 +149,13 @@ static void xencons_send(struct XenConsole *con)
     ssize_t len, size;
 
     size = con->buffer.size - con->buffer.consumed;
-    if (con->chr)
-        len = qemu_chr_fe_write(con->chr, con->buffer.data + 
con->buffer.consumed,
-                             size);
-    else
+    if (con->chr.chr) {
+        len = qemu_chr_fe_write(con->chr.chr,
+                                con->buffer.data + con->buffer.consumed,
+                                size);
+    } else {
         len = size;
+    }
     if (len < 1) {
        if (!con->backlog) {
            con->backlog = 1;
@@ -196,13 +199,17 @@ static int con_init(struct XenDevice *xendev)
 
     /* no Xen override, use qemu output device */
     if (output == NULL) {
-        con->chr = serial_hds[con->xendev.dev];
+        if (con->xendev.dev) {
+            qemu_chr_fe_init(&con->chr, serial_hds[con->xendev.dev],
+                             &error_abort);
+        }
     } else {
         snprintf(label, sizeof(label), "xencons%d", con->xendev.dev);
-        con->chr = qemu_chr_new(label, output);
+        qemu_chr_fe_init(&con->chr,
+                         qemu_chr_new(label, output), &error_abort);
     }
 
-    xenstore_store_pv_console_info(con->xendev.dev, con->chr);
+    xenstore_store_pv_console_info(con->xendev.dev, con->chr.chr);
 
 out:
     g_free(type);
@@ -235,15 +242,15 @@ static int con_initialise(struct XenDevice *xendev)
        return -1;
 
     xen_be_bind_evtchn(&con->xendev);
-    if (con->chr) {
-        if (qemu_chr_fe_claim(con->chr) == 0) {
-            qemu_chr_add_handlers(con->chr, xencons_can_receive,
+    if (con->chr.chr) {
+        if (qemu_chr_fe_claim(con->chr.chr) == 0) {
+            qemu_chr_add_handlers(con->chr.chr, xencons_can_receive,
                                   xencons_receive, NULL, con);
         } else {
             xen_be_printf(xendev, 0,
                           "xen_console_init error chardev %s already used\n",
-                          con->chr->label);
-            con->chr = NULL;
+                          con->chr.chr->label);
+            con->chr.chr = NULL;
         }
     }
 
@@ -259,9 +266,9 @@ static void con_disconnect(struct XenDevice *xendev)
 {
     struct XenConsole *con = container_of(xendev, struct XenConsole, xendev);
 
-    if (con->chr) {
-        qemu_chr_add_handlers(con->chr, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(con->chr);
+    if (con->chr.chr) {
+        qemu_chr_add_handlers(con->chr.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(con->chr.chr);
     }
     xen_be_unbind_evtchn(&con->xendev);
 
diff --git a/hw/mips/mips_malta.c b/hw/mips/mips_malta.c
index ed0850c..d5601b1 100644
--- a/hw/mips/mips_malta.c
+++ b/hw/mips/mips_malta.c
@@ -85,7 +85,7 @@ typedef struct {
     uint32_t i2coe;
     uint32_t i2cout;
     uint32_t i2csel;
-    CharDriverState *display;
+    CharBackend display;
     char display_text[9];
     SerialState *uart;
     bool display_inited;
@@ -125,8 +125,10 @@ static void malta_fpga_update_display(void *opaque)
     }
     leds_text[8] = '\0';
 
-    qemu_chr_fe_printf(s->display, "\e[H\n\n|\e[32m%-8.8s\e[00m|\r\n", 
leds_text);
-    qemu_chr_fe_printf(s->display, "\n\n\n\n|\e[31m%-8.8s\e[00m|", 
s->display_text);
+    qemu_chr_fe_printf(s->display.chr, "\e[H\n\n|\e[32m%-8.8s\e[00m|\r\n",
+                       leds_text);
+    qemu_chr_fe_printf(s->display.chr, "\n\n\n\n|\e[31m%-8.8s\e[00m|",
+                       s->display_text);
 }
 
 /*
@@ -536,15 +538,15 @@ static void malta_fgpa_display_event(void *opaque, int 
event)
     MaltaFPGAState *s = opaque;
 
     if (event == CHR_EVENT_OPENED && !s->display_inited) {
-        qemu_chr_fe_printf(s->display, "\e[HMalta LEDBAR\r\n");
-        qemu_chr_fe_printf(s->display, "+--------+\r\n");
-        qemu_chr_fe_printf(s->display, "+        +\r\n");
-        qemu_chr_fe_printf(s->display, "+--------+\r\n");
-        qemu_chr_fe_printf(s->display, "\n");
-        qemu_chr_fe_printf(s->display, "Malta ASCII\r\n");
-        qemu_chr_fe_printf(s->display, "+--------+\r\n");
-        qemu_chr_fe_printf(s->display, "+        +\r\n");
-        qemu_chr_fe_printf(s->display, "+--------+\r\n");
+        qemu_chr_fe_printf(s->display.chr, "\e[HMalta LEDBAR\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+--------+\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+        +\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+--------+\r\n");
+        qemu_chr_fe_printf(s->display.chr, "\n");
+        qemu_chr_fe_printf(s->display.chr, "Malta ASCII\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+--------+\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+        +\r\n");
+        qemu_chr_fe_printf(s->display.chr, "+--------+\r\n");
         s->display_inited = true;
     }
 }
@@ -553,6 +555,7 @@ static MaltaFPGAState *malta_fpga_init(MemoryRegion 
*address_space,
          hwaddr base, qemu_irq uart_irq, CharDriverState *uart_chr)
 {
     MaltaFPGAState *s;
+    CharDriverState *chr;
 
     s = (MaltaFPGAState *)g_malloc0(sizeof(MaltaFPGAState));
 
@@ -566,8 +569,9 @@ static MaltaFPGAState *malta_fpga_init(MemoryRegion 
*address_space,
     memory_region_add_subregion(address_space, base, &s->iomem_lo);
     memory_region_add_subregion(address_space, base + 0xa00, &s->iomem_hi);
 
-    s->display = qemu_chr_new("fpga", "vc:320x200");
-    qemu_chr_add_handlers(s->display, NULL, NULL,
+    chr = qemu_chr_new("fpga", "vc:320x200");
+    qemu_chr_fe_init(&s->display, chr, &error_abort);
+    qemu_chr_add_handlers(s->display.chr, NULL, NULL,
                           malta_fgpa_display_event, s);
 
     s->uart = serial_mm_init(address_space, base + 0x900, 3, uart_irq,
diff --git a/monitor.c b/monitor.c
index 8728dd9..40712f7 100644
--- a/monitor.c
+++ b/monitor.c
@@ -186,7 +186,7 @@ typedef struct {
 } MonitorQAPIEventConf;
 
 struct Monitor {
-    CharDriverState *chr;
+    CharBackend chr;
     int reset_seen;
     int flags;
     int suspend_cnt;
@@ -297,7 +297,7 @@ static void monitor_flush_locked(Monitor *mon)
     len = qstring_get_length(mon->outbuf);
 
     if (len && !mon->mux_out) {
-        rc = qemu_chr_fe_write(mon->chr, (const uint8_t *) buf, len);
+        rc = qemu_chr_fe_write(mon->chr.chr, (const uint8_t *) buf, len);
         if ((rc < 0 && errno != EAGAIN) || (rc == len)) {
             /* all flushed or error */
             QDECREF(mon->outbuf);
@@ -311,8 +311,9 @@ static void monitor_flush_locked(Monitor *mon)
             mon->outbuf = tmp;
         }
         if (mon->out_watch == 0) {
-            mon->out_watch = qemu_chr_fe_add_watch(mon->chr, G_IO_OUT|G_IO_HUP,
-                                                   monitor_unblocked, mon);
+            mon->out_watch =
+                qemu_chr_fe_add_watch(mon->chr.chr, G_IO_OUT | G_IO_HUP,
+                                      monitor_unblocked, mon);
         }
     }
 }
@@ -581,8 +582,8 @@ static void monitor_data_init(Monitor *mon)
 
 static void monitor_data_destroy(Monitor *mon)
 {
-    if (mon->chr) {
-        qemu_chr_add_handlers(mon->chr, NULL, NULL, NULL, NULL);
+    if (mon->chr.chr) {
+        qemu_chr_add_handlers(mon->chr.chr, NULL, NULL, NULL, NULL);
     }
     if (monitor_is_qmp(mon)) {
         json_message_parser_destroy(&mon->qmp.parser);
@@ -1745,7 +1746,7 @@ void qmp_getfd(const char *fdname, Error **errp)
     mon_fd_t *monfd;
     int fd;
 
-    fd = qemu_chr_fe_get_msgfd(cur_mon->chr);
+    fd = qemu_chr_fe_get_msgfd(cur_mon->chr.chr);
     if (fd == -1) {
         error_setg(errp, QERR_FD_NOT_SUPPLIED);
         return;
@@ -1870,7 +1871,7 @@ AddfdInfo *qmp_add_fd(bool has_fdset_id, int64_t 
fdset_id, bool has_opaque,
     Monitor *mon = cur_mon;
     AddfdInfo *fdinfo;
 
-    fd = qemu_chr_fe_get_msgfd(mon->chr);
+    fd = qemu_chr_fe_get_msgfd(mon->chr.chr);
     if (fd == -1) {
         error_setg(errp, QERR_FD_NOT_SUPPLIED);
         goto error;
@@ -3977,7 +3978,7 @@ void monitor_init(CharDriverState *chr, int flags)
     mon = g_malloc(sizeof(*mon));
     monitor_data_init(mon);
 
-    mon->chr = chr;
+    qemu_chr_fe_init(&mon->chr, chr, &error_abort);
     mon->flags = flags;
     if (flags & MONITOR_USE_READLINE) {
         mon->rs = readline_init(monitor_readline_printf,
diff --git a/net/colo-compare.c b/net/colo-compare.c
index 47703c5..efcd15e 100644
--- a/net/colo-compare.c
+++ b/net/colo-compare.c
@@ -68,9 +68,9 @@ typedef struct CompareState {
     char *pri_indev;
     char *sec_indev;
     char *outdev;
-    CharDriverState *chr_pri_in;
-    CharDriverState *chr_sec_in;
-    CharDriverState *chr_out;
+    CharBackend chr_pri_in;
+    CharBackend chr_sec_in;
+    CharBackend chr_out;
     SocketReadState pri_rs;
     SocketReadState sec_rs;
 
@@ -385,7 +385,7 @@ static void colo_compare_connection(void *opaque, void 
*user_data)
         }
 
         if (result) {
-            ret = compare_chr_send(s->chr_out, pkt->data, pkt->size);
+            ret = compare_chr_send(s->chr_out.chr, pkt->data, pkt->size);
             if (ret < 0) {
                 error_report("colo_send_primary_packet failed");
             }
@@ -451,7 +451,7 @@ static void compare_pri_chr_in(void *opaque, const uint8_t 
*buf, int size)
 
     ret = net_fill_rstate(&s->pri_rs, buf, size);
     if (ret == -1) {
-        qemu_chr_add_handlers(s->chr_pri_in, NULL, NULL, NULL, NULL);
+        qemu_chr_add_handlers(s->chr_pri_in.chr, NULL, NULL, NULL, NULL);
         error_report("colo-compare primary_in error");
     }
 }
@@ -467,7 +467,7 @@ static void compare_sec_chr_in(void *opaque, const uint8_t 
*buf, int size)
 
     ret = net_fill_rstate(&s->sec_rs, buf, size);
     if (ret == -1) {
-        qemu_chr_add_handlers(s->chr_sec_in, NULL, NULL, NULL, NULL);
+        qemu_chr_add_handlers(s->chr_sec_in.chr, NULL, NULL, NULL, NULL);
         error_report("colo-compare secondary_in error");
     }
 }
@@ -480,9 +480,9 @@ static void *colo_compare_thread(void *opaque)
 
     worker_context = g_main_context_new();
 
-    qemu_chr_add_handlers_full(s->chr_pri_in, compare_chr_can_read,
+    qemu_chr_add_handlers_full(s->chr_pri_in.chr, compare_chr_can_read,
                           compare_pri_chr_in, NULL, s, worker_context);
-    qemu_chr_add_handlers_full(s->chr_sec_in, compare_chr_can_read,
+    qemu_chr_add_handlers_full(s->chr_sec_in.chr, compare_chr_can_read,
                           compare_sec_chr_in, NULL, s, worker_context);
 
     compare_loop = g_main_loop_new(worker_context, FALSE);
@@ -545,7 +545,7 @@ static void compare_pri_rs_finalize(SocketReadState *pri_rs)
 
     if (packet_enqueue(s, PRIMARY_IN)) {
         trace_colo_compare_main("primary: unsupported packet in");
-        compare_chr_send(s->chr_out, pri_rs->buf, pri_rs->packet_len);
+        compare_chr_send(s->chr_out.chr, pri_rs->buf, pri_rs->packet_len);
     } else {
         /* compare connection */
         g_queue_foreach(&s->conn_list, colo_compare_connection, s);
@@ -634,23 +634,23 @@ static void colo_compare_complete(UserCreatable *uc, 
Error **errp)
         return;
     }
 
-    if (find_and_check_chardev(&s->chr_pri_in, s->pri_indev, errp)) {
+    if (find_and_check_chardev(&s->chr_pri_in.chr, s->pri_indev, errp)) {
         return;
     }
 
-    if (find_and_check_chardev(&s->chr_sec_in, s->sec_indev, errp)) {
+    if (find_and_check_chardev(&s->chr_sec_in.chr, s->sec_indev, errp)) {
         return;
     }
 
-    if (find_and_check_chardev(&s->chr_out, s->outdev, errp)) {
+    if (find_and_check_chardev(&s->chr_out.chr, s->outdev, errp)) {
         return;
     }
 
-    qemu_chr_fe_claim_no_fail(s->chr_pri_in);
+    qemu_chr_fe_claim_no_fail(s->chr_pri_in.chr);
 
-    qemu_chr_fe_claim_no_fail(s->chr_sec_in);
+    qemu_chr_fe_claim_no_fail(s->chr_sec_in.chr);
 
-    qemu_chr_fe_claim_no_fail(s->chr_out);
+    qemu_chr_fe_claim_no_fail(s->chr_out.chr);
 
     net_socket_rs_init(&s->pri_rs, compare_pri_rs_finalize);
     net_socket_rs_init(&s->sec_rs, compare_sec_rs_finalize);
@@ -702,16 +702,16 @@ static void colo_compare_finalize(Object *obj)
 {
     CompareState *s = COLO_COMPARE(obj);
 
-    if (s->chr_pri_in) {
-        qemu_chr_add_handlers(s->chr_pri_in, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(s->chr_pri_in);
+    if (s->chr_pri_in.chr) {
+        qemu_chr_add_handlers(s->chr_pri_in.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(s->chr_pri_in.chr);
     }
-    if (s->chr_sec_in) {
-        qemu_chr_add_handlers(s->chr_sec_in, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(s->chr_sec_in);
+    if (s->chr_sec_in.chr) {
+        qemu_chr_add_handlers(s->chr_sec_in.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(s->chr_sec_in.chr);
     }
-    if (s->chr_out) {
-        qemu_chr_fe_release(s->chr_out);
+    if (s->chr_out.chr) {
+        qemu_chr_fe_release(s->chr_out.chr);
     }
 
     g_queue_free(&s->conn_list);
diff --git a/net/filter-mirror.c b/net/filter-mirror.c
index 0ee58d9..425e146 100644
--- a/net/filter-mirror.c
+++ b/net/filter-mirror.c
@@ -38,8 +38,8 @@ typedef struct MirrorState {
     NetFilterState parent_obj;
     char *indev;
     char *outdev;
-    CharDriverState *chr_in;
-    CharDriverState *chr_out;
+    CharBackend chr_in;
+    CharBackend chr_out;
     SocketReadState rs;
 } MirrorState;
 
@@ -110,7 +110,7 @@ static void redirector_chr_read(void *opaque, const uint8_t 
*buf, int size)
     ret = net_fill_rstate(&s->rs, buf, size);
 
     if (ret == -1) {
-        qemu_chr_add_handlers(s->chr_in, NULL, NULL, NULL, NULL);
+        qemu_chr_add_handlers(s->chr_in.chr, NULL, NULL, NULL, NULL);
     }
 }
 
@@ -121,7 +121,7 @@ static void redirector_chr_event(void *opaque, int event)
 
     switch (event) {
     case CHR_EVENT_CLOSED:
-        qemu_chr_add_handlers(s->chr_in, NULL, NULL, NULL, NULL);
+        qemu_chr_add_handlers(s->chr_in.chr, NULL, NULL, NULL, NULL);
         break;
     default:
         break;
@@ -138,7 +138,7 @@ static ssize_t filter_mirror_receive_iov(NetFilterState *nf,
     MirrorState *s = FILTER_MIRROR(nf);
     int ret;
 
-    ret = filter_mirror_send(s->chr_out, iov, iovcnt);
+    ret = filter_mirror_send(s->chr_out.chr, iov, iovcnt);
     if (ret) {
         error_report("filter_mirror_send failed(%s)", strerror(-ret));
     }
@@ -160,8 +160,8 @@ static ssize_t filter_redirector_receive_iov(NetFilterState 
*nf,
     MirrorState *s = FILTER_REDIRECTOR(nf);
     int ret;
 
-    if (s->chr_out) {
-        ret = filter_mirror_send(s->chr_out, iov, iovcnt);
+    if (s->chr_out.chr) {
+        ret = filter_mirror_send(s->chr_out.chr, iov, iovcnt);
         if (ret) {
             error_report("filter_mirror_send failed(%s)", strerror(-ret));
         }
@@ -175,8 +175,8 @@ static void filter_mirror_cleanup(NetFilterState *nf)
 {
     MirrorState *s = FILTER_MIRROR(nf);
 
-    if (s->chr_out) {
-        qemu_chr_fe_release(s->chr_out);
+    if (s->chr_out.chr) {
+        qemu_chr_fe_release(s->chr_out.chr);
     }
 }
 
@@ -184,18 +184,19 @@ static void filter_redirector_cleanup(NetFilterState *nf)
 {
     MirrorState *s = FILTER_REDIRECTOR(nf);
 
-    if (s->chr_in) {
-        qemu_chr_add_handlers(s->chr_in, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(s->chr_in);
+    if (s->chr_in.chr) {
+        qemu_chr_add_handlers(s->chr_in.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(s->chr_in.chr);
     }
-    if (s->chr_out) {
-        qemu_chr_fe_release(s->chr_out);
+    if (s->chr_out.chr) {
+        qemu_chr_fe_release(s->chr_out.chr);
     }
 }
 
 static void filter_mirror_setup(NetFilterState *nf, Error **errp)
 {
     MirrorState *s = FILTER_MIRROR(nf);
+    CharDriverState *chr;
 
     if (!s->outdev) {
         error_setg(errp, "filter mirror needs 'outdev' "
@@ -203,17 +204,19 @@ static void filter_mirror_setup(NetFilterState *nf, Error 
**errp)
         return;
     }
 
-    s->chr_out = qemu_chr_find(s->outdev);
-    if (s->chr_out == NULL) {
+    chr = qemu_chr_find(s->outdev);
+    if (chr == NULL) {
         error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
                   "Device '%s' not found", s->outdev);
         return;
     }
 
-    if (qemu_chr_fe_claim(s->chr_out) != 0) {
+    if (qemu_chr_fe_claim(chr) != 0) {
         error_setg(errp, QERR_DEVICE_IN_USE, s->outdev);
         return;
     }
+
+    qemu_chr_fe_init(&s->chr_out, chr, errp);
 }
 
 static void redirector_rs_finalize(SocketReadState *rs)
@@ -227,6 +230,7 @@ static void redirector_rs_finalize(SocketReadState *rs)
 static void filter_redirector_setup(NetFilterState *nf, Error **errp)
 {
     MirrorState *s = FILTER_REDIRECTOR(nf);
+    CharDriverState *chr;
 
     if (!s->indev && !s->outdev) {
         error_setg(errp, "filter redirector needs 'indev' or "
@@ -243,26 +247,32 @@ static void filter_redirector_setup(NetFilterState *nf, 
Error **errp)
     net_socket_rs_init(&s->rs, redirector_rs_finalize);
 
     if (s->indev) {
-        s->chr_in = qemu_chr_find(s->indev);
-        if (s->chr_in == NULL) {
+        chr = qemu_chr_find(s->indev);
+        if (chr == NULL) {
             error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
                       "IN Device '%s' not found", s->indev);
             return;
         }
 
-        qemu_chr_fe_claim_no_fail(s->chr_in);
-        qemu_chr_add_handlers(s->chr_in, redirector_chr_can_read,
+        qemu_chr_fe_claim_no_fail(chr);
+        if (!qemu_chr_fe_init(&s->chr_in, chr, errp)) {
+            return;
+        }
+        qemu_chr_add_handlers(s->chr_in.chr, redirector_chr_can_read,
                               redirector_chr_read, redirector_chr_event, nf);
     }
 
     if (s->outdev) {
-        s->chr_out = qemu_chr_find(s->outdev);
-        if (s->chr_out == NULL) {
+        chr = qemu_chr_find(s->outdev);
+        if (chr == NULL) {
             error_set(errp, ERROR_CLASS_DEVICE_NOT_FOUND,
                       "OUT Device '%s' not found", s->outdev);
             return;
         }
-        qemu_chr_fe_claim_no_fail(s->chr_out);
+        qemu_chr_fe_claim_no_fail(chr);
+        if (!qemu_chr_fe_init(&s->chr_out, chr, errp)) {
+            return;
+        }
     }
 }
 
diff --git a/net/slirp.c b/net/slirp.c
index f9fdff5..407e8aa 100644
--- a/net/slirp.c
+++ b/net/slirp.c
@@ -40,6 +40,7 @@
 #include "sysemu/char.h"
 #include "sysemu/sysemu.h"
 #include "qemu/cutils.h"
+#include "qapi/error.h"
 
 static int get_str_sep(char *buf, int buf_size, const char **pp, int sep)
 {
@@ -682,7 +683,7 @@ int net_slirp_smb(const char *exported_dir)
 #endif /* !defined(_WIN32) */
 
 struct GuestFwd {
-    CharDriverState *hd;
+    CharBackend hd;
     struct in_addr server;
     int port;
     Slirp *slirp;
@@ -746,15 +747,23 @@ static int slirp_guestfwd(SlirpState *s, const char 
*config_str,
             return -1;
         }
     } else {
-        fwd = g_new(struct GuestFwd, 1);
-        fwd->hd = qemu_chr_new(buf, p);
-        if (!fwd->hd) {
+        Error *err = NULL;
+        CharDriverState *chr = qemu_chr_new(buf, p);
+
+        if (!chr) {
             error_report("could not open guest forwarding device '%s'", buf);
+            return -1;
+        }
+
+        fwd = g_new(struct GuestFwd, 1);
+        qemu_chr_fe_init(&fwd->hd, chr, &err);
+        if (err) {
+            error_report_err(err);
             g_free(fwd);
             return -1;
         }
 
-        if (slirp_add_exec(s->slirp, 3, fwd->hd, &server, port) < 0) {
+        if (slirp_add_exec(s->slirp, 3, fwd->hd.chr, &server, port) < 0) {
             error_report("conflicting/invalid host:port in guest forwarding "
                          "rule '%s'", config_str);
             g_free(fwd);
@@ -764,8 +773,8 @@ static int slirp_guestfwd(SlirpState *s, const char 
*config_str,
         fwd->port = port;
         fwd->slirp = s->slirp;
 
-        qemu_chr_fe_claim_no_fail(fwd->hd);
-        qemu_chr_add_handlers(fwd->hd, guestfwd_can_read, guestfwd_read,
+        qemu_chr_fe_claim_no_fail(fwd->hd.chr);
+        qemu_chr_add_handlers(fwd->hd.chr, guestfwd_can_read, guestfwd_read,
                               NULL, fwd);
     }
     return 0;
diff --git a/net/vhost-user.c b/net/vhost-user.c
index 5b94c84..957459f 100644
--- a/net/vhost-user.c
+++ b/net/vhost-user.c
@@ -20,7 +20,7 @@
 
 typedef struct VhostUserState {
     NetClientState nc;
-    CharDriverState *chr;
+    CharBackend chr;
     VHostNetState *vhost_net;
     guint watch;
     uint64_t acked_features;
@@ -78,7 +78,7 @@ static int vhost_user_start(int queues, NetClientState *ncs[])
         s = DO_UPCAST(VhostUserState, nc, ncs[i]);
 
         options.net_backend = ncs[i];
-        options.opaque      = s->chr;
+        options.opaque      = s->chr.chr;
         options.busyloop_timeout = 0;
         net = vhost_net_init(&options);
         if (!net) {
@@ -150,10 +150,10 @@ static void vhost_user_cleanup(NetClientState *nc)
         g_free(s->vhost_net);
         s->vhost_net = NULL;
     }
-    if (s->chr) {
-        qemu_chr_add_handlers(s->chr, NULL, NULL, NULL, NULL);
-        qemu_chr_fe_release(s->chr);
-        s->chr = NULL;
+    if (s->chr.chr) {
+        qemu_chr_add_handlers(s->chr.chr, NULL, NULL, NULL, NULL);
+        qemu_chr_fe_release(s->chr.chr);
+        s->chr.chr = NULL;
     }
 
     qemu_purge_queued_packets(nc);
@@ -187,7 +187,7 @@ static gboolean net_vhost_user_watch(GIOChannel *chan, 
GIOCondition cond,
 {
     VhostUserState *s = opaque;
 
-    qemu_chr_disconnect(s->chr);
+    qemu_chr_disconnect(s->chr.chr);
 
     return FALSE;
 }
@@ -206,13 +206,13 @@ static void net_vhost_user_event(void *opaque, int event)
     assert(queues < MAX_QUEUE_NUM);
 
     s = DO_UPCAST(VhostUserState, nc, ncs[0]);
-    trace_vhost_user_event(s->chr->label, event);
+    trace_vhost_user_event(s->chr.chr->label, event);
     switch (event) {
     case CHR_EVENT_OPENED:
-        s->watch = qemu_chr_fe_add_watch(s->chr, G_IO_HUP,
+        s->watch = qemu_chr_fe_add_watch(s->chr.chr, G_IO_HUP,
                                          net_vhost_user_watch, s);
         if (vhost_user_start(queues, ncs) < 0) {
-            qemu_chr_disconnect(s->chr);
+            qemu_chr_disconnect(s->chr.chr);
             return;
         }
         qmp_set_link(name, true, &err);
@@ -235,6 +235,7 @@ static int net_vhost_user_init(NetClientState *peer, const 
char *device,
                                const char *name, CharDriverState *chr,
                                int queues)
 {
+    Error *err = NULL;
     NetClientState *nc, *nc0 = NULL;
     VhostUserState *s;
     int i;
@@ -254,12 +255,14 @@ static int net_vhost_user_init(NetClientState *peer, 
const char *device,
         nc->queue_index = i;
 
         s = DO_UPCAST(VhostUserState, nc, nc);
-        s->chr = chr;
+        if (!qemu_chr_fe_init(&s->chr, chr, &err)) {
+            error_report_err(err);
+            return -1;
+        }
     }
 
     s = DO_UPCAST(VhostUserState, nc, nc0);
     do {
-        Error *err = NULL;
         if (qemu_chr_wait_connected(chr, &err) < 0) {
             error_report_err(err);
             return -1;
diff --git a/qtest.c b/qtest.c
index 2d9a021..3fb3c11 100644
--- a/qtest.c
+++ b/qtest.c
@@ -38,7 +38,7 @@ bool qtest_allowed;
 
 static DeviceState *irq_intercept_dev;
 static FILE *qtest_log_fp;
-static CharDriverState *qtest_chr;
+static CharBackend qtest_chr;
 static GString *inbuf;
 static int irq_levels[MAX_IRQ];
 static qemu_timeval start_time;
@@ -249,7 +249,7 @@ static void qtest_irq_handler(void *opaque, int n, int 
level)
     qemu_set_irq(old_irq, level);
 
     if (irq_levels[n] != level) {
-        CharDriverState *chr = qtest_chr;
+        CharDriverState *chr = qtest_chr.chr;
         irq_levels[n] = level;
         qtest_send_prefix(chr);
         qtest_sendf(chr, "IRQ %s %d\n",
@@ -690,12 +690,12 @@ void qtest_init(const char *qtest_chrdev, const char 
*qtest_log, Error **errp)
     qemu_chr_fe_set_echo(chr, true);
 
     inbuf = g_string_new("");
-    qtest_chr = chr;
+    qemu_chr_fe_init(&qtest_chr, chr, errp);
 }
 
 bool qtest_driver(void)
 {
-    return qtest_chr;
+    return qtest_chr.chr != NULL;
 }
 
 static void qtest_accel_class_init(ObjectClass *oc, void *data)
diff --git a/tests/vhost-user-test.c b/tests/vhost-user-test.c
index edf30ac..52fbc03 100644
--- a/tests/vhost-user-test.c
+++ b/tests/vhost-user-test.c
@@ -19,6 +19,7 @@
 #include "libqos/libqos.h"
 #include "libqos/pci-pc.h"
 #include "libqos/virtio-pci.h"
+#include "qapi/error.h"
 
 #include "libqos/pci-pc.h"
 #include "libqos/virtio-pci.h"
@@ -141,7 +142,7 @@ typedef struct TestServer {
     gchar *socket_path;
     gchar *mig_path;
     gchar *chr_name;
-    CharDriverState *chr;
+    CharBackend chr;
     int fds_num;
     int fds[VHOST_MEMORY_MAX_NREGIONS];
     VhostUserMemory memory;
@@ -261,13 +262,13 @@ static int chr_can_read(void *opaque)
 static void chr_read(void *opaque, const uint8_t *buf, int size)
 {
     TestServer *s = opaque;
-    CharDriverState *chr = s->chr;
+    CharBackend *chr = &s->chr;
     VhostUserMsg msg;
     uint8_t *p = (uint8_t *) &msg;
     int fd;
 
     if (s->test_fail) {
-        qemu_chr_disconnect(chr);
+        qemu_chr_disconnect(chr->chr);
         /* now switch to non-failure */
         s->test_fail = false;
     }
@@ -282,7 +283,7 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
 
     if (msg.size) {
         p += VHOST_USER_HDR_SIZE;
-        size = qemu_chr_fe_read_all(chr, p, msg.size);
+        size = qemu_chr_fe_read_all(chr->chr, p, msg.size);
         if (size != msg.size) {
             g_test_message("Wrong message size received %d != %d\n",
                            size, msg.size);
@@ -305,14 +306,14 @@ static void chr_read(void *opaque, const uint8_t *buf, 
int size)
             s->test_flags = TEST_FLAGS_END;
         }
         p = (uint8_t *) &msg;
-        qemu_chr_fe_write_all(chr, p, VHOST_USER_HDR_SIZE + msg.size);
+        qemu_chr_fe_write_all(chr->chr, p, VHOST_USER_HDR_SIZE + msg.size);
         break;
 
     case VHOST_USER_SET_FEATURES:
        g_assert_cmpint(msg.payload.u64 & (0x1ULL << 
VHOST_USER_F_PROTOCOL_FEATURES),
                        !=, 0ULL);
         if (s->test_flags == TEST_FLAGS_DISCONNECT) {
-            qemu_chr_disconnect(chr);
+            qemu_chr_disconnect(chr->chr);
             s->test_flags = TEST_FLAGS_BAD;
         }
         break;
@@ -326,7 +327,7 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
             msg.payload.u64 |= 1 << VHOST_USER_PROTOCOL_F_MQ;
         }
         p = (uint8_t *) &msg;
-        qemu_chr_fe_write_all(chr, p, VHOST_USER_HDR_SIZE + msg.size);
+        qemu_chr_fe_write_all(chr->chr, p, VHOST_USER_HDR_SIZE + msg.size);
         break;
 
     case VHOST_USER_GET_VRING_BASE:
@@ -335,7 +336,7 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
         msg.size = sizeof(m.payload.state);
         msg.payload.state.num = 0;
         p = (uint8_t *) &msg;
-        qemu_chr_fe_write_all(chr, p, VHOST_USER_HDR_SIZE + msg.size);
+        qemu_chr_fe_write_all(chr->chr, p, VHOST_USER_HDR_SIZE + msg.size);
 
         assert(msg.payload.state.index < s->queues * 2);
         s->rings &= ~(0x1ULL << msg.payload.state.index);
@@ -344,7 +345,8 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
     case VHOST_USER_SET_MEM_TABLE:
         /* received the mem table */
         memcpy(&s->memory, &msg.payload.memory, sizeof(msg.payload.memory));
-        s->fds_num = qemu_chr_fe_get_msgfds(chr, s->fds, G_N_ELEMENTS(s->fds));
+        s->fds_num = qemu_chr_fe_get_msgfds(chr->chr, s->fds,
+                                            G_N_ELEMENTS(s->fds));
 
         /* signal the test that it can continue */
         g_cond_signal(&s->data_cond);
@@ -353,7 +355,7 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
     case VHOST_USER_SET_VRING_KICK:
     case VHOST_USER_SET_VRING_CALL:
         /* consume the fd */
-        qemu_chr_fe_get_msgfds(chr, &fd, 1);
+        qemu_chr_fe_get_msgfds(chr->chr, &fd, 1);
         /*
          * This is a non-blocking eventfd.
          * The receive function forces it to be blocking,
@@ -367,11 +369,11 @@ static void chr_read(void *opaque, const uint8_t *buf, 
int size)
             close(s->log_fd);
             s->log_fd = -1;
         }
-        qemu_chr_fe_get_msgfds(chr, &s->log_fd, 1);
+        qemu_chr_fe_get_msgfds(chr->chr, &s->log_fd, 1);
         msg.flags |= VHOST_USER_REPLY_MASK;
         msg.size = 0;
         p = (uint8_t *) &msg;
-        qemu_chr_fe_write_all(chr, p, VHOST_USER_HDR_SIZE);
+        qemu_chr_fe_write_all(chr->chr, p, VHOST_USER_HDR_SIZE);
 
         g_cond_signal(&s->data_cond);
         break;
@@ -386,7 +388,7 @@ static void chr_read(void *opaque, const uint8_t *buf, int 
size)
         msg.size = sizeof(m.payload.u64);
         msg.payload.u64 = s->queues;
         p = (uint8_t *) &msg;
-        qemu_chr_fe_write_all(chr, p, VHOST_USER_HDR_SIZE + msg.size);
+        qemu_chr_fe_write_all(chr->chr, p, VHOST_USER_HDR_SIZE + msg.size);
         break;
 
     default:
@@ -453,12 +455,13 @@ static void chr_event(void *opaque, int event)
 static void test_server_create_chr(TestServer *server, const gchar *opt)
 {
     gchar *chr_path;
-
+    CharDriverState *chr;
     chr_path = g_strdup_printf("unix:%s%s", server->socket_path, opt);
-    server->chr = qemu_chr_new(server->chr_name, chr_path);
+    chr = qemu_chr_new(server->chr_name, chr_path);
+    qemu_chr_fe_init(&server->chr, chr, &error_abort);
     g_free(chr_path);
 
-    qemu_chr_add_handlers(server->chr, chr_can_read, chr_read,
+    qemu_chr_add_handlers(server->chr.chr, chr_can_read, chr_read,
                           chr_event, server);
 }
 
@@ -484,7 +487,7 @@ static gboolean _test_server_free(TestServer *server)
 {
     int i;
 
-    qemu_chr_delete(server->chr);
+    qemu_chr_delete(server->chr.chr);
 
     for (i = 0; i < server->fds_num; i++) {
         close(server->fds[i]);
@@ -721,7 +724,7 @@ reconnect_cb(gpointer user_data)
 {
     TestServer *s = user_data;
 
-    qemu_chr_disconnect(s->chr);
+    qemu_chr_disconnect(s->chr.chr);
 
     return FALSE;
 }
-- 
1.8.3.1





reply via email to

[Prev in Thread] Current Thread [Next in Thread]