From nobody Sun Feb 8 17:13:18 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of redhat.com designates 63.128.21.124 as permitted sender) client-ip=63.128.21.124; envelope-from=libvir-list-bounces@redhat.com; helo=us-smtp-delivery-124.mimecast.com; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of redhat.com designates 63.128.21.124 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1600331593; cv=none; d=zohomail.com; s=zohoarc; b=kXDJa641jtStF2IKDx598ipfD8zCT2b8cd2qyRr+5uGW4LQuCdXapyp4sW43OpbFHZ1kwJKokS8sAnwPf+0ZtkNuRdnr3pVdUo6EIDcrwzSFrQ8TUYhHSWHCOroKRRBLYFAS8LwGf0U+6LqZYqBqHrjmwI8/1YOCo7ox2fBtNKU= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1600331593; h=Content-Type:Content-Transfer-Encoding:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=cMs0I7DyjN8iXEtoG/Exf4R3DIj1qZVcPDY5/Ydty70=; b=hAUvwAocUXpV+AV66nNPttBLrKFsgrgsN5K9hTW/D6HlHTue2AiXYbh0no07gkkyoFlbHmMr86XMjcLNu4gIyHsB3gCenqOnACdnKrbsPmWbkXg5cjGwCLA3CSrKih0SP18k/N3C2fbckD6YA0FBfnSdQFhKEPaWxzhWWibo3zc= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of redhat.com designates 63.128.21.124 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=pass header.from= (p=none dis=none) header.from= Return-Path: Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [63.128.21.124]) by mx.zohomail.com with SMTPS id 1600331593936656.6276301002914; Thu, 17 Sep 2020 01:33:13 -0700 (PDT) Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-343-sRUZFO-8NJWFaaQjKyV29g-1; Thu, 17 Sep 2020 04:32:48 -0400 Received: from smtp.corp.redhat.com (int-mx07.intmail.prod.int.phx2.redhat.com [10.5.11.22]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 1C03E64147; Thu, 17 Sep 2020 08:32:43 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.21]) by smtp.corp.redhat.com (Postfix) with ESMTPS id E5FD7101416E; Thu, 17 Sep 2020 08:32:42 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id AA4C244A7C; Thu, 17 Sep 2020 08:32:42 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.phx2.redhat.com [10.5.11.14]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id 08H8UMoK004226 for ; Thu, 17 Sep 2020 04:30:22 -0400 Received: by smtp.corp.redhat.com (Postfix) id 88A2D5DA30; Thu, 17 Sep 2020 08:30:22 +0000 (UTC) Received: from antique-work.redhat.com (unknown [10.40.195.159]) by smtp.corp.redhat.com (Postfix) with ESMTP id 9E9D55DEBF for ; Thu, 17 Sep 2020 08:30:21 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1600331592; h=from:from:sender:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:mime-version:mime-version: content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references:list-id:list-help: list-unsubscribe:list-subscribe:list-post; bh=cMs0I7DyjN8iXEtoG/Exf4R3DIj1qZVcPDY5/Ydty70=; b=NNIBrm4W/33iOZIatmi1kBe4exvtUMsrew/a9iU+HKqna9e0o0T9bFf4h1KlfwRuJCP5qW qW8mf8DhuQPDAKsgF71+0+ejyFTB5wFstHpJFjs6On+VFUJR7fShXwaVu+Jsa3g9xT5bfV /k8O50C15Y823pJGr2mn7+jhBC1D8lU= X-MC-Unique: sRUZFO-8NJWFaaQjKyV29g-1 From: Pavel Hrdina To: libvir-list@redhat.com Subject: [libvirt PATCH 14/14] drop libdbus from libvirt Date: Thu, 17 Sep 2020 10:29:49 +0200 Message-Id: <4cbe87b5b6b5410b92ef164a5956991a4eb0903a.1600331276.git.phrdina@redhat.com> In-Reply-To: References: MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.14 X-loop: libvir-list@redhat.com X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.84 on 10.5.11.22 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=libvir-list-bounces@redhat.com X-Mimecast-Spam-Score: 0.104 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable X-ZohoMail-DKIM: pass (identity @redhat.com) Content-Type: text/plain; charset="utf-8" Signed-off-by: Pavel Hrdina --- libvirt.spec.in | 3 - meson.build | 27 +- meson_options.txt | 1 - po/POTFILES.in | 1 - src/libvirt_private.syms | 17 - src/libvirt_probes.d | 6 - src/meson.build | 1 - src/remote/remote_daemon_dispatch.c | 1 - src/util/meson.build | 2 - src/util/virdbus.c | 1871 --------------------------- src/util/virdbus.h | 76 -- src/util/virdbuspriv.h | 56 - tests/meson.build | 13 - tests/virdbusmock.c | 62 - tests/virdbustest.c | 728 ----------- 15 files changed, 3 insertions(+), 2862 deletions(-) delete mode 100644 src/util/virdbus.c delete mode 100644 src/util/virdbus.h delete mode 100644 src/util/virdbuspriv.h delete mode 100644 tests/virdbusmock.c delete mode 100644 tests/virdbustest.c diff --git a/libvirt.spec.in b/libvirt.spec.in index 62b401bd08..264932e6d5 100644 --- a/libvirt.spec.in +++ b/libvirt.spec.in @@ -374,9 +374,6 @@ BuildRequires: util-linux # For showmount in FS driver (netfs discovery) BuildRequires: nfs-utils =20 -# Communication with the firewall and polkit daemons use DBus -BuildRequires: dbus-devel - # Fedora build root suckage BuildRequires: gawk =20 diff --git a/meson.build b/meson.build index b5b1223227..24535a403c 100644 --- a/meson.build +++ b/meson.build @@ -1019,22 +1019,6 @@ if curl_dep.found() conf.set('WITH_CURL', 1) endif =20 -dbus_version =3D '1.0.0' -dbus_dep =3D dependency('dbus-1', version: '>=3D' + dbus_version, required= : get_option('dbus')) -if dbus_dep.found() - conf.set('WITH_DBUS', 1) - - function =3D 'dbus_watch_get_unix_fd' - if cc.has_function(function, dependencies: dbus_dep) - conf.set('WITH_@0@'.format(function.to_upper()), 1) - endif - - type =3D 'DBusBasicValue' - if cc.has_type(type, dependencies: dbus_dep, prefix: '#include ') - conf.set('WITH_@0@'.format(type.to_upper()), 1) - endif -endif - devmapper_version =3D '1.0.0' devmapper_dep =3D dependency('devmapper', version: '>=3D' + devmapper_vers= ion, required: false) if not devmapper_dep.found() @@ -1536,10 +1520,8 @@ if bash_completion_dep.found() endif =20 if host_machine.system() !=3D 'freebsd' - if not get_option('firewalld').disabled() and dbus_dep.found() + if not get_option('firewalld').disabled() conf.set('WITH_FIREWALLD', 1) - elif get_option('firewalld').enabled() - error('You must have dbus enabled for firewalld support') endif endif =20 @@ -1553,10 +1535,8 @@ if conf.has('WITH_MACVTAP') and not conf.has('WITH_L= IBNL') error('libnl3-devel is required for macvtap support') endif =20 -if (pkcheck_prog.found() or get_option('polkit').enabled()) and dbus_dep.f= ound() +if (pkcheck_prog.found() or get_option('polkit').enabled()) conf.set('WITH_POLKIT', 1) -elif get_option('polkit').enabled() - error('You must install dbus to compile libvirt with polkit-1') endif =20 if udev_dep.found() and not pciaccess_dep.found() @@ -2203,7 +2183,7 @@ endif =20 if not get_option('pm_utils').disabled() use_pm_utils =3D true - if dbus_dep.found() and init_script =3D=3D 'systemd' + if init_script =3D=3D 'systemd' use_pm_utils =3D false endif =20 @@ -2423,7 +2403,6 @@ libs_summary =3D { 'blkid': blkid_dep.found(), 'capng': capng_dep.found(), 'curl': curl_dep.found(), - 'dbus': dbus_dep.found(), 'dlopen': dlopen_dep.found(), 'firewalld': conf.has('WITH_FIREWALLD'), 'firewalld-zone': conf.has('WITH_FIREWALLD_ZONE'), diff --git a/meson_options.txt b/meson_options.txt index c8886e1430..f92c80553c 100644 --- a/meson_options.txt +++ b/meson_options.txt @@ -18,7 +18,6 @@ option('bash_completion_dir', type: 'string', value: '', = description: 'directory option('blkid', type: 'feature', value: 'auto', description: 'blkid suppor= t') option('capng', type: 'feature', value: 'auto', description: 'cap-ng suppo= rt') option('curl', type: 'feature', value: 'auto', description: 'curl support') -option('dbus', type: 'feature', value: 'auto', description: 'dbus-1 suppor= t') option('firewalld', type: 'feature', value: 'auto', description: 'firewall= d support') option('firewalld_zone', type: 'feature', value: 'auto', description: 'whe= ther to install firewalld libvirt zone') option('fuse', type: 'feature', value: 'auto', description: 'fuse support') diff --git a/po/POTFILES.in b/po/POTFILES.in index d87425a64c..54f78e7861 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -243,7 +243,6 @@ @SRCDIR@src/util/virconf.c @SRCDIR@src/util/vircrypto.c @SRCDIR@src/util/virdaemon.c -@SRCDIR@src/util/virdbus.c @SRCDIR@src/util/virdevmapper.c @SRCDIR@src/util/virdnsmasq.c @SRCDIR@src/util/virerror.c diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index fea5a49e55..bdbe3431b8 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1948,23 +1948,6 @@ virDaemonSetupLogging; virDaemonUnixSocketPaths; =20 =20 -# util/virdbus.h -virDBusCallMethod; -virDBusCloseSystemBus; -virDBusCreateMethod; -virDBusCreateMethodV; -virDBusCreateReply; -virDBusCreateReplyV; -virDBusErrorIsUnknownMethod; -virDBusGetSessionBus; -virDBusGetSystemBus; -virDBusHasSystemBus; -virDBusMessageDecode; -virDBusMessageEncode; -virDBusMessageUnref; -virDBusSetSharedBus; - - # util/virdevmapper.h virDevMapperGetTargets; virIsDevMapperDevice; diff --git a/src/libvirt_probes.d b/src/libvirt_probes.d index 5e4faa2f5b..6fac10a2bf 100644 --- a/src/libvirt_probes.d +++ b/src/libvirt_probes.d @@ -13,12 +13,6 @@ provider libvirt { probe event_glib_remove_timeout_idle(int timer, void *ff, void *opaque); probe event_glib_dispatch_timeout(int timer, void *cb, void *opaque); =20 - # file: src/util/virdbus.c - # prefix: dbus - probe dbus_method_call(const char *interface, const char *member, const c= har *object, const char *destination); - probe dbus_method_error(const char *interface, const char *member, const = char *object, const char *destination, const char *name, const char *messag= e); - probe dbus_method_reply(const char *interface, const char *member, const = char *object, const char *destination); - # file: src/util/virobject.c # prefix: object probe object_new(void *obj, const char *klassname); diff --git a/src/meson.build b/src/meson.build index 897b5ecbca..29c8210ab2 100644 --- a/src/meson.build +++ b/src/meson.build @@ -614,7 +614,6 @@ foreach daemon : virt_daemons dependencies: [ admin_dep, access_dep, - dbus_dep, gnutls_dep, libnl_dep, rpc_dep, diff --git a/src/remote/remote_daemon_dispatch.c b/src/remote/remote_daemon= _dispatch.c index 53d17a8f4a..c187932a3c 100644 --- a/src/remote/remote_daemon_dispatch.c +++ b/src/remote/remote_daemon_dispatch.c @@ -35,7 +35,6 @@ #include "virnetserver.h" #include "virfile.h" #include "virtypedparam.h" -#include "virdbus.h" #include "virprocess.h" #include "remote_protocol.h" #include "qemu_protocol.h" diff --git a/src/util/meson.build b/src/util/meson.build index 8a9dcac053..4d63173cbd 100644 --- a/src/util/meson.build +++ b/src/util/meson.build @@ -18,7 +18,6 @@ util_sources =3D [ 'virconf.c', 'vircrypto.c', 'virdaemon.c', - 'virdbus.c', 'virdevmapper.c', 'virdnsmasq.c', 'virebtables.c', @@ -185,7 +184,6 @@ virt_util_lib =3D static_library( acl_dep, audit_dep, capng_dep, - dbus_dep, devmapper_dep, gnutls_dep, intl_dep, diff --git a/src/util/virdbus.c b/src/util/virdbus.c deleted file mode 100644 index 459b57abc6..0000000000 --- a/src/util/virdbus.c +++ /dev/null @@ -1,1871 +0,0 @@ -/* - * virdbus.c: helper for using DBus - * - * Copyright (C) 2012-2014 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 - * . - * - */ - -#include - -#define LIBVIRT_VIRDBUSPRIV_H_ALLOW -#include "virdbuspriv.h" -#include "viralloc.h" -#include "virerror.h" -#include "virlog.h" -#include "virthread.h" -#include "virstring.h" -#include "virprobe.h" - -#define VIR_FROM_THIS VIR_FROM_DBUS - -VIR_LOG_INIT("util.dbus"); - -#ifdef WITH_DBUS - -static bool sharedBus =3D true; -static DBusConnection *systembus; -static DBusConnection *sessionbus; -static virOnceControl systemonce =3D VIR_ONCE_CONTROL_INITIALIZER; -static virOnceControl sessiononce =3D VIR_ONCE_CONTROL_INITIALIZER; -static DBusError systemdbuserr; -static DBusError sessiondbuserr; - -static dbus_bool_t virDBusAddWatch(DBusWatch *watch, void *data); -static void virDBusRemoveWatch(DBusWatch *watch, void *data); -static void virDBusToggleWatch(DBusWatch *watch, void *data); - -void virDBusSetSharedBus(bool shared) -{ - sharedBus =3D shared; -} - -static DBusConnection *virDBusBusInit(DBusBusType type, DBusError *dbuserr) -{ - DBusConnection *bus; - - /* Allocate and initialize a new HAL context */ - dbus_connection_set_change_sigpipe(FALSE); - dbus_threads_init_default(); - - dbus_error_init(dbuserr); - bus =3D sharedBus ? - dbus_bus_get(type, dbuserr) : - dbus_bus_get_private(type, dbuserr); - if (!bus) - return NULL; - - dbus_connection_set_exit_on_disconnect(bus, FALSE); - - /* Register dbus watch callbacks */ - if (!dbus_connection_set_watch_functions(bus, - virDBusAddWatch, - virDBusRemoveWatch, - virDBusToggleWatch, - bus, NULL)) { - return NULL; - } - return bus; -} - -static void virDBusSystemBusInit(void) -{ - systembus =3D virDBusBusInit(DBUS_BUS_SYSTEM, &systemdbuserr); -} - -static DBusConnection * -virDBusGetSystemBusInternal(void) -{ - if (virOnce(&systemonce, virDBusSystemBusInit) < 0) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Unable to run one time DBus initializer")); - return NULL; - } - - return systembus; -} - - -DBusConnection * -virDBusGetSystemBus(void) -{ - DBusConnection *bus; - - if (!(bus =3D virDBusGetSystemBusInternal())) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Unable to get DBus system bus connection: %s"), - systemdbuserr.message ? systemdbuserr.message : "wa= tch setup failed"); - return NULL; - } - - return bus; -} - - -/** - * virDBusHasSystemBus: - * - * Check if dbus system bus is running. This does not - * imply that we have a connection. DBus might be running - * and refusing connections due to its client limit. The - * latter must be treated as a fatal error. - * - * Return false if dbus is not available, true if probably available. - */ -bool -virDBusHasSystemBus(void) -{ - if (virDBusGetSystemBusInternal()) - return true; - - if (systemdbuserr.name && - (STREQ(systemdbuserr.name, "org.freedesktop.DBus.Error.FileNotFoun= d") || - STREQ(systemdbuserr.name, "org.freedesktop.DBus.Error.NoServer"))= ) { - VIR_DEBUG("System DBus not available: %s", NULLSTR(systemdbuserr.m= essage)); - return false; - } - return true; -} - - -void virDBusCloseSystemBus(void) -{ - if (systembus && !sharedBus) { - dbus_connection_close(systembus); - dbus_connection_unref(systembus); - systembus =3D NULL; - } -} - -static void virDBusSessionBusInit(void) -{ - sessionbus =3D virDBusBusInit(DBUS_BUS_SESSION, &sessiondbuserr); -} - -DBusConnection *virDBusGetSessionBus(void) -{ - if (virOnce(&sessiononce, virDBusSessionBusInit) < 0) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Unable to run one time DBus initializer")); - return NULL; - } - - if (!sessionbus) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Unable to get DBus session bus connection: %s"), - sessiondbuserr.message ? sessiondbuserr.message : "= watch setup failed"); - return NULL; - } - - return sessionbus; -} - -struct virDBusWatch -{ - int watch; - DBusConnection *bus; -}; - -static void virDBusWatchCallback(int fdatch G_GNUC_UNUSED, - int fd G_GNUC_UNUSED, - int events, void *opaque) -{ - DBusWatch *watch =3D opaque; - struct virDBusWatch *info; - int dbus_flags =3D 0; - - info =3D dbus_watch_get_data(watch); - - if (events & VIR_EVENT_HANDLE_READABLE) - dbus_flags |=3D DBUS_WATCH_READABLE; - if (events & VIR_EVENT_HANDLE_WRITABLE) - dbus_flags |=3D DBUS_WATCH_WRITABLE; - if (events & VIR_EVENT_HANDLE_ERROR) - dbus_flags |=3D DBUS_WATCH_ERROR; - if (events & VIR_EVENT_HANDLE_HANGUP) - dbus_flags |=3D DBUS_WATCH_HANGUP; - - if (dbus_watch_handle(watch, dbus_flags) =3D=3D FALSE) - VIR_DEBUG("dbus_watch_handle() returned FALSE"); - - dbus_connection_ref(info->bus); - while (dbus_connection_dispatch(info->bus) =3D=3D DBUS_DISPATCH_DATA_R= EMAINS) - /* keep dispatching while data remains */; - dbus_connection_unref(info->bus); -} - - -static int virDBusTranslateWatchFlags(int dbus_flags) -{ - unsigned int flags =3D 0; - if (dbus_flags & DBUS_WATCH_READABLE) - flags |=3D VIR_EVENT_HANDLE_READABLE; - if (dbus_flags & DBUS_WATCH_WRITABLE) - flags |=3D VIR_EVENT_HANDLE_WRITABLE; - if (dbus_flags & DBUS_WATCH_ERROR) - flags |=3D VIR_EVENT_HANDLE_ERROR; - if (dbus_flags & DBUS_WATCH_HANGUP) - flags |=3D VIR_EVENT_HANDLE_HANGUP; - return flags; -} - - -static void virDBusWatchFree(void *data) -{ - struct virDBusWatch *info =3D data; - VIR_FREE(info); -} - -static dbus_bool_t virDBusAddWatch(DBusWatch *watch, - void *data) -{ - int flags =3D 0; - int fd; - struct virDBusWatch *info; - - if (VIR_ALLOC(info) < 0) - return FALSE; - - if (dbus_watch_get_enabled(watch)) - flags =3D virDBusTranslateWatchFlags(dbus_watch_get_flags(watch)); - -# if WITH_DBUS_WATCH_GET_UNIX_FD - fd =3D dbus_watch_get_unix_fd(watch); -# else - fd =3D dbus_watch_get_fd(watch); -# endif - dbus_watch_set_data(watch, info, virDBusWatchFree); - info->bus =3D (DBusConnection *)data; - info->watch =3D virEventAddHandle(fd, flags, - virDBusWatchCallback, - watch, NULL); - if (info->watch < 0) { - dbus_watch_set_data(watch, NULL, NULL); - return FALSE; - } - - return TRUE; -} - - -static void virDBusRemoveWatch(DBusWatch *watch, - void *data G_GNUC_UNUSED) -{ - struct virDBusWatch *info; - - info =3D dbus_watch_get_data(watch); - - (void)virEventRemoveHandle(info->watch); -} - - -static void virDBusToggleWatch(DBusWatch *watch, - void *data G_GNUC_UNUSED) -{ - int flags =3D 0; - struct virDBusWatch *info; - - if (dbus_watch_get_enabled(watch)) - flags =3D virDBusTranslateWatchFlags(dbus_watch_get_flags(watch)); - - info =3D dbus_watch_get_data(watch); - - (void)virEventUpdateHandle(info->watch, flags); -} - -# define VIR_DBUS_TYPE_STACK_MAX_DEPTH 32 - -static const char virDBusBasicTypes[] =3D { - DBUS_TYPE_BYTE, - DBUS_TYPE_BOOLEAN, - DBUS_TYPE_INT16, - DBUS_TYPE_UINT16, - DBUS_TYPE_INT32, - DBUS_TYPE_UINT32, - DBUS_TYPE_INT64, - DBUS_TYPE_UINT64, - DBUS_TYPE_DOUBLE, - DBUS_TYPE_STRING, - DBUS_TYPE_OBJECT_PATH, - DBUS_TYPE_SIGNATURE, -}; - -static bool virDBusIsBasicType(char c) -{ - return !!memchr(virDBusBasicTypes, c, G_N_ELEMENTS(virDBusBasicTypes)); -} - -/* - * All code related to virDBusMessageIterEncode and - * virDBusMessageIterDecode is derived from systemd - * bus_message_append_ap()/message_read_ap() in - * bus-message.c under the terms of the LGPLv2+ - */ -static int -virDBusSignatureLengthInternal(const char *s, - bool allowDict, - unsigned arrayDepth, - unsigned structDepth, - size_t *skiplen, - size_t *siglen) -{ - if (virDBusIsBasicType(*s) || *s =3D=3D DBUS_TYPE_VARIANT) { - *skiplen =3D *siglen =3D 1; - return 0; - } - - if (*s =3D=3D DBUS_TYPE_ARRAY) { - size_t skiplencont; - size_t siglencont; - bool arrayref =3D false; - - if (arrayDepth >=3D VIR_DBUS_TYPE_STACK_MAX_DEPTH) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Signature '%s' too deeply nested"), - s); - return -1; - } - - if (*(s + 1) =3D=3D '&') { - arrayref =3D true; - s++; - } - - if (virDBusSignatureLengthInternal(s + 1, - true, - arrayDepth + 1, - structDepth, - &skiplencont, - &siglencont) < 0) - return -1; - - *skiplen =3D skiplencont + 1; - *siglen =3D siglencont + 1; - if (arrayref) - (*skiplen)++; - return 0; - } - - if (*s =3D=3D DBUS_STRUCT_BEGIN_CHAR) { - const char *p =3D s + 1; - - if (structDepth >=3D VIR_DBUS_TYPE_STACK_MAX_DEPTH) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Signature '%s' too deeply nested"), - s); - return -1; - } - - *skiplen =3D *siglen =3D 2; - - while (*p !=3D DBUS_STRUCT_END_CHAR) { - size_t skiplencont; - size_t siglencont; - - if (virDBusSignatureLengthInternal(p, - false, - arrayDepth, - structDepth + 1, - &skiplencont, - &siglencont) < 0) - return -1; - - p +=3D skiplencont; - *skiplen +=3D skiplencont; - *siglen +=3D siglencont; - } - - return 0; - } - - if (*s =3D=3D DBUS_DICT_ENTRY_BEGIN_CHAR && allowDict) { - const char *p =3D s + 1; - unsigned n =3D 0; - if (structDepth >=3D VIR_DBUS_TYPE_STACK_MAX_DEPTH) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Signature '%s' too deeply nested"), - s); - return -1; - } - - *skiplen =3D *siglen =3D 2; - - while (*p !=3D DBUS_DICT_ENTRY_END_CHAR) { - size_t skiplencont; - size_t siglencont; - - if (n =3D=3D 0 && !virDBusIsBasicType(*p)) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Dict entry in signature '%s' must be a b= asic type"), - s); - return -1; - } - - if (virDBusSignatureLengthInternal(p, - false, - arrayDepth, - structDepth + 1, - &skiplencont, - &siglencont) < 0) - return -1; - - p +=3D skiplencont; - *skiplen +=3D skiplencont; - *siglen +=3D siglencont; - n++; - } - - if (n !=3D 2) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Dict entry in signature '%s' is wrong size"), - s); - return -1; - } - - return 0; - } - - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Unexpected signature '%s'"), s); - return -1; -} - - -static int virDBusSignatureLength(const char *s, size_t *skiplen, size_t *= siglen) -{ - return virDBusSignatureLengthInternal(s, true, 0, 0, skiplen, siglen); -} - - -static char *virDBusCopyContainerSignature(const char *sig, - size_t *skiplen, - size_t *siglen) -{ - size_t i, j; - char *contsig; - bool isGroup; - - isGroup =3D (sig[0] =3D=3D DBUS_STRUCT_BEGIN_CHAR || - sig[0] =3D=3D DBUS_DICT_ENTRY_BEGIN_CHAR); - - if (virDBusSignatureLength(isGroup ? sig : sig + 1, skiplen, siglen) <= 0) - return NULL; - - if (VIR_ALLOC_N(contsig, *siglen + 1) < 0) - return NULL; - - for (i =3D 0, j =3D 0; i < *skiplen && j < *siglen; i++) { - if (sig[i + 1] =3D=3D '&') - continue; - contsig[j] =3D sig[i + 1]; - j++; - } - contsig[*siglen] =3D '\0'; - VIR_DEBUG("Extracted '%s' from '%s'", contsig, sig); - return contsig; -} - - -/* Ideally, we'd just call ourselves recursively on every - * complex type. However, the state of a va_list that is - * passed to a function is undefined after that function - * returns. This means we need to decode the va_list linearly - * in a single stackframe. We hence implement our own - * home-grown stack in an array. */ - -typedef struct _virDBusTypeStack virDBusTypeStack; -struct _virDBusTypeStack { - const char *types; - size_t nstruct; - size_t narray; - DBusMessageIter *iter; -}; - -static int virDBusTypeStackPush(virDBusTypeStack **stack, - size_t *nstack, - DBusMessageIter *iter, - const char *types, - size_t nstruct, - size_t narray) -{ - if (*nstack >=3D VIR_DBUS_TYPE_STACK_MAX_DEPTH) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("DBus type too deeply nested")); - return -1; - } - - if (VIR_EXPAND_N(*stack, *nstack, 1) < 0) - return -1; - - (*stack)[(*nstack) - 1].iter =3D iter; - (*stack)[(*nstack) - 1].types =3D types; - (*stack)[(*nstack) - 1].nstruct =3D nstruct; - (*stack)[(*nstack) - 1].narray =3D narray; - VIR_DEBUG("Pushed types=3D'%s' nstruct=3D%zu narray=3D%zd", - types, nstruct, (ssize_t)narray); - return 0; -} - - -static int virDBusTypeStackPop(virDBusTypeStack **stack, - size_t *nstack, - DBusMessageIter **iter, - const char **types, - size_t *nstruct, - size_t *narray) -{ - if (*nstack =3D=3D 0) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("DBus type stack is empty")); - return -1; - } - - *iter =3D (*stack)[(*nstack) - 1].iter; - *types =3D (*stack)[(*nstack) - 1].types; - *nstruct =3D (*stack)[(*nstack) - 1].nstruct; - *narray =3D (*stack)[(*nstack) - 1].narray; - VIR_DEBUG("Popped types=3D'%s' nstruct=3D%zu narray=3D%zd", - *types, *nstruct, (ssize_t)*narray); - VIR_SHRINK_N(*stack, *nstack, 1); - - return 0; -} - - -static void virDBusTypeStackFree(virDBusTypeStack **stack, - size_t *nstack) -{ - size_t i; - - if (!*stack) - return; - - /* The iter in the first level of the stack is the - * root iter which must not be freed - */ - for (i =3D 1; i < *nstack; i++) - VIR_FREE((*stack)[i].iter); - VIR_FREE(*stack); -} - - -static bool -virDBusIsAllowedRefType(const char *sig) -{ - if (*sig =3D=3D '{') { - if (strlen(sig) !=3D 4) - return false; - if (!virDBusIsBasicType(sig[1]) || - !virDBusIsBasicType(sig[2]) || - sig[1] !=3D sig[2]) - return false; - if (sig[3] !=3D '}') - return false; - } else { - if (strlen(sig) !=3D 1) - return false; - if (!virDBusIsBasicType(sig[0])) - return false; - } - return true; -} - - -# define SET_NEXT_VAL(dbustype, vargtype, arrtype, sigtype, fmt) \ - do { \ - dbustype x; \ - if (arrayref) { \ - arrtype valarray =3D arrayptr; \ - x =3D (dbustype)*valarray; \ - valarray++; \ - arrayptr =3D valarray; \ - } else { \ - x =3D (dbustype)va_arg(args, vargtype); \ - } \ - if (!dbus_message_iter_append_basic(iter, sigtype, &x)) { \ - virReportError(VIR_ERR_INTERNAL_ERROR, \ - _("Cannot append basic type %s"), #vargtype);\ - goto cleanup; \ - } \ - VIR_DEBUG("Appended basic type '" #dbustype "' varg '" #vargtype\ - "' sig '%c' val '" fmt "'", sigtype, (vargtype)x); \ - } while (0) - - -static int -virDBusMessageIterEncode(DBusMessageIter *rootiter, - const char *types, - va_list args) -{ - int ret =3D -1; - size_t narray; - size_t nstruct; - bool arrayref =3D false; - void *arrayptr =3D NULL; - virDBusTypeStack *stack =3D NULL; - size_t nstack =3D 0; - size_t siglen; - size_t skiplen; - char *contsig =3D NULL; - const char *vsig; - DBusMessageIter *newiter =3D NULL; - DBusMessageIter *iter =3D rootiter; - - VIR_DEBUG("rootiter=3D%p types=3D%s", rootiter, types); - - if (!types) - return 0; - - narray =3D (size_t)-1; - nstruct =3D strlen(types); - - for (;;) { - const char *t; - - VIR_DEBUG("Loop nstack=3D%zu narray=3D%zd nstruct=3D%zu types=3D'%= s'", - nstack, (ssize_t)narray, nstruct, types); - if (narray =3D=3D 0 || - (narray =3D=3D (size_t)-1 && - nstruct =3D=3D 0)) { - DBusMessageIter *thisiter =3D iter; - if (*types !=3D '}') { - VIR_DEBUG("Reset array ref"); - arrayref =3D false; - arrayptr =3D NULL; - } - VIR_DEBUG("Popping iter=3D%p", iter); - if (nstack =3D=3D 0) - break; - if (virDBusTypeStackPop(&stack, &nstack, &iter, - &types, &nstruct, &narray) < 0) - goto cleanup; - VIR_DEBUG("Popped iter=3D%p", iter); - - if (!dbus_message_iter_close_container(iter, thisiter)) { - if (thisiter !=3D rootiter) - VIR_FREE(thisiter); - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Cannot close container iterator")); - goto cleanup; - } - if (thisiter !=3D rootiter) - VIR_FREE(thisiter); - continue; - } - - t =3D types; - if (narray !=3D (size_t)-1) { - narray--; - } else { - types++; - nstruct--; - } - - switch (*t) { - case DBUS_TYPE_BYTE: - SET_NEXT_VAL(unsigned char, int, unsigned char *, *t, "%d"); - break; - - case DBUS_TYPE_BOOLEAN: - SET_NEXT_VAL(dbus_bool_t, int, bool *, *t, "%d"); - break; - - case DBUS_TYPE_INT16: - SET_NEXT_VAL(dbus_int16_t, int, short *, *t, "%d"); - break; - - case DBUS_TYPE_UINT16: - SET_NEXT_VAL(dbus_uint16_t, unsigned int, unsigned short *, - *t, "%d"); - break; - - case DBUS_TYPE_INT32: - SET_NEXT_VAL(dbus_int32_t, int, int *, *t, "%d"); - break; - - case DBUS_TYPE_UINT32: - SET_NEXT_VAL(dbus_uint32_t, unsigned int, unsigned int *, - *t, "%u"); - break; - - case DBUS_TYPE_INT64: - SET_NEXT_VAL(dbus_int64_t, long long, long long *, *t, "%lld"); - break; - - case DBUS_TYPE_UINT64: - SET_NEXT_VAL(dbus_uint64_t, unsigned long long, - unsigned long long *, *t, "%llu"); - break; - - case DBUS_TYPE_DOUBLE: - SET_NEXT_VAL(double, double, double *, *t, "%lf"); - break; - - case DBUS_TYPE_STRING: - case DBUS_TYPE_OBJECT_PATH: - case DBUS_TYPE_SIGNATURE: - SET_NEXT_VAL(char *, char *, char **, *t, "%s"); - break; - - case DBUS_TYPE_ARRAY: - arrayptr =3D NULL; - if (t[1] =3D=3D '&') { - VIR_DEBUG("Got array ref"); - t++; - types++; - nstruct--; - arrayref =3D true; - } else { - VIR_DEBUG("Got array non-ref"); - arrayref =3D false; - } - - if (!(contsig =3D virDBusCopyContainerSignature(t, &skiplen, &= siglen))) - goto cleanup; - - if (arrayref && !virDBusIsAllowedRefType(contsig)) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Got array ref but '%s' is not a single b= asic type " - "or dict with matching key+value type"), - contsig); - goto cleanup; - } - - if (narray =3D=3D (size_t)-1) { - types +=3D skiplen; - nstruct -=3D skiplen; - } - - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - VIR_DEBUG("Contsig '%s' skip=3D'%zu' len=3D'%zu'", contsig, sk= iplen, siglen); - if (!dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY, - contsig, newiter)) - goto cleanup; - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) { - VIR_FREE(newiter); - goto cleanup; - } - VIR_FREE(contsig); - iter =3D g_steal_pointer(&newiter); - types =3D t + 1; - nstruct =3D skiplen; - narray =3D (size_t)va_arg(args, int); - if (arrayref) - arrayptr =3D va_arg(args, void *); - break; - - case DBUS_TYPE_VARIANT: - vsig =3D va_arg(args, const char *); - if (!vsig) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Missing variant type signature")); - goto cleanup; - } - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - if (!dbus_message_iter_open_container(iter, DBUS_TYPE_VARIANT, - vsig, newiter)) - goto cleanup; - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) { - VIR_FREE(newiter); - goto cleanup; - } - iter =3D g_steal_pointer(&newiter); - types =3D vsig; - nstruct =3D strlen(types); - narray =3D (size_t)-1; - break; - - case DBUS_STRUCT_BEGIN_CHAR: - case DBUS_DICT_ENTRY_BEGIN_CHAR: - if (!(contsig =3D virDBusCopyContainerSignature(t, &skiplen, &= siglen))) - goto cleanup; - - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - VIR_DEBUG("Contsig '%s' skip=3D'%zu' len=3D'%zu'", contsig, sk= iplen, siglen); - if (!dbus_message_iter_open_container(iter, - *t =3D=3D DBUS_STRUCT_BE= GIN_CHAR ? - DBUS_TYPE_STRUCT : DBUS_= TYPE_DICT_ENTRY, - NULL, newiter)) - goto cleanup; - if (narray =3D=3D (size_t)-1) { - types +=3D skiplen - 1; - nstruct -=3D skiplen - 1; - } - - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) { - VIR_FREE(newiter); - goto cleanup; - } - VIR_FREE(contsig); - iter =3D g_steal_pointer(&newiter); - types =3D t + 1; - nstruct =3D skiplen - 2; - narray =3D (size_t)-1; - - break; - - default: - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Unknown type '%x' in signature '%s'"), - (int)*t, types); - goto cleanup; - } - } - - ret =3D 0; - - cleanup: - while (nstack > 0) { - DBusMessageIter *thisiter =3D iter; - VIR_DEBUG("Popping iter=3D%p", iter); - ignore_value(virDBusTypeStackPop(&stack, &nstack, &iter, - &types, &nstruct, &narray)); - VIR_DEBUG("Popped iter=3D%p", iter); - - if (thisiter !=3D rootiter) - VIR_FREE(thisiter); - } - - virDBusTypeStackFree(&stack, &nstack); - VIR_FREE(contsig); - VIR_FREE(newiter); - return ret; -} -# undef SET_NEXT_VAL - - -# define GET_NEXT_VAL(dbustype, member, vargtype, fmt) \ - do { \ - DBusBasicValue v; \ - dbustype *x =3D (dbustype *)&v.member; \ - vargtype *y; \ - if (arrayref) { \ - vargtype **xptrptr =3D arrayptr; \ - VIR_DEBUG("Use arrayref"); \ - if (VIR_EXPAND_N(*xptrptr, *narrayptr, 1) < 0) \ - goto cleanup; \ - y =3D (*xptrptr + (*narrayptr - 1)); \ - VIR_DEBUG("Expanded to %zu", *narrayptr); \ - } else { \ - y =3D va_arg(args, vargtype *); \ - } \ - dbus_message_iter_get_basic(iter, x); \ - *y =3D *x; \ - VIR_DEBUG("Read basic type '" #dbustype "' varg '" #vargtype \ - "' val '" fmt "'", (vargtype)*y); \ - } while (0) - - -static int -virDBusMessageIterDecode(DBusMessageIter *rootiter, - const char *types, - va_list args) -{ - int ret =3D -1; - size_t narray; - size_t nstruct; - bool arrayref =3D false; - void *arrayptr =3D NULL; - size_t *narrayptr =3D 0; - virDBusTypeStack *stack =3D NULL; - size_t nstack =3D 0; - size_t skiplen; - size_t siglen; - char *contsig =3D NULL; - const char *vsig; - DBusMessageIter *newiter =3D NULL; - DBusMessageIter *iter =3D rootiter; - - VIR_DEBUG("rootiter=3D%p types=3D%s", rootiter, types); - - if (!types) - return 0; - - narray =3D (size_t)-1; - nstruct =3D strlen(types); - - for (;;) { - const char *t; - bool advanceiter =3D true; - - VIR_DEBUG("Loop nstack=3D%zu narray=3D%zd nstruct=3D%zu type=3D'%s= '", - nstack, (ssize_t)narray, nstruct, types); - if (narray =3D=3D 0 || - (narray =3D=3D (size_t)-1 && - nstruct =3D=3D 0)) { - DBusMessageIter *thisiter =3D iter; - VIR_DEBUG("Popping iter=3D%p", iter); - if (nstack =3D=3D 0) - break; - if (virDBusTypeStackPop(&stack, &nstack, &iter, - &types, &nstruct, &narray) < 0) - goto cleanup; - VIR_DEBUG("Popped iter=3D%p types=3D%s", iter, types); - if (strchr(types, '}') =3D=3D NULL) { - arrayref =3D false; - arrayptr =3D NULL; - VIR_DEBUG("Clear array ref flag"); - } - if (thisiter !=3D rootiter) - VIR_FREE(thisiter); - if (arrayref) { - if (!dbus_message_iter_has_next(iter)) - narray =3D 0; - else - narray =3D 1; - VIR_DEBUG("Pop set narray=3D%zd", (ssize_t)narray); - } - if (!(narray =3D=3D 0 || - (narray =3D=3D (size_t)-1 && - nstruct =3D=3D 0)) && - !dbus_message_iter_next(iter)) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Not enough fields in message for signatu= re")); - goto cleanup; - } - continue; - } - - t =3D types; - if (narray !=3D (size_t)-1) { - if (!arrayref) - narray--; - } else { - types++; - nstruct--; - } - - switch (*t) { - case DBUS_TYPE_BYTE: - GET_NEXT_VAL(unsigned char, byt, unsigned char, "%d"); - break; - - case DBUS_TYPE_BOOLEAN: - GET_NEXT_VAL(dbus_bool_t, bool_val, bool, "%d"); - break; - - case DBUS_TYPE_INT16: - GET_NEXT_VAL(dbus_int16_t, i16, short, "%d"); - break; - - case DBUS_TYPE_UINT16: - GET_NEXT_VAL(dbus_uint16_t, u16, unsigned short, "%d"); - break; - - case DBUS_TYPE_INT32: - GET_NEXT_VAL(dbus_uint32_t, i32, int, "%d"); - break; - - case DBUS_TYPE_UINT32: - GET_NEXT_VAL(dbus_uint32_t, u32, unsigned int, "%u"); - break; - - case DBUS_TYPE_INT64: - GET_NEXT_VAL(dbus_uint64_t, i64, long long, "%lld"); - break; - - case DBUS_TYPE_UINT64: - GET_NEXT_VAL(dbus_uint64_t, u64, unsigned long long, "%llu"); - break; - - case DBUS_TYPE_DOUBLE: - GET_NEXT_VAL(double, dbl, double, "%lf"); - break; - - case DBUS_TYPE_STRING: - case DBUS_TYPE_OBJECT_PATH: - case DBUS_TYPE_SIGNATURE: - do { - char **x; - char *s; - if (arrayref) { - char ***xptrptr =3D arrayptr; - if (VIR_EXPAND_N(*xptrptr, *narrayptr, 1) < 0) - goto cleanup; - x =3D (char **)(*xptrptr + (*narrayptr - 1)); - VIR_DEBUG("Expanded to %zu", *narrayptr); - } else { - x =3D (char **)va_arg(args, char **); - } - dbus_message_iter_get_basic(iter, &s); - *x =3D g_strdup(s); - VIR_DEBUG("Read basic type 'char *' varg 'char **'" - "' val '%s'", *x); - } while (0); - break; - - case DBUS_TYPE_ARRAY: - arrayptr =3D NULL; - if (t[1] =3D=3D '&') { - VIR_DEBUG("Got array ref"); - t++; - types++; - nstruct--; - arrayref =3D true; - } else { - VIR_DEBUG("Got array non-ref"); - arrayref =3D false; - } - - advanceiter =3D false; - if (!(contsig =3D virDBusCopyContainerSignature(t, &skiplen, &= siglen))) - goto cleanup; - - if (arrayref && !virDBusIsAllowedRefType(contsig)) { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Got array ref but '%s' is not a single b= asic type / dict"), - contsig); - goto cleanup; - } - - if (narray =3D=3D (size_t)-1) { - types +=3D skiplen; - nstruct -=3D skiplen; - } - - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - VIR_DEBUG("Array contsig=3D'%s' skip=3D%'zu' len=3D'%zu' types= =3D'%s'", - contsig, skiplen, siglen, types); - dbus_message_iter_recurse(iter, newiter); - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) - goto cleanup; - VIR_FREE(contsig); - iter =3D g_steal_pointer(&newiter); - types =3D t + 1; - nstruct =3D skiplen; - if (arrayref) { - narrayptr =3D va_arg(args, size_t *); - arrayptr =3D va_arg(args, void *); - *narrayptr =3D 0; - *(char **)arrayptr =3D NULL; - } else { - narray =3D va_arg(args, int); - } - break; - - case DBUS_TYPE_VARIANT: - advanceiter =3D false; - vsig =3D va_arg(args, const char *); - if (!vsig) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Missing variant type signature")); - goto cleanup; - } - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - dbus_message_iter_recurse(iter, newiter); - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) { - VIR_DEBUG("Push failed"); - goto cleanup; - } - iter =3D g_steal_pointer(&newiter); - types =3D vsig; - nstruct =3D strlen(types); - narray =3D (size_t)-1; - break; - - case DBUS_STRUCT_BEGIN_CHAR: - case DBUS_DICT_ENTRY_BEGIN_CHAR: - advanceiter =3D false; - if (!(contsig =3D virDBusCopyContainerSignature(t, &skiplen, &= siglen))) - goto cleanup; - - if (VIR_ALLOC(newiter) < 0) - goto cleanup; - VIR_DEBUG("Dict/struct contsig=3D'%s' skip=3D'%zu' len=3D'%zu'= types=3D'%s'", - contsig, skiplen, siglen, types); - dbus_message_iter_recurse(iter, newiter); - if (narray =3D=3D (size_t)-1) { - types +=3D skiplen - 1; - nstruct -=3D skiplen - 1; - } - - if (virDBusTypeStackPush(&stack, &nstack, - iter, types, - nstruct, narray) < 0) - goto cleanup; - VIR_FREE(contsig); - iter =3D g_steal_pointer(&newiter); - types =3D t + 1; - nstruct =3D skiplen - 2; - narray =3D (size_t)-1; - - break; - - default: - virReportError(VIR_ERR_INTERNAL_ERROR, - _("Unknown type '%c' in signature '%s'"), - *t, types); - goto cleanup; - } - - VIR_DEBUG("After nstack=3D%zu narray=3D%zd nstruct=3D%zu types=3D'= %s'", - nstack, (ssize_t)narray, nstruct, types); - - if (arrayref) { - if (dbus_message_iter_get_arg_type(iter) =3D=3D DBUS_TYPE_INVA= LID) { - narray =3D 0; - } else { - if (advanceiter) - dbus_message_iter_next(iter); - if (dbus_message_iter_get_arg_type(iter) =3D=3D DBUS_TYPE_= INVALID) { - narray =3D 0; - } else { - narray =3D 1; - } - } - VIR_DEBUG("Set narray=3D%zd", (ssize_t)narray); - } else { - if (advanceiter && - !(narray =3D=3D 0 || - (narray =3D=3D (size_t)-1 && - nstruct =3D=3D 0)) && - !dbus_message_iter_next(iter)) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Not enough fields in message for signatu= re")); - goto cleanup; - } - } - } - - if (dbus_message_iter_has_next(iter)) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Too many fields in message for signature")); - goto cleanup; - } - - ret =3D 0; - - cleanup: - virDBusTypeStackFree(&stack, &nstack); - VIR_FREE(contsig); - VIR_FREE(newiter); - return ret; -} -# undef GET_NEXT_VAL - -int -virDBusMessageEncodeArgs(DBusMessage* msg, - const char *types, - va_list args) -{ - DBusMessageIter iter; - - memset(&iter, 0, sizeof(iter)); - - dbus_message_iter_init_append(msg, &iter); - - return virDBusMessageIterEncode(&iter, types, args); -} - - -int virDBusMessageDecodeArgs(DBusMessage* msg, - const char *types, - va_list args) -{ - DBusMessageIter iter; - - if (!dbus_message_iter_init(msg, &iter)) { - if (*types !=3D '\0') { - virReportError(VIR_ERR_INTERNAL_ERROR, - _("No args present for signature %s"), - types); - } else { - return 0; - } - return -1; - } - - return virDBusMessageIterDecode(&iter, types, args); -} - - -int virDBusMessageEncode(DBusMessage* msg, - const char *types, - ...) -{ - int ret; - va_list args; - va_start(args, types); - ret =3D virDBusMessageEncodeArgs(msg, types, args); - va_end(args); - return ret; -} - - -/** - * virDBusMessageDecode: - * @msg: the reply to decode - * @types: type signature for following return values - * @...: pointers in which to store return values - * - * The @types type signature is the same format as - * that used for the virDBusCallMethod. The difference - * is that each variadic parameter must be a pointer to - * be filled with the values. eg instead of passing an - * 'int', pass an 'int *'. - * - */ -int -virDBusMessageDecode(DBusMessage* msg, - const char *types, - ...) -{ - int ret; - va_list args; - va_start(args, types); - ret =3D virDBusMessageDecodeArgs(msg, types, args); - va_end(args); - return ret; -} - -# define VIR_DBUS_METHOD_CALL_TIMEOUT_MILLIS 30 * 1000 - -/** - * virDBusCreateMethodV: - * @call: pointer to be filled with a method call message - * @destination: bus identifier of the target service - * @path: object path of the target service - * @iface: the interface of the object - * @member: the name of the method in the interface - * @types: type signature for following method arguments - * @args: method arguments - * - * This creates a DBus method call message and saves a - * pointer to it in @call. The @destination, @path, @iface - * and @member parameters identify the object method to - * be invoked. The optional @replyout parameter will be - * filled with any reply to the method call. The method - * can be later invoked using virDBusCall. - * - * The @types parameter is a DBus signature describing - * the method call parameters which will be provided - * as variadic args. Each character in @types must - * correspond to one of the following DBus codes for - * basic types: - * - * 'y' - 8-bit byte, promoted to an 'int' - * 'b' - bool value, promoted to an 'int' - * 'n' - 16-bit signed integer, promoted to an 'int' - * 'q' - 16-bit unsigned integer, promoted to an 'int' - * 'i' - 32-bit signed integer, passed as an 'int' - * 'u' - 32-bit unsigned integer, passed as an 'int' - * 'x' - 64-bit signed integer, passed as a 'long long' - * 't' - 64-bit unsigned integer, passed as an 'unsigned long long' - * 'd' - 8-byte floating point, passed as a 'double' - * 's' - NUL-terminated string, in UTF-8 - * 'o' - NUL-terminated string, representing a valid object path - * 'g' - NUL-terminated string, representing a valid type signature - * - * or use one of the compound types - * - * 'a' - array of values - * 'v' - a variadic type. - * '(' - start of a struct - * ')' - end of a struct - * '{' - start of a dictionary entry (pair of types) - * '}' - start of a dictionary entry (pair of types) - * - * At this time, there is no support for Unix fd's ('h'), which only - * newer DBus supports. - * - * Passing values in variadic args for basic types is - * simple, the value is just passed directly using the - * corresponding C type listed against the type code - * above. Note how any integer value smaller than an - * 'int' is promoted to an 'int' by the C rules for - * variadic args. - * - * Passing values in variadic args for compound types - * requires a little further explanation. - * - * - Variant: the first arg is a string containing - * the type signature for the values to be stored - * inside the variant. This is then followed by - * the values corresponding to the type signature - * in the normal manner. - * - * - Array: when 'a' appears in a type signature, it - * must be followed by a single type describing the - * array element type. For example 'as' is an array - * of strings. 'a(is)' is an array of structs, each - * struct containing an int and a string. - * - * The first variadic arg for an array, is an 'int' - * specifying the number of elements in the array. - * This is then followed by additional variadic args, - * one for each element of the array. - * - * - Array reference: when 'a' appears in a type signature, - * followed by '&', this signifies an array passed by - * reference. - * - * Array references may only be used when the - * element values are basic types, or a dict - * entry where both keys and values are using - * the same basic type. - * - * The first variadic arg for an array, is an 'int' - * specifying the number of elements in the array. - * When the element is a basic type, the second - * variadic arg is a pointer to an array containing - * the element values. When the element is a dict - * entry, the second variadic arg is a pointer to - * an array containing the dict keys, and the - * third variadic arg is a pointer to an array - * containing the dict values. - * - * - Struct: when a '(' appears in a type signature, - * it must be followed by one or more types describing - * the elements in the array, terminated by a ')'. - * - * - Dict entry: when a '{' appears in a type signature it - * must be followed by exactly two types, one describing - * the type of the hash key, the other describing the - * type of the hash entry. The hash key type must be - * a basic type, not a compound type. - * - * Example signatures, with their corresponding variadic - * args: - * - * - "biiss" - some basic types - * - * (true, 7, 42, "hello", "world") - * - * - "as" - an array with a basic type element - * - * (3, "one", "two", "three") - * - * - "a(is)" - an array with a struct element - * - * (3, 1, "one", 2, "two", 3, "three") - * - * - "svs" - some basic types with a variant as an int - * - * ("hello", "i", 3, "world") - * - * - "svs" - some basic types with a variant as an array of ints - * - * ("hello", "ai", 4, 1, 2, 3, 4, "world") - * - * - "a{ss}" - a hash table (aka array + dict entry) - * - * (3, "title", "Mr", "forename", "Joe", "surname", "Bloggs") - * - * - "a{sv}" - a hash table (aka array + dict entry) - * - * (3, "email", "s", "joe@blogs.com", "age", "i", 35, - * "address", "as", 3, "Some house", "Some road", "some city") - */ -int virDBusCreateMethodV(DBusMessage **call, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, - va_list args) -{ - if (!(*call =3D dbus_message_new_method_call(destination, - path, - iface, - member))) { - virReportOOMError(); - return -1; - } - - if (virDBusMessageEncodeArgs(*call, types, args) < 0) { - virDBusMessageUnref(*call); - *call =3D NULL; - return -1; - } - - return 0; -} - - -/** - * virDBusCreateMethod: - * @call: pointer to be filled with a method call message - * @destination: bus identifier of the target service - * @path: object path of the target service - * @iface: the interface of the object - * @member: the name of the method in the interface - * @types: type signature for following method arguments - * @...: method arguments - * - * See virDBusCreateMethodV for a description of the - * behaviour of this method. - */ -int virDBusCreateMethod(DBusMessage **call, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, ...) -{ - va_list args; - int ret; - - va_start(args, types); - ret =3D virDBusCreateMethodV(call, destination, path, - iface, member, types, args); - va_end(args); - - return ret; -} - - -/** - * virDBusCreateReplyV: - * @reply: pointer to be filled with a method reply message - * @types: type signature for following method arguments - * @args: method arguments - * - * This creates a DBus method reply message and saves a - * pointer to it in @reply. - * - * The @types parameter is a DBus signature describing - * the method call parameters which will be provided - * as variadic args. See virDBusCreateMethodV for a - * description of this parameter. - */ -int virDBusCreateReplyV(DBusMessage **reply, - const char *types, - va_list args) -{ - if (!(*reply =3D dbus_message_new(DBUS_MESSAGE_TYPE_METHOD_RETURN))) { - virReportOOMError(); - return -1; - } - - if (virDBusMessageEncodeArgs(*reply, types, args) < 0) { - virDBusMessageUnref(*reply); - *reply =3D NULL; - return -1; - } - - return 0; -} - - -/** - * virDBusCreateReply: - * @reply: pointer to be filled with a method reply message - * @types: type signature for following method arguments - * @...: method arguments - * - * See virDBusCreateReplyV for a description of the - * behaviour of this method. - */ -int virDBusCreateReply(DBusMessage **reply, - const char *types, ...) -{ - va_list args; - int ret; - - va_start(args, types); - ret =3D virDBusCreateReplyV(reply, types, args); - va_end(args); - - return ret; -} - - -/** - * virDBusCall: - * @conn: a DBus connection - * @call: pointer to a message to send - * @replyout: pointer to receive reply message, or NULL - * @error: pointer to receive error message - * - * This invokes a method encoded in @call on a remote - * service on the DBus bus @conn. The optional @replyout - * parameter will be filled with any reply to the method - * call. The virDBusMethodReply method can be used to - * decode the return values. - * - * If @error is NULL then a libvirt error will be raised - * when a DBus error is received and the return value will - * be -1. If @error is non-NULL then any DBus error will - * be saved into that object and the return value will - * be 0. - * - * Returns 0 on success, or -1 upon error - */ -static int -virDBusCall(DBusConnection *conn, - DBusMessage *call, - DBusMessage **replyout, - virErrorPtr error) - -{ - DBusMessage *reply =3D NULL; - DBusError localerror; - int ret =3D -1; - const char *iface, *member, *path, *dest; - - dbus_error_init(&localerror); - if (error) - memset(error, 0, sizeof(*error)); - - iface =3D dbus_message_get_interface(call); - member =3D dbus_message_get_member(call); - path =3D dbus_message_get_path(call); - dest =3D dbus_message_get_destination(call); - - PROBE(DBUS_METHOD_CALL, - "'%s.%s' on '%s' at '%s'", - iface, member, path, dest); - - if (!(reply =3D dbus_connection_send_with_reply_and_block(conn, - call, - VIR_DBUS_METHO= D_CALL_TIMEOUT_MILLIS, - &localerror)))= { - PROBE(DBUS_METHOD_ERROR, - "'%s.%s' on '%s' at '%s' error %s: %s", - iface, member, path, dest, - localerror.name, - localerror.message); - if (error) { - error->level =3D VIR_ERR_ERROR; - error->code =3D VIR_ERR_DBUS_SERVICE; - error->domain =3D VIR_FROM_DBUS; - error->message =3D g_strdup(localerror.message); - error->str1 =3D g_strdup(localerror.name); - ret =3D 0; - } else { - virReportError(VIR_ERR_DBUS_SERVICE, _("%s: %s"), member, - localerror.message ? : _("unknown error")); - } - goto cleanup; - } - - PROBE(DBUS_METHOD_REPLY, - "'%s.%s' on '%s' at '%s'", - iface, member, path, dest); - - ret =3D 0; - - cleanup: - if (ret < 0 && error) - virResetError(error); - dbus_error_free(&localerror); - if (reply) { - if (ret =3D=3D 0 && replyout) - *replyout =3D reply; - else - virDBusMessageUnref(reply); - } - return ret; -} - - -/** - * virDBusCallMethod: - * @conn: a DBus connection - * @replyout: pointer to receive reply message, or NULL - * @destination: bus identifier of the target service - * @path: object path of the target service - * @iface: the interface of the object - * @member: the name of the method in the interface - * @types: type signature for following method arguments - * @...: method arguments - * - * This invokes a method on a remote service on the - * DBus bus @conn. The @destination, @path, @iface - * and @member parameters identify the object method to - * be invoked. The optional @replyout parameter will be - * filled with any reply to the method call. The - * virDBusMethodReply method can be used to decode the - * return values. - * - * The @types parameter is a DBus signature describing - * the method call parameters which will be provided - * as variadic args. See virDBusCreateMethodV for a - * description of this parameter. - * - * - * If @error is NULL then a libvirt error will be raised - * when a DBus error is received and the return value will - * be -1. If @error is non-NULL then any DBus error will - * be saved into that object and the return value will - * be 0. If an error occurs while encoding method args - * the return value will always be -1 regardless of whether - * @error is set. - * - * Returns 0 on success, or -1 upon error - */ -int virDBusCallMethod(DBusConnection *conn, - DBusMessage **replyout, - virErrorPtr error, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, ...) -{ - DBusMessage *call =3D NULL; - int ret =3D -1; - va_list args; - - va_start(args, types); - ret =3D virDBusCreateMethodV(&call, destination, path, - iface, member, types, args); - va_end(args); - if (ret < 0) - goto cleanup; - - ret =3D virDBusCall(conn, call, replyout, error); - - cleanup: - virDBusMessageUnref(call); - return ret; -} - - -static int virDBusIsServiceInList(const char *listMethod, const char *name) -{ - DBusConnection *conn; - DBusMessage *reply =3D NULL; - DBusMessageIter iter, sub; - int ret =3D -1; - - if (!virDBusHasSystemBus()) - return -2; - - if (!(conn =3D virDBusGetSystemBus())) - return -1; - - if (virDBusCallMethod(conn, - &reply, - NULL, - "org.freedesktop.DBus", - "/org/freedesktop/DBus", - "org.freedesktop.DBus", - listMethod, - NULL) < 0) - return ret; - - if (!dbus_message_iter_init(reply, &iter) || - dbus_message_iter_get_arg_type(&iter) !=3D DBUS_TYPE_ARRAY) { - virReportError(VIR_ERR_INTERNAL_ERROR, "%s", - _("Reply message incorrect")); - goto cleanup; - } - - ret =3D -2; - dbus_message_iter_recurse(&iter, &sub); - while (dbus_message_iter_get_arg_type(&sub) =3D=3D DBUS_TYPE_STRING) { - const char *service =3D NULL; - - dbus_message_iter_get_basic(&sub, &service); - dbus_message_iter_next(&sub); - - if (STREQ(service, name)) { - ret =3D 0; - break; - } - } - - cleanup: - virDBusMessageUnref(reply); - return ret; -} - -/** - * virDBusIsServiceEnabled: - * @name: service name - * - * Returns 0 if service is available, -1 on fatal error, or -2 if service = is not available - */ -int virDBusIsServiceEnabled(const char *name) -{ - int ret =3D virDBusIsServiceInList("ListActivatableNames", name); - - VIR_DEBUG("Service %s is %s", name, ret ? "unavailable" : "available"); - - return ret; -} - -/** - * virDBusIsServiceRegistered - * @name: service name - * - * Returns 0 if service is registered, -1 on fatal error, or -2 if service= is not registered - */ -int virDBusIsServiceRegistered(const char *name) -{ - int ret =3D virDBusIsServiceInList("ListNames", name); - - VIR_DEBUG("Service %s is %s", name, ret ? "not registered" : "register= ed"); - - return ret; -} - -void virDBusMessageUnref(DBusMessage *msg) -{ - if (msg) - dbus_message_unref(msg); -} - -#else /* ! WITH_DBUS */ -void virDBusSetSharedBus(bool shared G_GNUC_UNUSED) -{ - /* nothing */ -} - -DBusConnection *virDBusGetSystemBus(void) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return NULL; -} - - -bool -virDBusHasSystemBus(void) -{ - VIR_DEBUG("DBus support not compiled into this binary"); - return false; -} - -void virDBusCloseSystemBus(void) -{ - /* nothing */ -} - -DBusConnection *virDBusGetSessionBus(void) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return NULL; -} - -int virDBusCreateMethod(DBusMessage **call G_GNUC_UNUSED, - const char *destination G_GNUC_UNUSED, - const char *path G_GNUC_UNUSED, - const char *iface G_GNUC_UNUSED, - const char *member G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, ...) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusCreateMethodV(DBusMessage **call G_GNUC_UNUSED, - const char *destination G_GNUC_UNUSED, - const char *path G_GNUC_UNUSED, - const char *iface G_GNUC_UNUSED, - const char *member G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, - va_list args G_GNUC_UNUSED) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusCreateReplyV(DBusMessage **reply G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, - va_list args G_GNUC_UNUSED) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusCreateReply(DBusMessage **reply G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, ...) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusCallMethod(DBusConnection *conn G_GNUC_UNUSED, - DBusMessage **reply G_GNUC_UNUSED, - virErrorPtr error G_GNUC_UNUSED, - const char *destination G_GNUC_UNUSED, - const char *path G_GNUC_UNUSED, - const char *iface G_GNUC_UNUSED, - const char *member G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, ...) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - - -int virDBusMessageEncode(DBusMessage* msg G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, - ...) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusMessageDecode(DBusMessage* msg G_GNUC_UNUSED, - const char *types G_GNUC_UNUSED, - ...) -{ - virReportError(VIR_ERR_INTERNAL_ERROR, - "%s", _("DBus support not compiled into this binary")); - return -1; -} - -int virDBusIsServiceEnabled(const char *name G_GNUC_UNUSED) -{ - VIR_DEBUG("DBus support not compiled into this binary"); - return -2; -} - -int virDBusIsServiceRegistered(const char *name G_GNUC_UNUSED) -{ - VIR_DEBUG("DBus support not compiled into this binary"); - return -2; -} - -void virDBusMessageUnref(DBusMessage *msg G_GNUC_UNUSED) -{ - /* nothing */ -} -#endif /* ! WITH_DBUS */ - -bool virDBusErrorIsUnknownMethod(virErrorPtr err) -{ - return err->domain =3D=3D VIR_FROM_DBUS && - err->code =3D=3D VIR_ERR_DBUS_SERVICE && - err->level =3D=3D VIR_ERR_ERROR && - STREQ_NULLABLE("org.freedesktop.DBus.Error.UnknownMethod", - err->str1); -} diff --git a/src/util/virdbus.h b/src/util/virdbus.h deleted file mode 100644 index 083c074d59..0000000000 --- a/src/util/virdbus.h +++ /dev/null @@ -1,76 +0,0 @@ -/* - * virdbus.h: helper for using DBus - * - * Copyright (C) 2012-2013 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 - * . - * - */ - -#pragma once - -#ifdef WITH_DBUS -# undef interface /* Work around namespace pollution in mingw's rpc.h */ -# include -#else -# define DBusConnection void -# define DBusMessage void -#endif -#include "internal.h" - -#include - -void virDBusSetSharedBus(bool shared); - -DBusConnection *virDBusGetSystemBus(void); -bool virDBusHasSystemBus(void); -void virDBusCloseSystemBus(void); -DBusConnection *virDBusGetSessionBus(void); - -int virDBusCreateMethod(DBusMessage **call, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, ...); -int virDBusCreateMethodV(DBusMessage **call, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, - va_list args); -int virDBusCreateReply(DBusMessage **reply, - const char *types, ...); -int virDBusCreateReplyV(DBusMessage **reply, - const char *types, - va_list args); - -int virDBusCallMethod(DBusConnection *conn, - DBusMessage **reply, - virErrorPtr error, - const char *destination, - const char *path, - const char *iface, - const char *member, - const char *types, ...); -int virDBusMessageDecode(DBusMessage *msg, - const char *types, ...); -void virDBusMessageUnref(DBusMessage *msg); - -int virDBusIsServiceEnabled(const char *name); -int virDBusIsServiceRegistered(const char *name); - -bool virDBusErrorIsUnknownMethod(virErrorPtr err); diff --git a/src/util/virdbuspriv.h b/src/util/virdbuspriv.h deleted file mode 100644 index 5b4fe217f9..0000000000 --- a/src/util/virdbuspriv.h +++ /dev/null @@ -1,56 +0,0 @@ -/* - * virdbuspriv.h: internal APIs for testing DBus code - * - * Copyright (C) 2012-2014 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 - * . - * - */ - -#ifndef LIBVIRT_VIRDBUSPRIV_H_ALLOW -# error "virdbuspriv.h may only be included by virdbus.c or test suites" -#endif /* LIBVIRT_VIRDBUSPRIV_H_ALLOW */ - -#pragma once - -#include "virdbus.h" - -#if defined(WITH_DBUS) && !WITH_DBUSBASICVALUE -/* Copied (and simplified) from dbus 1.6.12, for use with older dbus heade= rs */ -typedef union -{ - dbus_int16_t i16; /**< as int16 */ - dbus_uint16_t u16; /**< as int16 */ - dbus_int32_t i32; /**< as int32 */ - dbus_uint32_t u32; /**< as int32 */ - dbus_bool_t bool_val; /**< as boolean */ - dbus_int64_t i64; /**< as int64 */ - dbus_uint64_t u64; /**< as int64 */ - double dbl; /**< as double */ - unsigned char byt; /**< as byte */ -} DBusBasicValue; -#endif - -int virDBusMessageEncodeArgs(DBusMessage* msg, - const char *types, - va_list args); - -int virDBusMessageDecodeArgs(DBusMessage* msg, - const char *types, - va_list args); - -int virDBusMessageEncode(DBusMessage* msg, - const char *types, - ...); diff --git a/tests/meson.build b/tests/meson.build index 356286839a..f4fbb25e66 100644 --- a/tests/meson.build +++ b/tests/meson.build @@ -86,12 +86,6 @@ if conf.has('WITH_BHYVE') ] endif =20 -if conf.has('WITH_DBUS') - mock_libs +=3D [ - { 'name': 'virdbusmock', 'deps': [ dbus_dep ] }, - ] -endif - if conf.has('WITH_LIBXL') mock_libs +=3D [ { 'name': 'xlmock', 'sources': [ 'libxlmock.c' ], 'deps': [ libxl_dep = ] }, @@ -360,13 +354,6 @@ if conf.has('WITH_BHYVE') ] endif =20 -if conf.has('WITH_DBUS') - tests +=3D [ - { 'name': 'virdbustest', 'deps': [ dbus_dep ] }, - ] - -endif - if conf.has('WITH_ESX') tests +=3D [ { 'name': 'esxutilstest', 'include': [ esx_inc_dir ] }, diff --git a/tests/virdbusmock.c b/tests/virdbusmock.c deleted file mode 100644 index 0673f7292a..0000000000 --- a/tests/virdbusmock.c +++ /dev/null @@ -1,62 +0,0 @@ -/* - * virdbusmock.c: mocking of dbus message send/reply - * - * Copyright (C) 2013-2014 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 - * . - */ - -#include - -#if defined(WITH_DBUS) && !defined(WIN32) -# include "virmock.h" -# include - -VIR_MOCK_STUB_VOID_ARGS(dbus_connection_set_change_sigpipe, - dbus_bool_t, will_modify_sigpipe) - - -VIR_MOCK_STUB_RET_ARGS(dbus_bus_get, - DBusConnection *, (DBusConnection *)0x1, - DBusBusType, type, - DBusError *, error) - -VIR_MOCK_STUB_VOID_ARGS(dbus_connection_set_exit_on_disconnect, - DBusConnection *, connection, - dbus_bool_t, exit_on_disconnect) - -VIR_MOCK_STUB_RET_ARGS(dbus_connection_set_watch_functions, - dbus_bool_t, 1, - DBusConnection *, connection, - DBusAddWatchFunction, add_function, - DBusRemoveWatchFunction, remove_function, - DBusWatchToggledFunction, toggled_function, - void *, data, - DBusFreeFunction, free_data_function) - -VIR_MOCK_STUB_RET_ARGS(dbus_message_set_reply_serial, - dbus_bool_t, 1, - DBusMessage *, message, - dbus_uint32_t, serial) - - -VIR_MOCK_LINK_RET_ARGS(dbus_connection_send_with_reply_and_block, - DBusMessage *, - DBusConnection *, connection, - DBusMessage *, message, - int, timeout_milliseconds, - DBusError *, error) - -#endif /* WITH_DBUS && !WIN32 */ diff --git a/tests/virdbustest.c b/tests/virdbustest.c deleted file mode 100644 index f9c2fb9587..0000000000 --- a/tests/virdbustest.c +++ /dev/null @@ -1,728 +0,0 @@ -/* - * Copyright (C) 2013, 2014 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 - * . - */ - -#include - -#define LIBVIRT_VIRDBUSPRIV_H_ALLOW -#include "virdbuspriv.h" -#include "virlog.h" -#include "testutils.h" - -VIR_LOG_INIT("tests.dbustest"); - -#define VERIFY(typname, valorig, valnew, fmt) \ - do { \ - VIR_DEBUG("Compare " typname " '" fmt "' to '" \ - fmt "'", valorig, valnew); \ - if (valorig !=3D valnew) { \ - fprintf(stderr, "Failed to round-trip " typname " '" \ - fmt "' to '" fmt "'\n", valorig, valnew); \ - goto cleanup; \ - } \ - } while (0) - -#define VERIFY_STR(typname, valorig, valnew, fmt) \ - do { \ - VIR_DEBUG("Compare " typname " '" fmt "' to '" \ - fmt "'", valorig, valnew); \ - if (STRNEQ(valorig, valnew)) { \ - fprintf(stderr, "Failed to round-trip " typname " '" \ - fmt "' to '" fmt "'\n", valorig, valnew); \ - goto cleanup; \ - } \ - } while (0) - -static int testMessageSimple(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - unsigned char in_byte =3D 200, out_byte =3D 0; - bool in_bool =3D true, out_bool =3D false; - short in_int16 =3D 0xfefe, out_int16 =3D 0; - unsigned short in_uint16 =3D 32000, out_uint16 =3D 0; - int in_int32 =3D 100000000, out_int32 =3D 0; - unsigned int in_uint32 =3D 200000000, out_uint32 =3D 0; - long long in_int64 =3D 1000000000000LL, out_int64 =3D 0; - unsigned long long in_uint64 =3D 2000000000000LL, out_uint64 =3D 0; - double in_double =3D 3.14159265359, out_double =3D 0; - const char *in_string =3D "Hello World"; - char *out_string =3D NULL; - const char *in_objectpath =3D "/org/libvirt/test"; - char *out_objectpath =3D NULL; - const char *in_signature =3D "ybnqiuxtdsog"; - char *out_signature =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "ybnqiuxtdsog", - in_byte, in_bool, - in_int16, in_uint16, - in_int32, in_uint32, - in_int64, in_uint64, - in_double, in_string, - in_objectpath, in_signature) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "ybnqiuxtdsog", - &out_byte, &out_bool, - &out_int16, &out_uint16, - &out_int32, &out_uint32, - &out_int64, &out_uint64, - &out_double, &out_string, - &out_objectpath, &out_signature) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - VERIFY("byte", in_byte, out_byte, "%d"); - VERIFY("bool", in_bool, out_bool, "%d"); - VERIFY("int16", in_int16, out_int16, "%d"); - VERIFY("uint16", in_int16, out_int16, "%d"); - VERIFY("int32", in_int32, out_int32, "%d"); - VERIFY("uint32", in_int32, out_int32, "%d"); - VERIFY("int64", in_int64, out_int64, "%lld"); - VERIFY("uint64", in_int64, out_int64, "%lld"); - VERIFY("double", in_double, out_double, "%lf"); - VERIFY_STR("string", in_string, out_string, "%s"); - VERIFY_STR("objectpath", in_objectpath, out_objectpath, "%s"); - VERIFY_STR("signature", in_signature, out_signature, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_string); - VIR_FREE(out_signature); - VIR_FREE(out_objectpath); - virDBusMessageUnref(msg); - return ret; -} - - -static int testMessageVariant(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_str1 =3D "Hello"; - int in_int32 =3D 100000000, out_int32 =3D 0; - const char *in_str2 =3D "World"; - char *out_str1 =3D NULL, *out_str2 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "svs", - in_str1, - "i", in_int32, - in_str2) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "svs", - &out_str1, - "i", &out_int32, - &out_str2) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - VERIFY_STR("str1", in_str1, out_str1, "%s"); - VERIFY("int32", in_int32, out_int32, "%d"); - VERIFY_STR("str2", in_str2, out_str2, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_str1); - VIR_FREE(out_str2); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageArray(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_str1 =3D "Hello"; - int in_int32a =3D 1000000000, out_int32a =3D 0; - int in_int32b =3D 2000000000, out_int32b =3D 0; - int in_int32c =3D -2000000000, out_int32c =3D 0; - bool in_bool[] =3D { true, false, true }, out_bool[] =3D { false, true= , false}; - const char *in_str2 =3D "World"; - char *out_str1 =3D NULL, *out_str2 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "saiabs", - in_str1, - 3, in_int32a, in_int32b, in_int32c, - 3, in_bool[0], in_bool[1], in_bool[2], - in_str2) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "saiabs", - &out_str1, - 3, &out_int32a, &out_int32b, &out_int32c, - 3, &out_bool[0], &out_bool[1], &out_bool[2], - &out_str2) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - VERIFY_STR("str1", in_str1, out_str1, "%s"); - VERIFY("int32a", in_int32a, out_int32a, "%d"); - VERIFY("int32b", in_int32b, out_int32b, "%d"); - VERIFY("int32c", in_int32c, out_int32c, "%d"); - VERIFY("bool[0]", in_bool[0], out_bool[0], "%d"); - VERIFY("bool[1]", in_bool[1], out_bool[1], "%d"); - VERIFY("bool[2]", in_bool[2], out_bool[2], "%d"); - VERIFY_STR("str2", in_str2, out_str2, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_str1); - VIR_FREE(out_str2); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageEmptyArrayRef(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_strv1[] =3D {}; - size_t out_nstrv1; - char **out_strv1 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "a&s", - 0, in_strv1) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "a&s", - &out_nstrv1, &out_strv1) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - if (out_nstrv1 !=3D 0) { - fprintf(stderr, "Expected 0 string, but got %zu\n", - out_nstrv1); - goto cleanup; - } - - ret =3D 0; - - cleanup: - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageSingleArrayRef(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_strv1[] =3D { - "Fishfood", - }; - char **out_strv1 =3D NULL; - size_t out_nstrv1 =3D 0; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "a&s", - 1, in_strv1) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "a&s", - &out_nstrv1, &out_strv1) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - if (out_nstrv1 !=3D 1) { - fprintf(stderr, "Expected 1 string, but got %zu\n", - out_nstrv1); - goto cleanup; - } - VERIFY_STR("strv1[0]", in_strv1[0], out_strv1[0], "%s"); - - ret =3D 0; - - cleanup: - if (out_strv1) - VIR_FREE(out_strv1[0]); - VIR_FREE(out_strv1); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageArrayRef(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_str1 =3D "Hello"; - int in_int32[] =3D { - 100000000, 2000000000, -2000000000 - }; - bool in_bool[] =3D { true, false, true }; - const char *in_strv1[] =3D { - "Fishfood", - }; - const char *in_strv2[] =3D { - "Hello", "World", - }; - int *out_int32 =3D NULL; - size_t out_nint32 =3D 0; - bool *out_bool =3D NULL; - size_t out_nbool =3D 0; - char **out_strv1 =3D NULL; - char **out_strv2 =3D NULL; - size_t out_nstrv1 =3D 0; - size_t out_nstrv2 =3D 0; - const char *in_str2 =3D "World"; - char *out_str1 =3D NULL, *out_str2 =3D NULL; - size_t i; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "sa&sa&ia&ba&ss", - in_str1, - 1, in_strv1, - 3, in_int32, - 3, in_bool, - 2, in_strv2, - in_str2) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "sa&sa&ia&ba&ss", - &out_str1, - &out_nstrv1, &out_strv1, - &out_nint32, &out_int32, - &out_nbool, &out_bool, - &out_nstrv2, &out_strv2, - &out_str2) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - VERIFY_STR("str1", in_str1, out_str1, "%s"); - if (out_nstrv1 !=3D 1) { - fprintf(stderr, "Expected 1 string, but got %zu\n", - out_nstrv1); - goto cleanup; - } - VERIFY_STR("strv1[0]", in_strv1[0], out_strv1[0], "%s"); - - if (out_nint32 !=3D 3) { - fprintf(stderr, "Expected 3 integers, but got %zu\n", - out_nint32); - goto cleanup; - } - VERIFY("int32a", in_int32[0], out_int32[0], "%d"); - VERIFY("int32b", in_int32[1], out_int32[1], "%d"); - VERIFY("int32c", in_int32[2], out_int32[2], "%d"); - - if (out_nbool !=3D 3) { - fprintf(stderr, "Expected 3 bools, but got %zu\n", - out_nbool); - goto cleanup; - } - VERIFY("bool[0]", in_bool[0], out_bool[0], "%d"); - VERIFY("bool[1]", in_bool[1], out_bool[1], "%d"); - VERIFY("bool[2]", in_bool[2], out_bool[2], "%d"); - - if (out_nstrv2 !=3D 2) { - fprintf(stderr, "Expected 2 strings, but got %zu\n", - out_nstrv2); - goto cleanup; - } - VERIFY_STR("strv2[0]", in_strv2[0], out_strv2[0], "%s"); - VERIFY_STR("strv2[1]", in_strv2[1], out_strv2[1], "%s"); - - VERIFY_STR("str2", in_str2, out_str2, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_int32); - VIR_FREE(out_bool); - VIR_FREE(out_str1); - VIR_FREE(out_str2); - for (i =3D 0; i < out_nstrv1; i++) - VIR_FREE(out_strv1[i]); - VIR_FREE(out_strv1); - for (i =3D 0; i < out_nstrv2; i++) - VIR_FREE(out_strv2[i]); - VIR_FREE(out_strv2); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageStruct(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - unsigned char in_byte =3D 200, out_byte =3D 0; - bool in_bool =3D true, out_bool =3D false; - short in_int16 =3D 12000, out_int16 =3D 0; - unsigned short in_uint16 =3D 32000, out_uint16 =3D 0; - int in_int32 =3D 100000000, out_int32 =3D 0; - unsigned int in_uint32 =3D 200000000, out_uint32 =3D 0; - long long in_int64 =3D -1000000000000LL, out_int64 =3D 0; - unsigned long long in_uint64 =3D 2000000000000LL, out_uint64 =3D 0; - double in_double =3D 3.14159265359, out_double =3D 0; - const char *in_string =3D "Hello World"; - char *out_string =3D NULL; - const char *in_objectpath =3D "/org/libvirt/test"; - char *out_objectpath =3D NULL; - const char *in_signature =3D "ybnqiuxtdsog"; - char *out_signature =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "ybn(qiuxtds)og", - in_byte, in_bool, - in_int16, in_uint16, - in_int32, in_uint32, - in_int64, in_uint64, - in_double, in_string, - in_objectpath, in_signature) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "ybn(qiuxtds)og", - &out_byte, &out_bool, - &out_int16, &out_uint16, - &out_int32, &out_uint32, - &out_int64, &out_uint64, - &out_double, &out_string, - &out_objectpath, &out_signature) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - VERIFY("byte", in_byte, out_byte, "%d"); - VERIFY("bool", in_bool, out_bool, "%d"); - VERIFY("int16", in_int16, out_int16, "%d"); - VERIFY("uint16", in_int16, out_int16, "%d"); - VERIFY("int32", in_int32, out_int32, "%d"); - VERIFY("uint32", in_int32, out_int32, "%d"); - VERIFY("int64", in_int64, out_int64, "%lld"); - VERIFY("uint64", in_int64, out_int64, "%lld"); - VERIFY("double", in_double, out_double, "%lf"); - VERIFY_STR("string", in_string, out_string, "%s"); - VERIFY_STR("objectpath", in_objectpath, out_objectpath, "%s"); - VERIFY_STR("signature", in_signature, out_signature, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_string); - VIR_FREE(out_signature); - VIR_FREE(out_objectpath); - virDBusMessageUnref(msg); - return ret; -} - - -static int testMessageDict(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_str1 =3D "Hello"; - int in_int32a =3D 100000000, out_int32a =3D 0; - const char *in_key1 =3D "turnover"; - int in_int32b =3D 200000000, out_int32b =3D 0; - const char *in_key2 =3D "revenue"; - int in_int32c =3D 300000000, out_int32c =3D 0; - const char *in_key3 =3D "debt"; - const char *in_str2 =3D "World"; - char *out_str1 =3D NULL, *out_str2 =3D NULL; - char *out_key1 =3D NULL, *out_key2 =3D NULL, *out_key3 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "(sa{si}s)", - in_str1, - 3, - in_key1, in_int32a, - in_key2, in_int32b, - in_key3, in_int32c, - in_str2) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "(sa{si}s)", - &out_str1, - 3, - &out_key1, &out_int32a, - &out_key2, &out_int32b, - &out_key3, &out_int32c, - &out_str2) < 0) { - VIR_DEBUG("Failed to decode arguments"); - goto cleanup; - } - - - VERIFY_STR("str1", in_str1, out_str1, "%s"); - VERIFY("int32a", in_int32a, out_int32a, "%d"); - VERIFY("int32b", in_int32b, out_int32b, "%d"); - VERIFY("int32c", in_int32c, out_int32c, "%d"); - VERIFY_STR("key1", in_key1, out_key1, "%s"); - VERIFY_STR("key1", in_key2, out_key2, "%s"); - VERIFY_STR("key1", in_key3, out_key3, "%s"); - VERIFY_STR("str2", in_str2, out_str2, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_str1); - VIR_FREE(out_str2); - VIR_FREE(out_key1); - VIR_FREE(out_key2); - VIR_FREE(out_key3); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageDictRef(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_str1 =3D "Hello"; - const char *in_strv1[] =3D { - "Fruit1", "Apple", - "Fruit2", "Orange", - "Fruit3", "Kiwi", - }; - const char *in_str2 =3D "World"; - char *out_str1 =3D NULL; - size_t out_nint32 =3D 0; - char **out_strv1 =3D NULL; - char *out_str2 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "(sa&{ss}s)", - in_str1, - 3, in_strv1, - in_str2) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "(sa&{ss}s)", - &out_str1, - &out_nint32, - &out_strv1, - &out_str2) < 0) { - VIR_DEBUG("Failed to decode arguments: '%s'", virGetLastErrorMessa= ge()); - goto cleanup; - } - - - VERIFY_STR("str1", in_str1, out_str1, "%s"); - VERIFY_STR("strv1[0]", in_strv1[0], out_strv1[0], "%s"); - VERIFY_STR("strv1[1]", in_strv1[1], out_strv1[1], "%s"); - VERIFY_STR("strv1[2]", in_strv1[2], out_strv1[2], "%s"); - VERIFY_STR("strv1[3]", in_strv1[3], out_strv1[3], "%s"); - VERIFY_STR("strv1[4]", in_strv1[4], out_strv1[4], "%s"); - VERIFY_STR("strv1[5]", in_strv1[5], out_strv1[5], "%s"); - VERIFY_STR("str2", in_str2, out_str2, "%s"); - - ret =3D 0; - - cleanup: - VIR_FREE(out_str1); - VIR_FREE(out_str2); - if (out_strv1) { - VIR_FREE(out_strv1[0]); - VIR_FREE(out_strv1[1]); - VIR_FREE(out_strv1[2]); - VIR_FREE(out_strv1[3]); - VIR_FREE(out_strv1[4]); - VIR_FREE(out_strv1[5]); - } - VIR_FREE(out_strv1); - virDBusMessageUnref(msg); - return ret; -} - -static int testMessageEmptyDictRef(const void *args G_GNUC_UNUSED) -{ - DBusMessage *msg =3D NULL; - int ret =3D -1; - const char *in_strv1[] =3D {}; - size_t out_nint32 =3D 0; - char **out_strv1 =3D NULL; - - if (!(msg =3D dbus_message_new_method_call("org.libvirt.test", - "/org/libvirt/test", - "org.libvirt.test.astrochicke= n", - "cluck"))) { - VIR_DEBUG("Failed to allocate method call"); - goto cleanup; - } - - if (virDBusMessageEncode(msg, - "a&{ss}", - 0, in_strv1) < 0) { - VIR_DEBUG("Failed to encode arguments"); - goto cleanup; - } - - if (virDBusMessageDecode(msg, - "a&{ss}", - &out_nint32, - &out_strv1) < 0) { - VIR_DEBUG("Failed to decode arguments: '%s'", virGetLastErrorMessa= ge()); - goto cleanup; - } - - if (out_nint32 !=3D 0) { - fprintf(stderr, "Unexpected dict entries\n"); - goto cleanup; - } - - ret =3D 0; - - cleanup: - virDBusMessageUnref(msg); - return ret; -} - -static int -mymain(void) -{ - int ret =3D 0; - - if (virTestRun("Test message simple ", testMessageSimple, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message variant ", testMessageVariant, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message array ", testMessageArray, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message array empty ref ", testMessageEmptyArrayR= ef, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message array single ref ", testMessageSingleArra= yRef, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message array ref ", testMessageArrayRef, NULL) <= 0) - ret =3D -1; - if (virTestRun("Test message struct ", testMessageStruct, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message dict ", testMessageDict, NULL) < 0) - ret =3D -1; - if (virTestRun("Test message dict empty ref ", testMessageEmptyDictRef= , NULL) < 0) - ret =3D -1; - if (virTestRun("Test message dict ref ", testMessageDictRef, NULL) < 0) - ret =3D -1; - return ret =3D=3D 0 ? EXIT_SUCCESS : EXIT_FAILURE; -} - -VIR_TEST_MAIN(mymain) --=20 2.26.2