]> xenbits.xensource.com Git - libvirt.git/commitdiff
bhyve: implement PCI address allocation
authorRoman Bogorodskiy <bogorodskiy@gmail.com>
Sat, 12 Apr 2014 19:37:53 +0000 (23:37 +0400)
committerRoman Bogorodskiy <bogorodskiy@gmail.com>
Fri, 13 Jun 2014 15:25:27 +0000 (19:25 +0400)
Automatically allocate PCI addresses for devices instead
of hardcoding them in the driver code. The current
allocation schema is to dedicate an entire slot for each devices.

Also, allow having arbitrary number of devices.

21 files changed:
po/POTFILES.in
src/Makefile.am
src/bhyve/bhyve_command.c
src/bhyve/bhyve_device.c [new file with mode: 0644]
src/bhyve/bhyve_device.h [new file with mode: 0644]
src/bhyve/bhyve_domain.c [new file with mode: 0644]
src/bhyve/bhyve_domain.h [new file with mode: 0644]
src/bhyve/bhyve_driver.c
src/bhyve/bhyve_process.c
tests/bhyvexml2argvdata/bhyvexml2argv-acpiapic.args
tests/bhyvexml2argvdata/bhyvexml2argv-acpiapic.xml
tests/bhyvexml2argvdata/bhyvexml2argv-base.args
tests/bhyvexml2argvdata/bhyvexml2argv-base.xml
tests/bhyvexml2argvdata/bhyvexml2argv-console.args
tests/bhyvexml2argvdata/bhyvexml2argv-console.xml
tests/bhyvexml2argvdata/bhyvexml2argv-disk-virtio.args
tests/bhyvexml2argvdata/bhyvexml2argv-disk-virtio.xml
tests/bhyvexml2argvdata/bhyvexml2argv-macaddr.args
tests/bhyvexml2argvdata/bhyvexml2argv-macaddr.xml
tests/bhyvexml2argvdata/bhyvexml2argv-serial.args
tests/bhyvexml2argvdata/bhyvexml2argv-serial.xml

index d01116bd03954e62be5e10fd3c317b61c66cb240..31a8381748cffbff5d41683a15cad21e7759fdae 100644 (file)
@@ -9,6 +9,7 @@ gnulib/lib/regcomp.c
 src/access/viraccessdriverpolkit.c
 src/access/viraccessmanager.c
 src/bhyve/bhyve_command.c
+src/bhyve/bhyve_device.c
 src/bhyve/bhyve_driver.c
 src/bhyve/bhyve_process.c
 src/conf/capabilities.c
index a72c284f38c2eb5db0a224f3c4419a06fe8d756e..2b9ac61823ec2d3d1c3615d429c4a865330615f2 100644 (file)
@@ -789,6 +789,10 @@ BHYVE_DRIVER_SOURCES =                                             \
                bhyve/bhyve_capabilities.h                      \
                bhyve/bhyve_command.c                           \
                bhyve/bhyve_command.h                           \
+               bhyve/bhyve_device.c                            \
+               bhyve/bhyve_device.h                            \
+               bhyve/bhyve_domain.c                            \
+               bhyve/bhyve_domain.h                            \
                bhyve/bhyve_driver.h                            \
                bhyve/bhyve_driver.c                            \
                bhyve/bhyve_process.c                           \
index 91a873162c0b255c107d8c308455b3be621b14e4..d3b3f69998fe2ae04003c9433e2ea6f1a2b3908b 100644 (file)
 VIR_LOG_INIT("bhyve.bhyve_command");
 
 static int
-bhyveBuildNetArgStr(const virDomainDef *def, virCommandPtr cmd, bool dryRun)
+bhyveBuildNetArgStr(const virDomainDef *def,
+                    virDomainNetDefPtr net,
+                    virCommandPtr cmd,
+                    bool dryRun)
 {
-    virDomainNetDefPtr net = NULL;
-    char *brname = NULL;
+    char macaddr[VIR_MAC_STRING_BUFLEN];
     char *realifname = NULL;
     int *tapfd = NULL;
-    char macaddr[VIR_MAC_STRING_BUFLEN];
+    char *brname = NULL;
+    int actualType = virDomainNetGetActualType(net);
 
-    if (def->nnets != 1) {
-        virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
-                       _("domain should have one and only one net defined"));
+    if (actualType == VIR_DOMAIN_NET_TYPE_BRIDGE) {
+        if (VIR_STRDUP(brname, virDomainNetGetActualBridgeName(net)) < 0)
+            return -1;
+    } else {
+        virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
+                       _("Network type %d is not supported"),
+                       virDomainNetGetActualType(net));
         return -1;
     }
 
-    net = def->nets[0];
-
-    if (net) {
-        int actualType = virDomainNetGetActualType(net);
-
-        if (actualType == VIR_DOMAIN_NET_TYPE_BRIDGE) {
-            if (VIR_STRDUP(brname, virDomainNetGetActualBridgeName(net)) < 0)
-                return -1;
-        } else {
-            virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
-                           _("Network type %d is not supported"),
-                           virDomainNetGetActualType(net));
+    if (!net->ifname ||
+        STRPREFIX(net->ifname, VIR_NET_GENERATED_PREFIX) ||
+        strchr(net->ifname, '%')) {
+        VIR_FREE(net->ifname);
+        if (VIR_STRDUP(net->ifname, VIR_NET_GENERATED_PREFIX "%d") < 0) {
+            VIR_FREE(brname);
             return -1;
         }
+    }
 
-        if (!net->ifname ||
-            STRPREFIX(net->ifname, VIR_NET_GENERATED_PREFIX) ||
-            strchr(net->ifname, '%')) {
+    if (!dryRun) {
+        if (virNetDevTapCreateInBridgePort(brname, &net->ifname, &net->mac,
+                                           def->uuid, tapfd, 1,
+                                           virDomainNetGetActualVirtPortProfile(net),
+                                           virDomainNetGetActualVlan(net),
+                                           VIR_NETDEV_TAP_CREATE_IFUP | VIR_NETDEV_TAP_CREATE_PERSIST) < 0) {
             VIR_FREE(net->ifname);
-            if (VIR_STRDUP(net->ifname, VIR_NET_GENERATED_PREFIX "%d") < 0) {
-                VIR_FREE(brname);
-                return -1;
-            }
+            VIR_FREE(brname);
+            return -1;
         }
 
-        if (!dryRun)
-            if (virNetDevTapCreateInBridgePort(brname, &net->ifname, &net->mac,
-                                               def->uuid, tapfd, 1,
-                                               virDomainNetGetActualVirtPortProfile(net),
-                                               virDomainNetGetActualVlan(net),
-                                               VIR_NETDEV_TAP_CREATE_IFUP | VIR_NETDEV_TAP_CREATE_PERSIST) < 0) {
-                VIR_FREE(net->ifname);
-                VIR_FREE(brname);
-                return -1;
-            }
-    }
-
-    if (!dryRun) {
         realifname = virNetDevTapGetRealDeviceName(net->ifname);
 
         if (realifname == NULL) {
@@ -105,6 +95,7 @@ bhyveBuildNetArgStr(const virDomainDef *def, virCommandPtr cmd, bool dryRun)
          * name
          */
         if (virNetDevSetOnline(net->ifname, true) != 0) {
+            VIR_FREE(realifname);
             VIR_FREE(net->ifname);
             VIR_FREE(brname);
             return -1;
@@ -116,8 +107,10 @@ bhyveBuildNetArgStr(const virDomainDef *def, virCommandPtr cmd, bool dryRun)
 
 
     virCommandAddArg(cmd, "-s");
-    virCommandAddArgFormat(cmd, "1:0,virtio-net,%s,mac=%s",
+    virCommandAddArgFormat(cmd, "%d:0,virtio-net,%s,mac=%s",
+                           net->info.addr.pci.slot,
                            realifname, virMacAddrFormat(&net->mac, macaddr));
+    VIR_FREE(realifname);
 
     return 0;
 }
@@ -146,7 +139,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommandPtr cmd)
         return -1;
     }
 
-    virCommandAddArgList(cmd, "-s", "31,lpc", NULL);
+    virCommandAddArgList(cmd, "-s", "1,lpc", NULL);
     virCommandAddArg(cmd, "-l");
     virCommandAddArgFormat(cmd, "com%d,%s",
                            chr->target.port + 1, chr->source.data.file.path);
@@ -155,19 +148,12 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommandPtr cmd)
 }
 
 static int
-bhyveBuildDiskArgStr(const virDomainDef *def, virCommandPtr cmd)
+bhyveBuildDiskArgStr(const virDomainDef *def ATTRIBUTE_UNUSED,
+                     virDomainDiskDefPtr disk,
+                     virCommandPtr cmd)
 {
-    virDomainDiskDefPtr disk;
     const char *bus_type;
 
-    if (def->ndisks != 1) {
-        virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
-                       _("domain should have one and only one disk defined"));
-        return -1;
-    }
-
-    disk = def->disks[0];
-
     switch (disk->bus) {
     case VIR_DOMAIN_DISK_BUS_SATA:
         bus_type = "ahci-hd";
@@ -194,7 +180,8 @@ bhyveBuildDiskArgStr(const virDomainDef *def, virCommandPtr cmd)
     }
 
     virCommandAddArg(cmd, "-s");
-    virCommandAddArgFormat(cmd, "2:0,%s,%s", bus_type,
+    virCommandAddArgFormat(cmd, "%d:0,%s,%s",
+                           disk->info.addr.pci.slot, bus_type,
                            virDomainDiskGetSource(disk));
 
     return 0;
@@ -212,6 +199,8 @@ virBhyveProcessBuildBhyveCmd(bhyveConnPtr driver ATTRIBUTE_UNUSED,
      *            -S 31,uart,stdio \
      *            vm0
      */
+    size_t i;
+
     virCommandPtr cmd = virCommandNew(BHYVE);
 
     /* CPUs */
@@ -245,10 +234,17 @@ virBhyveProcessBuildBhyveCmd(bhyveConnPtr driver ATTRIBUTE_UNUSED,
 
     virCommandAddArgList(cmd, "-s", "0:0,hostbridge", NULL);
     /* Devices */
-    if (bhyveBuildNetArgStr(def, cmd, dryRun) < 0)
-        goto error;
-    if (bhyveBuildDiskArgStr(def, cmd) < 0)
-        goto error;
+    for (i = 0; i < def->nnets; i++) {
+        virDomainNetDefPtr net = def->nets[i];
+        if (bhyveBuildNetArgStr(def, net, cmd, dryRun) < 0)
+            goto error;
+    }
+    for (i = 0; i < def->ndisks; i++) {
+        virDomainDiskDefPtr disk = def->disks[i];
+
+        if (bhyveBuildDiskArgStr(def, disk, cmd) < 0)
+            goto error;
+    }
     if (bhyveBuildConsoleArgStr(def, cmd) < 0)
         goto error;
     virCommandAddArg(cmd, def->name);
@@ -279,9 +275,9 @@ virBhyveProcessBuildLoadCmd(bhyveConnPtr driver ATTRIBUTE_UNUSED,
     virCommandPtr cmd;
     virDomainDiskDefPtr disk;
 
-    if (def->ndisks != 1) {
+    if (def->ndisks < 1) {
         virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
-                       _("domain should have one and only one disk defined"));
+                       _("domain should have at least one disk defined"));
         return NULL;
     }
 
diff --git a/src/bhyve/bhyve_device.c b/src/bhyve/bhyve_device.c
new file mode 100644 (file)
index 0000000..fa266de
--- /dev/null
@@ -0,0 +1,174 @@
+/*
+ * bhyve_device.c: bhyve device management
+ *
+ * Copyright (C) 2014 Roman Bogorodskiy
+ *
+ * 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * 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/>.
+ *
+ * Author: Roman Bogorodskiy
+ */
+
+#include <config.h>
+
+#include "bhyve_device.h"
+#include "domain_addr.h"
+#include "viralloc.h"
+#include "virlog.h"
+#include "virstring.h"
+
+#define VIR_FROM_THIS VIR_FROM_BHYVE
+
+VIR_LOG_INIT("bhyve.bhyve_device");
+
+static int
+bhyveCollectPCIAddress(virDomainDefPtr def ATTRIBUTE_UNUSED,
+                       virDomainDeviceDefPtr device ATTRIBUTE_UNUSED,
+                       virDomainDeviceInfoPtr info,
+                       void *opaque)
+{
+    int ret = -1;
+    virDomainPCIAddressSetPtr addrs = opaque;
+    virDevicePCIAddressPtr addr = &info->addr.pci;
+
+    if (addr->domain == 0 && addr->bus == 0) {
+        if (addr->slot == 0) {
+            return 0;
+        } else if (addr->slot == 1) {
+            virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+                           _("PCI bus 0 slot 1 is reserved for the implicit "
+                             "LPC PCI-ISA bridge"));
+            return -1;
+        }
+    }
+
+    if (virDomainPCIAddressReserveSlot(addrs, addr, VIR_PCI_CONNECT_TYPE_PCI) < 0)
+        goto cleanup;
+
+    ret = 0;
+ cleanup:
+    return ret;
+}
+
+virDomainPCIAddressSetPtr
+bhyveDomainPCIAddressSetCreate(virDomainDefPtr def ATTRIBUTE_UNUSED, unsigned int nbuses)
+{
+    virDomainPCIAddressSetPtr addrs;
+
+    if ((addrs = virDomainPCIAddressSetAlloc(nbuses)) == NULL)
+        return NULL;
+
+    if (virDomainPCIAddressBusSetModel(&addrs->buses[0],
+                                       VIR_DOMAIN_CONTROLLER_MODEL_PCI_ROOT) < 0)
+        goto error;
+
+    if (virDomainDeviceInfoIterate(def, bhyveCollectPCIAddress, addrs) < 0)
+        goto error;
+
+    return addrs;
+
+ error:
+    virDomainPCIAddressSetFree(addrs);
+    return NULL;
+}
+
+static int
+bhyveAssignDevicePCISlots(virDomainDefPtr def,
+                          virDomainPCIAddressSetPtr addrs)
+{
+    size_t i;
+    virDevicePCIAddress lpc_addr;
+
+    /* explicitly reserve slot 1 for LPC-ISA bridge */
+    memset(&lpc_addr, 0, sizeof(lpc_addr));
+    lpc_addr.slot = 0x1;
+
+    if (virDomainPCIAddressReserveSlot(addrs, &lpc_addr, VIR_PCI_CONNECT_TYPE_PCI) < 0)
+        goto error;
+
+    for (i = 0; i < def->nnets; i++) {
+        if (def->nets[i]->info.type != VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE)
+            continue;
+        if (virDomainPCIAddressReserveNextSlot(addrs,
+                                               &def->nets[i]->info,
+                                               VIR_PCI_CONNECT_TYPE_PCI) < 0)
+            goto error;
+    }
+
+    for (i = 0; i < def->ndisks; i++) {
+        if (def->disks[i]->info.type != VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE &&
+            def->disks[i]->info.addr.pci.slot != 0)
+            continue;
+        if (virDomainPCIAddressReserveNextSlot(addrs,
+                                               &def->disks[i]->info,
+                                               VIR_PCI_CONNECT_TYPE_PCI) < 0)
+            goto error;
+    }
+
+    for (i = 0; i < def->ncontrollers; i++) {
+        if (def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_PCI) {
+            if (def->controllers[i]->info.type != VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE)
+                continue;
+            if (def->controllers[i]->model == VIR_DOMAIN_CONTROLLER_MODEL_PCI_ROOT)
+                continue;
+
+            if (virDomainPCIAddressReserveNextSlot(addrs,
+                                                   &def->controllers[i]->info,
+                                                   VIR_PCI_CONNECT_TYPE_PCI) < 0)
+                goto error;
+        }
+
+    }
+
+    return 0;
+
+ error:
+    return -1;
+}
+
+int bhyveDomainAssignPCIAddresses(virDomainDefPtr def,
+                                  virDomainObjPtr obj)
+{
+    virDomainPCIAddressSetPtr addrs = NULL;
+    bhyveDomainObjPrivatePtr priv = NULL;
+
+    int ret = -1;
+
+    if (!(addrs = bhyveDomainPCIAddressSetCreate(def, 1)))
+        goto cleanup;
+
+    if (bhyveAssignDevicePCISlots(def, addrs) < 0)
+        goto cleanup;
+
+    if (obj && obj->privateData) {
+        priv = obj->privateData;
+        if (addrs) {
+            virDomainPCIAddressSetFree(priv->pciaddrs);
+            priv->persistentAddrs = 1;
+            priv->pciaddrs = addrs;
+        } else {
+            priv->persistentAddrs = 0;
+        }
+    }
+
+    ret = 0;
+
+ cleanup:
+    return ret;
+}
+
+int bhyveDomainAssignAddresses(virDomainDefPtr def, virDomainObjPtr obj)
+{
+    return bhyveDomainAssignPCIAddresses(def, obj);
+}
diff --git a/src/bhyve/bhyve_device.h b/src/bhyve/bhyve_device.h
new file mode 100644 (file)
index 0000000..1144f51
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * bhyve_device.h: bhyve device management headers
+ *
+ * Copyright (C) 2014 Roman Bogorodskiy
+ *
+ * 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * 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/>.
+ *
+ * Author: Roman Bogorodskiy
+ */
+
+#ifndef __BHYVE_DEVICE_H__
+# define __BHYVE_DEVICE_H__
+
+# include "domain_conf.h"
+# include "virpci.h"
+# include "bhyve_domain.h"
+
+int bhyveDomainAssignPCIAddresses(virDomainDefPtr def, virDomainObjPtr obj);
+
+virDomainPCIAddressSetPtr bhyveDomainPCIAddressSetCreate(virDomainDefPtr def,
+                                                         unsigned int nbuses);
+
+int bhyveDomainAssignAddresses(virDomainDefPtr def, virDomainObjPtr obj)
+    ATTRIBUTE_NONNULL(1);
+
+#endif /* __BHYVE_DEVICE_H__ */
diff --git a/src/bhyve/bhyve_domain.c b/src/bhyve/bhyve_domain.c
new file mode 100644 (file)
index 0000000..7c7bec3
--- /dev/null
@@ -0,0 +1,75 @@
+/*
+ * bhyve_domain.c: bhyve domain private state
+ *
+ * Copyright (C) 2014 Roman Bogorodskiy
+ *
+ * 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * 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/>.
+ *
+ * Author: Roman Bogorodskiy
+ */
+
+#include <config.h>
+
+#include "bhyve_device.h"
+#include "bhyve_domain.h"
+#include "viralloc.h"
+#include "virlog.h"
+
+#define VIR_FROM_THIS VIR_FROM_BHYVE
+
+VIR_LOG_INIT("bhyve.bhyve_domain");
+
+static void *
+bhyveDomainObjPrivateAlloc(void)
+{
+    bhyveDomainObjPrivatePtr priv;
+
+    if (VIR_ALLOC(priv) < 0)
+        return NULL;
+
+    return priv;
+}
+
+static void
+bhyveDomainObjPrivateFree(void *data)
+{
+    bhyveDomainObjPrivatePtr priv = data;
+
+    virDomainPCIAddressSetFree(priv->pciaddrs);
+
+    VIR_FREE(priv);
+}
+
+virDomainXMLPrivateDataCallbacks virBhyveDriverPrivateDataCallbacks = {
+    .alloc = bhyveDomainObjPrivateAlloc,
+    .free = bhyveDomainObjPrivateFree,
+};
+
+static int
+bhyveDomainDefPostParse(virDomainDefPtr def,
+                        virCapsPtr caps ATTRIBUTE_UNUSED,
+                        void *opaque ATTRIBUTE_UNUSED)
+{
+    /* Add an implicit PCI root controller */
+    if (virDomainDefMaybeAddController(def, VIR_DOMAIN_CONTROLLER_TYPE_PCI, 0,
+                                       VIR_DOMAIN_CONTROLLER_MODEL_PCI_ROOT) < 0)
+        return -1;
+
+    return 0;
+}
+
+virDomainDefParserConfig virBhyveDriverDomainDefParserConfig = {
+    .domainPostParseCallback = bhyveDomainDefPostParse,
+};
diff --git a/src/bhyve/bhyve_domain.h b/src/bhyve/bhyve_domain.h
new file mode 100644 (file)
index 0000000..b8ef22a
--- /dev/null
@@ -0,0 +1,39 @@
+/*
+ * bhyve_domain.h: bhyve domain private state headers
+ *
+ * Copyright (C) 2014 Roman Bogorodskiy
+ *
+ * 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; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * 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/>.
+ *
+ * Author: Roman Bogorodskiy
+ */
+
+#ifndef __BHYVE_DOMAIN_H__
+# define __BHYVE_DOMAIN_H__
+
+# include "domain_addr.h"
+# include "domain_conf.h"
+
+typedef struct _bhyveDomainObjPrivate bhyveDomainObjPrivate;
+typedef bhyveDomainObjPrivate *bhyveDomainObjPrivatePtr;
+struct _bhyveDomainObjPrivate {
+    virDomainPCIAddressSetPtr pciaddrs;
+    bool persistentAddrs;
+};
+
+extern virDomainXMLPrivateDataCallbacks virBhyveDriverPrivateDataCallbacks;
+extern virDomainDefParserConfig virBhyveDriverDomainDefParserConfig;
+
+#endif /* __BHYVE_DOMAIN_H__ */
index 55c6a7ffbe40cb46d8da9cf5368f521b109fe2d9..89f73ff3327b980da152f4baeed072a7140eaf0c 100644 (file)
 #include "viraccessapicheck.h"
 #include "nodeinfo.h"
 
+#include "bhyve_device.h"
 #include "bhyve_driver.h"
 #include "bhyve_command.h"
+#include "bhyve_domain.h"
 #include "bhyve_process.h"
 #include "bhyve_utils.h"
 #include "bhyve_capabilities.h"
@@ -509,6 +511,9 @@ bhyveDomainDefineXML(virConnectPtr conn, const char *xml)
     if (virDomainDefineXMLEnsureACL(conn, def) < 0)
         goto cleanup;
 
+    if (bhyveDomainAssignAddresses(def, NULL) < 0)
+        goto cleanup;
+
     if (!(vm = virDomainObjListAdd(privconn->domains, def,
                                    privconn->xmlopt,
                                    0, &oldDef)))
@@ -685,6 +690,9 @@ bhyveConnectDomainXMLToNative(virConnectPtr conn,
                                   VIR_DOMAIN_XML_INACTIVE)))
         goto cleanup;
 
+    if (bhyveDomainAssignAddresses(def, NULL) < 0)
+        goto cleanup;
+
     if (!(loadcmd = virBhyveProcessBuildLoadCmd(privconn, def)))
         goto cleanup;
 
@@ -897,6 +905,9 @@ bhyveDomainCreateXML(virConnectPtr conn,
     if (virDomainCreateXMLEnsureACL(conn, def) < 0)
         goto cleanup;
 
+    if (bhyveDomainAssignAddresses(def, NULL) < 0)
+        goto cleanup;
+
     if (!(vm = virDomainObjListAdd(privconn->domains, def,
                                    privconn->xmlopt,
                                    VIR_DOMAIN_OBJ_LIST_ADD_CHECK_LIVE, NULL)))
@@ -1160,7 +1171,9 @@ bhyveStateInitialize(bool priveleged ATTRIBUTE_UNUSED,
     if (!(bhyve_driver->caps = virBhyveCapsBuild()))
         goto cleanup;
 
-    if (!(bhyve_driver->xmlopt = virDomainXMLOptionNew(NULL, NULL, NULL)))
+    if (!(bhyve_driver->xmlopt = virDomainXMLOptionNew(&virBhyveDriverDomainDefParserConfig,
+                                                       &virBhyveDriverPrivateDataCallbacks,
+                                                       NULL)))
         goto cleanup;
 
     if (!(bhyve_driver->domains = virDomainObjListNew()))
index 9f02a4910aa886e4ed69ed3cfed2482245395129..a5ad68d33e08877477d459e7fe071aa9785ed74e 100644 (file)
@@ -31,6 +31,7 @@
 #include <net/if.h>
 #include <net/if_tap.h>
 
+#include "bhyve_device.h"
 #include "bhyve_process.h"
 #include "bhyve_command.h"
 #include "datatypes.h"
@@ -130,6 +131,9 @@ virBhyveProcessStart(virConnectPtr conn,
         goto cleanup;
     }
 
+    if (bhyveDomainAssignAddresses(vm->def, NULL) < 0)
+        goto cleanup;
+
     /* Call bhyve to start the VM */
     if (!(cmd = virBhyveProcessBuildBhyveCmd(driver,
                                              vm->def,
index 60a56b9805898107da5615e447884719c721f451..79f8e88613df4a31bcc88a86d1cefbd14525eb39 100644 (file)
@@ -1,3 +1,3 @@
 /usr/sbin/bhyve -c 1 -m 214 -A -I -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
 -s 2:0,ahci-hd,/tmp/freebsd.img bhyve
index b429fefe162fc2415fd19bb43b89f8d40e1a7587..2be970e05db8d67a34b06efa9cb8575871db3e31 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='hda' bus='sata'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
   </devices>
 </domain>
index 9d4faa52dd8556301a4bc3766ecfcd37fb0e34c6..4122e627b0abc8223052985969bf688e4058fb80 100644 (file)
@@ -1,3 +1,3 @@
 /usr/sbin/bhyve -c 1 -m 214 -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
 -s 2:0,ahci-hd,/tmp/freebsd.img bhyve
index 8c96f77730d47029912790c314f1fd3ec1f8c42f..3d2337520bc0afcc32ea11cbcc1428715c33196b 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='hda' bus='sata'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
   </devices>
 </domain>
index 1e09fb410d26c3cd664dfbeccee2a1376da66f0b..df502902142b64c5d7a8afea5cd9ea7b3634a215 100644 (file)
@@ -1,4 +1,4 @@
 /usr/sbin/bhyve -c 1 -m 214 -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
 -s 2:0,ahci-hd,/tmp/freebsd.img \
--s 31,lpc -l com1,/dev/nmdm0A bhyve
+-s 1,lpc -l com1,/dev/nmdm0A bhyve
index 64073f081eb9d51d91236c0d84af779bd5ba5023..35206b521629ea34f80e3ec09875724bd7113167 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='hda' bus='sata'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
     <console type='nmdm'>
       <source master='/dev/nmdm0A' slave='/dev/nmdm0B'/>
index 54ad2b89debc689b1ad0e125ed884422b6b93d06..1638d540b42b21cc2a72abe1fe6d1a9cc1b1daa9 100644 (file)
@@ -1,3 +1,3 @@
 /usr/sbin/bhyve -c 1 -m 214 -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
 -s 2:0,virtio-blk,/tmp/freebsd.img bhyve
index 8cfb51811f61e42078d06fb4d58d2f243beae519..773d55e611a908805b2fa73870178a6e77303a5e 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='vda' bus='virtio'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
   </devices>
 </domain>
index 1a06abddf197f77128bd0fe345daaec7d2dab351..f91486502e4a0bfb8e17bfcfad8654ca874af530 100644 (file)
@@ -1,3 +1,3 @@
 /usr/sbin/bhyve -c 1 -m 214 -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:22:ee:11 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:22:ee:11 \
 -s 2:0,ahci-hd,/tmp/freebsd.img bhyve
index 41a42b00147cf5ed07a7268bc24ae2ccaab68e2c..b262eb709835cdc00400af23ba29bfc1f11a9c3d 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='hda' bus='sata'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <mac address="52:54:00:22:ee:11"/>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
   </devices>
 </domain>
index 1e09fb410d26c3cd664dfbeccee2a1376da66f0b..df502902142b64c5d7a8afea5cd9ea7b3634a215 100644 (file)
@@ -1,4 +1,4 @@
 /usr/sbin/bhyve -c 1 -m 214 -H -P -s 0:0,hostbridge \
--s 1:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
+-s 3:0,virtio-net,faketapdev,mac=52:54:00:00:00:00 \
 -s 2:0,ahci-hd,/tmp/freebsd.img \
--s 31,lpc -l com1,/dev/nmdm0A bhyve
+-s 1,lpc -l com1,/dev/nmdm0A bhyve
index bfecbb91ee4f0bcad0978b1c3e02b4e02f9de0bd..cd4f25b6e2cbf334213f4627cd0d3a171ed422fc 100644 (file)
       <driver name='file' type='raw'/>
       <source file='/tmp/freebsd.img'/>
       <target dev='hda' bus='sata'/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
     </disk>
     <interface type='bridge'>
       <model type='virtio'/>
       <source bridge="virbr0"/>
+      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
     </interface>
     <serial type='nmdm'>
       <source master='/dev/nmdm0A' slave='/dev/nmdm0B'/>