3e5111
From 705cbf8998e405b98f2d536f6d92c524755fe219 Mon Sep 17 00:00:00 2001
3e5111
Message-Id: <705cbf8998e405b98f2d536f6d92c524755fe219@dist-git>
3e5111
From: Martin Kletzander <mkletzan@redhat.com>
3e5111
Date: Tue, 25 Apr 2017 13:41:16 +0200
3e5111
Subject: [PATCH] conf, docs: Add support for coalesce setting(s)
3e5111
3e5111
https://bugzilla.redhat.com/show_bug.cgi?id=1414627
3e5111
3e5111
We are currently parsing only rx/frames/max because that's the only
3e5111
value that makes sense for us.  The tun device just added support for
3e5111
this one and the others are only supported by hardware devices which
3e5111
we don't need to worry about as the only way we'd pass those to the
3e5111
domain is using <hostdev/> or <interface type='hostdev'/>.  And in
3e5111
those cases the guest can modify the settings itself.
3e5111
3e5111
Signed-off-by: Martin Kletzander <mkletzan@redhat.com>
3e5111
(cherry picked from commit 523c9960621eaf307ae8d4ae2735fb66f89d5634)
3e5111
Signed-off-by: Martin Kletzander <mkletzan@redhat.com>
3e5111
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
3e5111
---
3e5111
 docs/formatdomain.html.in                          |  27 +++++
3e5111
 docs/schemas/domaincommon.rng                      | 131 +++++++++++++++++++++
3e5111
 src/conf/domain_conf.c                             |  80 +++++++++++++
3e5111
 src/conf/domain_conf.h                             |   2 +
3e5111
 src/qemu/qemu_domain.c                             |  31 +++++
3e5111
 .../qemuxml2argvdata/qemuxml2argv-net-coalesce.xml |  68 +++++++++++
3e5111
 .../qemuxml2xmlout-net-coalesce.xml                |  71 +++++++++++
3e5111
 tests/qemuxml2xmltest.c                            |   1 +
3e5111
 8 files changed, 411 insertions(+)
3e5111
 create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-net-coalesce.xml
3e5111
 create mode 100644 tests/qemuxml2xmloutdata/qemuxml2xmlout-net-coalesce.xml
3e5111
3e5111
diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
3e5111
index aee1e1442..7374cb243 100644
3e5111
--- a/docs/formatdomain.html.in
3e5111
+++ b/docs/formatdomain.html.in
3e5111
@@ -5437,6 +5437,33 @@ qemu-kvm -net nic,model=? /dev/null
3e5111
       Since 3.1.0
3e5111
     

3e5111
 
3e5111
+    
Coalesce settings
3e5111
+
3e5111
+...
3e5111
+<devices>
3e5111
+  <interface type='network'>
3e5111
+    <source network='default'/>
3e5111
+    <target dev='vnet0'/>
3e5111
+    <coalesce>
3e5111
+      <rx>
3e5111
+        <frames max='7'/>
3e5111
+      </rx>
3e5111
+    </coalesce>
3e5111
+  </interface>
3e5111
+</devices>
3e5111
+...
3e5111
+
3e5111
+    

3e5111
+      This element provides means of setting coalesce settings for
3e5111
+      some interface devices (currently only type network
3e5111
+      and bridge.  Currently there is just one attribute,
3e5111
+      max, to tweak, in element frames for
3e5111
+      the rx group, which accepts a non-negative integer
3e5111
+      that specifies the maximum number of packets that will be
3e5111
+      received before an interrupt.
3e5111
+      Since 3.3.0
3e5111
+    

3e5111
+
3e5111
     
IP configuration
3e5111
 
3e5111
 ...
3e5111
diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
3e5111
index d5c28ee3c..7a9b4b702 100644
3e5111
--- a/docs/schemas/domaincommon.rng
3e5111
+++ b/docs/schemas/domaincommon.rng
3e5111
@@ -2509,6 +2509,9 @@
3e5111
         <ref name="mtu"/>
3e5111
       </optional>
3e5111
       <optional>
3e5111
+        <ref name="coalesce"/>
3e5111
+      </optional>
3e5111
+      <optional>
3e5111
         <element name="target">
3e5111
           <attribute name="dev">
3e5111
             <ref name="deviceName"/>
3e5111
@@ -5746,4 +5749,132 @@
3e5111
       </choice>
3e5111
     </attribute>
3e5111
   </define>
3e5111
+
3e5111
+  <define name="coalesce">
3e5111
+    <element name="coalesce">
3e5111
+      <interleave>
3e5111
+        <optional>
3e5111
+          <element name="rx">
3e5111
+            <optional>
3e5111
+              <element name="frames">
3e5111
+                <optional>
3e5111
+                  <attribute name="max">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                
3e5111
+                    This is how we'd add more Rx-related settings for
3e5111
+                    frames, like irq, high, and low
3e5111
+
3e5111
+                <optional>
3e5111
+                  <attribute name="irq">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="high">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="low">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+
3e5111
+              -->
3e5111
+              </element>
3e5111
+            </optional>
3e5111
+            
3e5111
+                This is how we'd add more Rx-related settings, like
3e5111
+                usecs
3e5111
+
3e5111
+            <optional>
3e5111
+              <element name="usecs">
3e5111
+                <optional>
3e5111
+                  <attribute name="max">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="irq">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="high">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="low">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+              </element>
3e5111
+            </optional>
3e5111
+              -->
3e5111
+          </element>
3e5111
+        </optional>
3e5111
+        
3e5111
+            This is how you would add more coalesce settings, like
3e5111
+            Tx-related ones
3e5111
+
3e5111
+        <optional>
3e5111
+          <element name="tx">
3e5111
+            <optional>
3e5111
+              <element name="frames">
3e5111
+                <optional>
3e5111
+                  <attribute name="max">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="irq">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="high">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="low">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+              </element>
3e5111
+            </optional>
3e5111
+            <optional>
3e5111
+              <element name="usecs">
3e5111
+                <optional>
3e5111
+                  <attribute name="max">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="irq">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="high">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+                <optional>
3e5111
+                  <attribute name="low">
3e5111
+                    <ref name="unsignedInt"/>
3e5111
+                  </attribute>
3e5111
+                </optional>
3e5111
+              </element>
3e5111
+            </optional>
3e5111
+          </element>
3e5111
+        </optional>
3e5111
+        -->
3e5111
+      </interleave>
3e5111
+    </element>
3e5111
+  </define>
3e5111
+
3e5111
 </grammar>
3e5111
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
3e5111
index 71f0c95c3..f2801ec84 100644
3e5111
--- a/src/conf/domain_conf.c
3e5111
+++ b/src/conf/domain_conf.c
3e5111
@@ -6759,6 +6759,77 @@ virDomainNetIPInfoParseXML(const char *source,
3e5111
     return ret;
3e5111
 }
3e5111
 
3e5111
+
3e5111
+static virNetDevCoalescePtr
3e5111
+virDomainNetDefCoalesceParseXML(xmlNodePtr node,
3e5111
+                                xmlXPathContextPtr ctxt)
3e5111
+{
3e5111
+    virNetDevCoalescePtr ret = NULL;
3e5111
+    xmlNodePtr save = NULL;
3e5111
+    char *str = NULL;
3e5111
+    unsigned long long tmp = 0;
3e5111
+
3e5111
+    save = ctxt->node;
3e5111
+    ctxt->node = node;
3e5111
+
3e5111
+    str = virXPathString("string(./rx/frames/@max)", ctxt);
3e5111
+    if (!str)
3e5111
+        goto cleanup;
3e5111
+
3e5111
+    if (!ret && VIR_ALLOC(ret) < 0)
3e5111
+        goto cleanup;
3e5111
+
3e5111
+    if (virStrToLong_ullp(str, NULL, 10, &tmp) < 0) {
3e5111
+        virReportError(VIR_ERR_XML_DETAIL,
3e5111
+                       _("cannot parse value '%s' for coalesce parameter"),
3e5111
+                       str);
3e5111
+        VIR_FREE(str);
3e5111
+        goto error;
3e5111
+    }
3e5111
+    VIR_FREE(str);
3e5111
+
3e5111
+    if (tmp > UINT32_MAX) {
3e5111
+        virReportError(VIR_ERR_OVERFLOW,
3e5111
+                       _("value '%llu' is too big for coalesce "
3e5111
+                         "parameter, maximum is '%lu'"),
3e5111
+                       tmp, (unsigned long) UINT32_MAX);
3e5111
+        goto error;
3e5111
+    }
3e5111
+    ret->rx_max_coalesced_frames = tmp;
3e5111
+
3e5111
+ cleanup:
3e5111
+    ctxt->node = save;
3e5111
+    return ret;
3e5111
+
3e5111
+ error:
3e5111
+    VIR_FREE(ret);
3e5111
+    goto cleanup;
3e5111
+}
3e5111
+
3e5111
+static void
3e5111
+virDomainNetDefCoalesceFormatXML(virBufferPtr buf,
3e5111
+                                 virNetDevCoalescePtr coalesce)
3e5111
+{
3e5111
+    if (!coalesce || !coalesce->rx_max_coalesced_frames)
3e5111
+        return;
3e5111
+
3e5111
+    virBufferAddLit(buf, "<coalesce>\n");
3e5111
+    virBufferAdjustIndent(buf, 2);
3e5111
+
3e5111
+    virBufferAddLit(buf, "<rx>\n");
3e5111
+    virBufferAdjustIndent(buf, 2);
3e5111
+
3e5111
+    virBufferAsprintf(buf, "<frames max='%u'/>\n",
3e5111
+                      coalesce->rx_max_coalesced_frames);
3e5111
+
3e5111
+    virBufferAdjustIndent(buf, -2);
3e5111
+    virBufferAddLit(buf, "</rx>\n");
3e5111
+
3e5111
+    virBufferAdjustIndent(buf, -2);
3e5111
+    virBufferAddLit(buf, "</coalesce>\n");
3e5111
+}
3e5111
+
3e5111
+
3e5111
 static int
3e5111
 virDomainHostdevDefParseXMLCaps(xmlNodePtr node ATTRIBUTE_UNUSED,
3e5111
                                 xmlXPathContextPtr ctxt,
3e5111
@@ -10242,6 +10313,13 @@ virDomainNetDefParseXML(virDomainXMLOptionPtr xmlopt,
3e5111
         goto error;
3e5111
     }
3e5111
 
3e5111
+    node = virXPathNode("./coalesce", ctxt);
3e5111
+    if (node) {
3e5111
+        def->coalesce = virDomainNetDefCoalesceParseXML(node, ctxt);
3e5111
+        if (!def->coalesce)
3e5111
+            goto error;
3e5111
+    }
3e5111
+
3e5111
  cleanup:
3e5111
     ctxt->node = oldnode;
3e5111
     VIR_FREE(macaddr);
3e5111
@@ -22135,6 +22213,8 @@ virDomainNetDefFormat(virBufferPtr buf,
3e5111
     if (def->mtu)
3e5111
         virBufferAsprintf(buf, "<mtu size='%u'/>\n", def->mtu);
3e5111
 
3e5111
+    virDomainNetDefCoalesceFormatXML(buf, def->coalesce);
3e5111
+
3e5111
     if (virDomainDeviceInfoFormat(buf, &def->info,
3e5111
                                   flags | VIR_DOMAIN_DEF_FORMAT_ALLOW_BOOT
3e5111
                                   | VIR_DOMAIN_DEF_FORMAT_ALLOW_ROM) < 0)
3e5111
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
3e5111
index 71e651975..1dbbcdc51 100644
3e5111
--- a/src/conf/domain_conf.h
3e5111
+++ b/src/conf/domain_conf.h
3e5111
@@ -41,6 +41,7 @@
3e5111
 # include "numa_conf.h"
3e5111
 # include "virnetdevmacvlan.h"
3e5111
 # include "virsysinfo.h"
3e5111
+# include "virnetdev.h"
3e5111
 # include "virnetdevip.h"
3e5111
 # include "virnetdevvportprofile.h"
3e5111
 # include "virnetdevbandwidth.h"
3e5111
@@ -1036,6 +1037,7 @@ struct _virDomainNetDef {
3e5111
     int trustGuestRxFilters; /* enum virTristateBool */
3e5111
     int linkstate;
3e5111
     unsigned int mtu;
3e5111
+    virNetDevCoalescePtr coalesce;
3e5111
 };
3e5111
 
3e5111
 /* Used for prefix of ifname of any network name generated dynamically
3e5111
diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
3e5111
index d31645fd1..53586878b 100644
3e5111
--- a/src/qemu/qemu_domain.c
3e5111
+++ b/src/qemu/qemu_domain.c
3e5111
@@ -3012,6 +3012,30 @@ qemuDomainDefValidate(const virDomainDef *def,
3e5111
 }
3e5111
 
3e5111
 
3e5111
+static bool
3e5111
+qemuDomainNetSupportsCoalesce(virDomainNetType type)
3e5111
+{
3e5111
+    switch (type) {
3e5111
+    case VIR_DOMAIN_NET_TYPE_NETWORK:
3e5111
+    case VIR_DOMAIN_NET_TYPE_BRIDGE:
3e5111
+        return true;
3e5111
+    case VIR_DOMAIN_NET_TYPE_VHOSTUSER:
3e5111
+    case VIR_DOMAIN_NET_TYPE_ETHERNET:
3e5111
+    case VIR_DOMAIN_NET_TYPE_DIRECT:
3e5111
+    case VIR_DOMAIN_NET_TYPE_HOSTDEV:
3e5111
+    case VIR_DOMAIN_NET_TYPE_USER:
3e5111
+    case VIR_DOMAIN_NET_TYPE_SERVER:
3e5111
+    case VIR_DOMAIN_NET_TYPE_CLIENT:
3e5111
+    case VIR_DOMAIN_NET_TYPE_MCAST:
3e5111
+    case VIR_DOMAIN_NET_TYPE_INTERNAL:
3e5111
+    case VIR_DOMAIN_NET_TYPE_UDP:
3e5111
+    case VIR_DOMAIN_NET_TYPE_LAST:
3e5111
+        break;
3e5111
+    }
3e5111
+    return false;
3e5111
+}
3e5111
+
3e5111
+
3e5111
 static int
3e5111
 qemuDomainDeviceDefValidate(const virDomainDeviceDef *dev,
3e5111
                             const virDomainDef *def ATTRIBUTE_UNUSED,
3e5111
@@ -3046,6 +3070,13 @@ qemuDomainDeviceDefValidate(const virDomainDeviceDef *dev,
3e5111
                            virDomainNetTypeToString(net->type));
3e5111
             goto cleanup;
3e5111
         }
3e5111
+
3e5111
+        if (net->coalesce && !qemuDomainNetSupportsCoalesce(net->type)) {
3e5111
+            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
3e5111
+                           _("coalesce settings on interface type %s are not supported"),
3e5111
+                           virDomainNetTypeToString(net->type));
3e5111
+            goto cleanup;
3e5111
+        }
3e5111
     }
3e5111
 
3e5111
     ret = 0;
3e5111
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-net-coalesce.xml b/tests/qemuxml2argvdata/qemuxml2argv-net-coalesce.xml
3e5111
new file mode 100644
3e5111
index 000000000..b51032442
3e5111
--- /dev/null
3e5111
+++ b/tests/qemuxml2argvdata/qemuxml2argv-net-coalesce.xml
3e5111
@@ -0,0 +1,68 @@
3e5111
+<domain type='qemu'>
3e5111
+  <name>test</name>
3e5111
+  <uuid>15d091de-0181-456b-9554-e4382dc1f1ab</uuid>
3e5111
+  <memory unit='KiB'>1048576</memory>
3e5111
+  <currentMemory unit='KiB'>1048576</currentMemory>
3e5111
+  <vcpu placement='static'>1</vcpu>
3e5111
+  <os>
3e5111
+    <type arch='x86_64' machine='pc-0.13'>hvm</type>
3e5111
+    <boot dev='cdrom'/>
3e5111
+    <boot dev='hd'/>
3e5111
+    <bootmenu enable='yes'/>
3e5111
+  </os>
3e5111
+  <clock offset='utc'/>
3e5111
+  <on_poweroff>destroy</on_poweroff>
3e5111
+  <on_reboot>restart</on_reboot>
3e5111
+  <on_crash>restart</on_crash>
3e5111
+  <devices>
3e5111
+    <emulator>/usr/bin/qemu-system-x86_64</emulator>
3e5111
+    <disk type='file' device='disk'>
3e5111
+      <driver name='qemu' type='qcow2' event_idx='on'/>
3e5111
+      <source file='/var/lib/libvirt/images/f14.img'/>
3e5111
+      <target dev='vda' bus='virtio'/>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
3e5111
+    </disk>
3e5111
+    <disk type='file' device='cdrom'>
3e5111
+      <driver name='qemu' type='raw'/>
3e5111
+      <source file='/var/lib/libvirt/Fedora-14-x86_64-Live-KDE.iso'/>
3e5111
+      <target dev='hdc' bus='ide'/>
3e5111
+      <readonly/>
3e5111
+      <address type='drive' controller='0' bus='1' target='0' unit='0'/>
3e5111
+    </disk>
3e5111
+    <controller type='usb' index='0'/>
3e5111
+    <controller type='virtio-serial' index='0'>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x06' function='0x0'/>
3e5111
+    </controller>
3e5111
+    <controller type='ide' index='0'/>
3e5111
+    <controller type='pci' index='0' model='pci-root'/>
3e5111
+    <interface type='network'>
3e5111
+      <source network='default'/>
3e5111
+      <mac address='52:54:00:e5:48:58'/>
3e5111
+      <model type='virtio'/>
3e5111
+      <coalesce>
3e5111
+        <rx>
3e5111
+          <frames max='7'/>
3e5111
+        </rx>
3e5111
+      </coalesce>
3e5111
+    </interface>
3e5111
+    <interface type='network'>
3e5111
+      <source network='default'/>
3e5111
+      <mac address='52:54:00:e5:48:59'/>
3e5111
+      <model type='virtio'/>
3e5111
+      <coalesce>
3e5111
+        <rx>
3e5111
+          <frames max='0'/>
3e5111
+        </rx>
3e5111
+      </coalesce>
3e5111
+    </interface>
3e5111
+    <serial type='pty'>
3e5111
+      <target port='0'/>
3e5111
+    </serial>
3e5111
+    <console type='pty'>
3e5111
+      <target type='serial' port='0'/>
3e5111
+    </console>
3e5111
+    <input type='mouse' bus='ps2'/>
3e5111
+    <input type='keyboard' bus='ps2'/>
3e5111
+    <memballoon model='virtio'/>
3e5111
+  </devices>
3e5111
+</domain>
3e5111
diff --git a/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-coalesce.xml b/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-coalesce.xml
3e5111
new file mode 100644
3e5111
index 000000000..fd5fdbece
3e5111
--- /dev/null
3e5111
+++ b/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-coalesce.xml
3e5111
@@ -0,0 +1,71 @@
3e5111
+<domain type='qemu'>
3e5111
+  <name>test</name>
3e5111
+  <uuid>15d091de-0181-456b-9554-e4382dc1f1ab</uuid>
3e5111
+  <memory unit='KiB'>1048576</memory>
3e5111
+  <currentMemory unit='KiB'>1048576</currentMemory>
3e5111
+  <vcpu placement='static'>1</vcpu>
3e5111
+  <os>
3e5111
+    <type arch='x86_64' machine='pc-0.13'>hvm</type>
3e5111
+    <boot dev='cdrom'/>
3e5111
+    <boot dev='hd'/>
3e5111
+    <bootmenu enable='yes'/>
3e5111
+  </os>
3e5111
+  <clock offset='utc'/>
3e5111
+  <on_poweroff>destroy</on_poweroff>
3e5111
+  <on_reboot>restart</on_reboot>
3e5111
+  <on_crash>restart</on_crash>
3e5111
+  <devices>
3e5111
+    <emulator>/usr/bin/qemu-system-x86_64</emulator>
3e5111
+    <disk type='file' device='disk'>
3e5111
+      <driver name='qemu' type='qcow2' event_idx='on'/>
3e5111
+      <source file='/var/lib/libvirt/images/f14.img'/>
3e5111
+      <target dev='vda' bus='virtio'/>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
3e5111
+    </disk>
3e5111
+    <disk type='file' device='cdrom'>
3e5111
+      <driver name='qemu' type='raw'/>
3e5111
+      <source file='/var/lib/libvirt/Fedora-14-x86_64-Live-KDE.iso'/>
3e5111
+      <target dev='hdc' bus='ide'/>
3e5111
+      <readonly/>
3e5111
+      <address type='drive' controller='0' bus='1' target='0' unit='0'/>
3e5111
+    </disk>
3e5111
+    <controller type='usb' index='0'>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x2'/>
3e5111
+    </controller>
3e5111
+    <controller type='virtio-serial' index='0'>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x06' function='0x0'/>
3e5111
+    </controller>
3e5111
+    <controller type='ide' index='0'>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x1'/>
3e5111
+    </controller>
3e5111
+    <controller type='pci' index='0' model='pci-root'/>
3e5111
+    <interface type='network'>
3e5111
+      <mac address='52:54:00:e5:48:58'/>
3e5111
+      <source network='default'/>
3e5111
+      <model type='virtio'/>
3e5111
+      <coalesce>
3e5111
+        <rx>
3e5111
+          <frames max='7'/>
3e5111
+        </rx>
3e5111
+      </coalesce>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
3e5111
+    </interface>
3e5111
+    <interface type='network'>
3e5111
+      <mac address='52:54:00:e5:48:59'/>
3e5111
+      <source network='default'/>
3e5111
+      <model type='virtio'/>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x05' function='0x0'/>
3e5111
+    </interface>
3e5111
+    <serial type='pty'>
3e5111
+      <target port='0'/>
3e5111
+    </serial>
3e5111
+    <console type='pty'>
3e5111
+      <target type='serial' port='0'/>
3e5111
+    </console>
3e5111
+    <input type='mouse' bus='ps2'/>
3e5111
+    <input type='keyboard' bus='ps2'/>
3e5111
+    <memballoon model='virtio'>
3e5111
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x07' function='0x0'/>
3e5111
+    </memballoon>
3e5111
+  </devices>
3e5111
+</domain>
3e5111
diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c
3e5111
index eae999dd6..26a2259fd 100644
3e5111
--- a/tests/qemuxml2xmltest.c
3e5111
+++ b/tests/qemuxml2xmltest.c
3e5111
@@ -532,6 +532,7 @@ mymain(void)
3e5111
     DO_TEST("net-bandwidth", NONE);
3e5111
     DO_TEST("net-bandwidth2", NONE);
3e5111
     DO_TEST("net-mtu", NONE);
3e5111
+    DO_TEST("net-coalesce", NONE);
3e5111
 
3e5111
     DO_TEST("serial-vc", NONE);
3e5111
     DO_TEST("serial-pty", NONE);
3e5111
-- 
3e5111
2.12.2
3e5111