[libvirt] [PATCH v3] qemu: set default vhost-user ifname
John Ferlan
jferlan at redhat.com
Wed Jan 18 13:21:00 UTC 2017
I think I half assumed this would have been pushed already, but seeing
as it wasn't...
On 12/22/2016 04:45 AM, Michal Privoznik wrote:
> Based on work of Mehdi Abaakouk <sileht at sileht.net>.
>
> When parsing vhost-user interface XML and no ifname is found we
> can try to fill it in in post parse callback. The way this works
> is we try to make up interface name from given socket path and
> then ask openvswitch wether it knows the interface.
s/wether/whether
>
> Signed-off-by: Michal Privoznik <mprivozn at redhat.com>
> ---
>
> diff to v2:
> - All the review points from v2 worked in
>
> src/libvirt_private.syms | 1 +
> src/qemu/qemu_domain.c | 21 +++++---
> src/util/virnetdevopenvswitch.c | 58 ++++++++++++++++++++++
> src/util/virnetdevopenvswitch.h | 4 ++
> tests/Makefile.am | 7 +++
> tests/qemuxml2argvmock.c | 8 +++
> tests/qemuxml2xmlmock.c | 33 ++++++++++++
> .../qemuxml2xmlout-net-vhostuser.xml | 2 +
> tests/qemuxml2xmltest.c | 2 +-
> 9 files changed, 129 insertions(+), 7 deletions(-)
> create mode 100644 tests/qemuxml2xmlmock.c
>
> diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
> index 2d23e462d..9e4e8f83f 100644
> --- a/src/libvirt_private.syms
> +++ b/src/libvirt_private.syms
> @@ -2057,6 +2057,7 @@ virNetDevMidonetUnbindPort;
> # util/virnetdevopenvswitch.h
> virNetDevOpenvswitchAddPort;
> virNetDevOpenvswitchGetMigrateData;
> +virNetDevOpenvswitchGetVhostuserIfname;
> virNetDevOpenvswitchInterfaceStats;
> virNetDevOpenvswitchRemovePort;
> virNetDevOpenvswitchSetMigrateData;
> diff --git a/src/qemu/qemu_domain.c b/src/qemu/qemu_domain.c
> index acfa69589..eed5745b6 100644
> --- a/src/qemu/qemu_domain.c
> +++ b/src/qemu/qemu_domain.c
> @@ -41,6 +41,7 @@
> #include "domain_addr.h"
> #include "domain_event.h"
> #include "virtime.h"
> +#include "virnetdevopenvswitch.h"
> #include "virstoragefile.h"
> #include "virstring.h"
> #include "virthreadjob.h"
> @@ -3028,12 +3029,20 @@ qemuDomainDeviceDefPostParse(virDomainDeviceDefPtr dev,
> def->emulator);
> }
>
> - if (dev->type == VIR_DOMAIN_DEVICE_NET &&
> - dev->data.net->type != VIR_DOMAIN_NET_TYPE_HOSTDEV &&
> - !dev->data.net->model) {
> - if (VIR_STRDUP(dev->data.net->model,
> - qemuDomainDefaultNetModel(def, qemuCaps)) < 0)
> - goto cleanup;
> + if (dev->type == VIR_DOMAIN_DEVICE_NET) {
> + if (dev->data.net->type != VIR_DOMAIN_NET_TYPE_HOSTDEV &&
> + !dev->data.net->model) {
> + if (VIR_STRDUP(dev->data.net->model,
> + qemuDomainDefaultNetModel(def, qemuCaps)) < 0)
> + goto cleanup;
> + }
> + if (dev->data.net->type == VIR_DOMAIN_NET_TYPE_VHOSTUSER &&
> + !dev->data.net->ifname) {
> + if (virNetDevOpenvswitchGetVhostuserIfname(
> + dev->data.net->data.vhostuser->data.nix.path,
> + &dev->data.net->ifname) < 0)
> + goto cleanup;
> + }
> }
>
> /* set default disk types and drivers */
> diff --git a/src/util/virnetdevopenvswitch.c b/src/util/virnetdevopenvswitch.c
> index f003b3b13..d93653317 100644
> --- a/src/util/virnetdevopenvswitch.c
> +++ b/src/util/virnetdevopenvswitch.c
> @@ -377,3 +377,61 @@ virNetDevOpenvswitchInterfaceStats(const char *ifname,
> virCommandFree(cmd);
> return ret;
> }
> +
> +/**
> + * virNetDevOpenvswitchVhostuserGetIfname:
> + * @path: the path of the unix socket
> + * @ifname: the retrieved name of the interface
> + *
> + * Retreives the ovs ifname from vhostuser unix socket path.
> + *
> + * Returns: 1 if interface is an openvswitch interface,
> + * 0 if it is not, but no other error occurred,
> + * -1 otherwise.
> + */
> +int
> +virNetDevOpenvswitchGetVhostuserIfname(const char *path,
> + char **ifname)
> +{
> + virCommandPtr cmd = NULL;
> + char *tmpIfname = NULL;
> + char **tokens = NULL;
> + size_t ntokens = 0;
> + int status;
> + int ret = -1;
> +
> + /* Openvswitch vhostuser path are hardcoded to
> + * /<runstatedir>/openvswitch/<ifname>
> + * for example: /var/run/openvswitch/dpdkvhostuser0
> + *
> + * so we pick the filename and check it's a openvswitch interface
> + */
> + if ((tokens = virStringSplitCount(path, "/", 0, &ntokens))) {
Seems like a lot of extra work just to pull off the last element of the
path. Why not something using strrchr?
ACK in principal - I think you can decide whether strrchr would be more
useful since it seems you can guarantee that @path has at least a '/' in
it... Probably wouldn't need to strdup below either...
John
> + if (VIR_STRDUP(tmpIfname, tokens[ntokens - 1]) < 0)
> + goto cleanup;
> + }
> +
> + if (!tmpIfname) {
> + ret = 0;
> + goto cleanup;
> + }
> +
> + cmd = virCommandNewArgList(OVSVSCTL, "--timeout=5", "get", "Interface",
> + tmpIfname, "name", NULL);
> + if (virCommandRun(cmd, &status) < 0 ||
> + status) {
> + /* it's not a openvswitch vhostuser interface. */
> + ret = 0;
> + goto cleanup;
> + }
> +
> + *ifname = tmpIfname;
> + tmpIfname = NULL;
> + ret = 1;
> +
> + cleanup:
> + virStringListFreeCount(tokens, ntokens);
> + virCommandFree(cmd);
> + VIR_FREE(tmpIfname);
> + return ret;
> +}
> diff --git a/src/util/virnetdevopenvswitch.h b/src/util/virnetdevopenvswitch.h
> index 0f9e1dfa6..8f5faf14e 100644
> --- a/src/util/virnetdevopenvswitch.h
> +++ b/src/util/virnetdevopenvswitch.h
> @@ -52,4 +52,8 @@ int virNetDevOpenvswitchInterfaceStats(const char *ifname,
> virDomainInterfaceStatsPtr stats)
> ATTRIBUTE_NONNULL(1) ATTRIBUTE_RETURN_CHECK;
>
> +int virNetDevOpenvswitchGetVhostuserIfname(const char *path,
> + char **ifname)
> + ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK;
> +
> #endif /* __VIR_NETDEV_OPENVSWITCH_H__ */
> diff --git a/tests/Makefile.am b/tests/Makefile.am
> index ecd04e895..c8584fea6 100644
> --- a/tests/Makefile.am
> +++ b/tests/Makefile.am
> @@ -414,6 +414,7 @@ if WITH_QEMU
> test_libraries += libqemumonitortestutils.la \
> libqemutestdriver.la \
> qemuxml2argvmock.la \
> + qemuxml2xmlmock.la \
> qemucaps2xmlmock.la \
> qemucapsprobemock.la \
> $(NULL)
> @@ -571,6 +572,12 @@ qemuxml2argvmock_la_CFLAGS = $(AM_CFLAGS)
> qemuxml2argvmock_la_LDFLAGS = $(MOCKLIBS_LDFLAGS)
> qemuxml2argvmock_la_LIBADD = $(MOCKLIBS_LIBS)
>
> +qemuxml2xmlmock_la_SOURCES = \
> + qemuxml2xmlmock.c
> +qemuxml2xmlmock_la_CFLAGS = $(AM_CFLAGS)
> +qemuxml2xmlmock_la_LDFLAGS = $(MOCKLIBS_LDFLAGS)
> +qemuxml2xmlmock_la_LIBADD = $(MOCKLIBS_LIBS)
> +
> qemuxml2xmltest_SOURCES = \
> qemuxml2xmltest.c testutilsqemu.c testutilsqemu.h \
> testutils.c testutils.h
> diff --git a/tests/qemuxml2argvmock.c b/tests/qemuxml2argvmock.c
> index c501b59ac..177b24e0a 100644
> --- a/tests/qemuxml2argvmock.c
> +++ b/tests/qemuxml2argvmock.c
> @@ -28,6 +28,7 @@
> #include "virnetdev.h"
> #include "virnetdevip.h"
> #include "virnetdevtap.h"
> +#include "virnetdevopenvswitch.h"
> #include "virnuma.h"
> #include "virrandom.h"
> #include "virscsi.h"
> @@ -180,3 +181,10 @@ virCryptoGenerateRandom(size_t nbytes)
>
> return buf;
> }
> +
> +int
> +virNetDevOpenvswitchGetVhostuserIfname(const char *path ATTRIBUTE_UNUSED,
> + char **ifname)
> +{
> + return VIR_STRDUP(*ifname, "vhost-user0");
> +}
> diff --git a/tests/qemuxml2xmlmock.c b/tests/qemuxml2xmlmock.c
> new file mode 100644
> index 000000000..0d3e6f2bd
> --- /dev/null
> +++ b/tests/qemuxml2xmlmock.c
> @@ -0,0 +1,33 @@
> +/*
> + * Copyright (C) 2016 Red Hat, Inc.
> + *
> + * 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: Michal Privoznik <mprivozn at redhat.com>
> + */
> +
> +#include <config.h>
> +
> +#include "virnetdevopenvswitch.h"
> +#include "virstring.h"
> +
> +#define VIR_FROM_THIS VIR_FROM_NONE
> +
> +int
> +virNetDevOpenvswitchGetVhostuserIfname(const char *path ATTRIBUTE_UNUSED,
> + char **ifname)
> +{
> + return VIR_STRDUP(*ifname, "vhost-user0");
> +}
> diff --git a/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-vhostuser.xml b/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-vhostuser.xml
> index ac1d7e110..2bdcac358 100644
> --- a/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-vhostuser.xml
> +++ b/tests/qemuxml2xmloutdata/qemuxml2xmlout-net-vhostuser.xml
> @@ -30,12 +30,14 @@
> <interface type='vhostuser'>
> <mac address='52:54:00:ee:96:6b'/>
> <source type='unix' path='/tmp/vhost0.sock' mode='server'/>
> + <target dev='vhost-user0'/>
> <model type='virtio'/>
> <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
> </interface>
> <interface type='vhostuser'>
> <mac address='52:54:00:ee:96:6c'/>
> <source type='unix' path='/tmp/vhost1.sock' mode='client'/>
> + <target dev='vhost-user0'/>
> <model type='virtio'/>
> <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
> </interface>
> diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c
> index ddd17cb1e..30931f581 100644
> --- a/tests/qemuxml2xmltest.c
> +++ b/tests/qemuxml2xmltest.c
> @@ -1031,7 +1031,7 @@ mymain(void)
> return ret == 0 ? EXIT_SUCCESS : EXIT_FAILURE;
> }
>
> -VIRT_TEST_MAIN(mymain)
> +VIRT_TEST_MAIN_PRELOAD(mymain, abs_builddir "/.libs/qemuxml2xmlmock.so")
>
> #else
>
>
More information about the libvir-list
mailing list