[libvirt] [PATCH] systemd: add debug message when virDBusCallMethod failed

Generate debug message when systemd doesn't support interface org.freedesktop.machine1.Manager. Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virsystemd.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c index 3e69ef6..c631557 100644 --- a/src/util/virsystemd.c +++ b/src/util/virsystemd.c @@ -233,6 +233,7 @@ int virSystemdCreateMachine(const char *name, if (err->code == VIR_ERR_DBUS_SERVICE && STREQ(err->str2, "org.freedesktop.DBus.Error.ServiceUnknown")) { virResetLastError(); + VIR_DEBUG("systemd doesn't support interface org.freedesktop.machine1.Manager"); ret = -2; } goto cleanup; -- 1.8.3.1

On Wed, Sep 04, 2013 at 10:58:23AM +0800, Gao feng wrote:
Generate debug message when systemd doesn't support interface org.freedesktop.machine1.Manager.
Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virsystemd.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c index 3e69ef6..c631557 100644 --- a/src/util/virsystemd.c +++ b/src/util/virsystemd.c @@ -233,6 +233,7 @@ int virSystemdCreateMachine(const char *name, if (err->code == VIR_ERR_DBUS_SERVICE && STREQ(err->str2, "org.freedesktop.DBus.Error.ServiceUnknown")) { virResetLastError(); + VIR_DEBUG("systemd doesn't support interface org.freedesktop.machine1.Manager");
Is this really needed ? The virRaiseError call will have already reported this scenario surely ? Daniel -- |: http://berrange.com -o- http://www.flickr.com/photos/dberrange/ :| |: http://libvirt.org -o- http://virt-manager.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: http://entangle-photo.org -o- http://live.gnome.org/gtk-vnc :|

On 09/05/13 13:03, Daniel P. Berrange wrote:
On Wed, Sep 04, 2013 at 10:58:23AM +0800, Gao feng wrote:
Generate debug message when systemd doesn't support interface org.freedesktop.machine1.Manager.
Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virsystemd.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c index 3e69ef6..c631557 100644 --- a/src/util/virsystemd.c +++ b/src/util/virsystemd.c @@ -233,6 +233,7 @@ int virSystemdCreateMachine(const char *name, if (err->code == VIR_ERR_DBUS_SERVICE && STREQ(err->str2, "org.freedesktop.DBus.Error.ServiceUnknown")) { virResetLastError(); + VIR_DEBUG("systemd doesn't support interface org.freedesktop.machine1.Manager");
Is this really needed ? The virRaiseError call will have already reported this scenario surely ?
Yes, it will. It is actually spamming the log with "error" messages every time you start a VM on a non-systemd host even when it is later successful using the old approach. Peter

On Thu, Sep 05, 2013 at 02:21:53PM +0200, Peter Krempa wrote:
On 09/05/13 13:03, Daniel P. Berrange wrote:
On Wed, Sep 04, 2013 at 10:58:23AM +0800, Gao feng wrote:
Generate debug message when systemd doesn't support interface org.freedesktop.machine1.Manager.
Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virsystemd.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c index 3e69ef6..c631557 100644 --- a/src/util/virsystemd.c +++ b/src/util/virsystemd.c @@ -233,6 +233,7 @@ int virSystemdCreateMachine(const char *name, if (err->code == VIR_ERR_DBUS_SERVICE && STREQ(err->str2, "org.freedesktop.DBus.Error.ServiceUnknown")) { virResetLastError(); + VIR_DEBUG("systemd doesn't support interface org.freedesktop.machine1.Manager");
Is this really needed ? The virRaiseError call will have already reported this scenario surely ?
Yes, it will. It is actually spamming the log with "error" messages every time you start a VM on a non-systemd host even when it is later successful using the old approach.
We likely need to invoke org.freedesktop.DBus.ListActivatableNames and/or org.freedesktop.DBus.NameHasOwner to find out if systemd is available without triggering an error. Daniel -- |: http://berrange.com -o- http://www.flickr.com/photos/dberrange/ :| |: http://libvirt.org -o- http://virt-manager.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: http://entangle-photo.org -o- http://live.gnome.org/gtk-vnc :|

This patch introduces virDBusIsServiceEnabled, we can use this method to get if the service is supported. In one case, if org.freedesktop.machine1 is unavailable on host, we should skip creating machine through systemd. Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virdbus.c | 59 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/util/virdbus.h | 1 + src/util/virsystemd.c | 11 ++-------- 3 files changed, 62 insertions(+), 9 deletions(-) diff --git a/src/util/virdbus.c b/src/util/virdbus.c index 62c31be..29068b0 100644 --- a/src/util/virdbus.c +++ b/src/util/virdbus.c @@ -1207,6 +1207,58 @@ int virDBusMessageRead(DBusMessage *msg, return ret; } +/** + * virDBusIsServiceEnabled: + * @name: service name + */ +bool virDBusIsServiceEnabled(const char *name) +{ + DBusConnection *conn; + DBusMessage *reply = NULL; + DBusMessageIter iter, sub; + bool ret = false; + + if (!virDBusHasSystemBus()) + return ret; + + conn = virDBusGetSystemBus(); + + if (virDBusCallMethod(conn, + &reply, + "org.freedesktop.DBus", + "/org/freedesktop/DBus", + "org.freedesktop.DBus", + "ListActivatableNames", + DBUS_TYPE_INVALID) < 0) { + VIR_DEBUG("ListActivatableNames failed."); + return ret; + } + + if (!dbus_message_iter_init(reply, &iter) || + dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) { + VIR_DEBUG("Reply message incorrect."); + goto cleanup; + } + + dbus_message_iter_recurse(&iter, &sub); + while (dbus_message_iter_get_arg_type(&sub) == DBUS_TYPE_STRING) { + const char *service = NULL; + + dbus_message_iter_get_basic(&sub, &service); + dbus_message_iter_next(&sub); + + if (STREQ(service, name)) { + ret = true; + goto cleanup; + } + } + + cleanup: + VIR_DEBUG("Service %s is %s", name, ret ? "available" : "unavailable"); + dbus_message_unref(reply); + return false; +} + #else /* ! WITH_DBUS */ DBusConnection *virDBusGetSystemBus(void) @@ -1271,4 +1323,11 @@ int virDBusMessageDecode(DBusMessage* msg ATTRIBUTE_UNUSED, return -1; } +bool virDBusIsServiceEnabled(const char *name ATTRIBUTE_UNUSED) +{ + virReportError(VIR_ERR_INTERNAL_ERROR, + "%s", _("DBus support not compiled into this binary")); + return false; +} + #endif /* ! WITH_DBUS */ diff --git a/src/util/virdbus.h b/src/util/virdbus.h index a5aab56..0ce5e1a 100644 --- a/src/util/virdbus.h +++ b/src/util/virdbus.h @@ -45,4 +45,5 @@ int virDBusCallMethod(DBusConnection *conn, int virDBusMessageRead(DBusMessage *msg, const char *types, ...); +bool virDBusIsServiceEnabled(const char *name); #endif /* __VIR_DBUS_H__ */ diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c index 3e69ef6..abbb438 100644 --- a/src/util/virsystemd.c +++ b/src/util/virsystemd.c @@ -145,7 +145,7 @@ int virSystemdCreateMachine(const char *name, char *username = NULL; char *slicename = NULL; - if (!virDBusHasSystemBus()) + if (!virDBusIsServiceEnabled("org.freedesktop.machine1")) return -2; conn = virDBusGetSystemBus(); @@ -228,15 +228,8 @@ int virSystemdCreateMachine(const char *name, (unsigned int)pidleader, rootdir ? rootdir : "", 1, "Slice", "s", - slicename) < 0) { - virErrorPtr err = virGetLastError(); - if (err->code == VIR_ERR_DBUS_SERVICE && - STREQ(err->str2, "org.freedesktop.DBus.Error.ServiceUnknown")) { - virResetLastError(); - ret = -2; - } + slicename) < 0) goto cleanup; - } ret = 0; -- 1.8.3.1

On Tue, Sep 10, 2013 at 11:34:32AM +0800, Gao feng wrote:
This patch introduces virDBusIsServiceEnabled, we can use this method to get if the service is supported.
In one case, if org.freedesktop.machine1 is unavailable on host, we should skip creating machine through systemd.
Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com> --- src/util/virdbus.c | 59 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/util/virdbus.h | 1 + src/util/virsystemd.c | 11 ++-------- 3 files changed, 62 insertions(+), 9 deletions(-)
diff --git a/src/util/virdbus.c b/src/util/virdbus.c index 62c31be..29068b0 100644 --- a/src/util/virdbus.c +++ b/src/util/virdbus.c @@ -1207,6 +1207,58 @@ int virDBusMessageRead(DBusMessage *msg, return ret; }
+/** + * virDBusIsServiceEnabled: + * @name: service name + */ +bool virDBusIsServiceEnabled(const char *name)
IMHO this should be a tri-state so we can distinguish actual 'service not available' from other fatal errors.
+{ + DBusConnection *conn; + DBusMessage *reply = NULL; + DBusMessageIter iter, sub; + bool ret = false; + + if (!virDBusHasSystemBus()) + return ret; + + conn = virDBusGetSystemBus(); + + if (virDBusCallMethod(conn, + &reply, + "org.freedesktop.DBus", + "/org/freedesktop/DBus", + "org.freedesktop.DBus", + "ListActivatableNames", + DBUS_TYPE_INVALID) < 0) { + VIR_DEBUG("ListActivatableNames failed."); + return ret;
In particular this is a fatal error condition that should be treated as such.
+ } + + if (!dbus_message_iter_init(reply, &iter) || + dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY) { + VIR_DEBUG("Reply message incorrect."); + goto cleanup; + } + + dbus_message_iter_recurse(&iter, &sub); + while (dbus_message_iter_get_arg_type(&sub) == DBUS_TYPE_STRING) { + const char *service = NULL; + + dbus_message_iter_get_basic(&sub, &service); + dbus_message_iter_next(&sub); + + if (STREQ(service, name)) { + ret = true; + goto cleanup; + } + } + + cleanup: + VIR_DEBUG("Service %s is %s", name, ret ? "available" : "unavailable"); + dbus_message_unref(reply); + return false; +}
Daniel -- |: http://berrange.com -o- http://www.flickr.com/photos/dberrange/ :| |: http://libvirt.org -o- http://virt-manager.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: http://entangle-photo.org -o- http://live.gnome.org/gtk-vnc :|
participants (3)
-
Daniel P. Berrange
-
Gao feng
-
Peter Krempa