[libvirt] [PATCH 02/12] libxl: Introduce libxl_domain.[ch]

Jim Fehlig jfehlig at suse.com
Fri Aug 30 21:46:48 UTC 2013


Create libxl_domain.[ch] and move all functions operating on
libxlDomainObjPrivate to these files.  This will be useful for
future patches that e.g. add job support for libxlDomainObjPrivate.

Signed-off-by: Jim Fehlig <jfehlig at suse.com>
---
 po/POTFILES.in           |   1 +
 src/Makefile.am          |   1 +
 src/libxl/libxl_conf.c   |   2 +-
 src/libxl/libxl_conf.h   |  18 --
 src/libxl/libxl_domain.c | 469 +++++++++++++++++++++++++++++++++++++++++++++++
 src/libxl/libxl_domain.h |  61 ++++++
 src/libxl/libxl_driver.c | 436 +------------------------------------------
 7 files changed, 535 insertions(+), 453 deletions(-)

diff --git a/po/POTFILES.in b/po/POTFILES.in
index 9a83069..281274e 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -67,6 +67,7 @@ src/lxc/lxc_conf.c
 src/lxc/lxc_controller.c
 src/lxc/lxc_driver.c
 src/lxc/lxc_process.c
+src/libxl/libxl_domain.c
 src/libxl/libxl_driver.c
 src/libxl/libxl_conf.c
 src/network/bridge_driver.c
diff --git a/src/Makefile.am b/src/Makefile.am
index d8b943d..82aefe3 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -657,6 +657,7 @@ XENAPI_DRIVER_SOURCES =						\
 
 LIBXL_DRIVER_SOURCES =						\
 		libxl/libxl_conf.c libxl/libxl_conf.h		\
+		libxl/libxl_domain.c libxl/libxl_domain.h       \
 		libxl/libxl_driver.c libxl/libxl_driver.h
 
 UML_DRIVER_SOURCES =						\
diff --git a/src/libxl/libxl_conf.c b/src/libxl/libxl_conf.c
index f8937a4..f9ffe5d 100644
--- a/src/libxl/libxl_conf.c
+++ b/src/libxl/libxl_conf.c
@@ -39,7 +39,7 @@
 #include "viralloc.h"
 #include "viruuid.h"
 #include "capabilities.h"
-#include "libxl_driver.h"
+#include "libxl_domain.h"
 #include "libxl_conf.h"
 #include "libxl_utils.h"
 #include "virstoragefile.h"
diff --git a/src/libxl/libxl_conf.h b/src/libxl/libxl_conf.h
index 0498012..68e770c 100644
--- a/src/libxl/libxl_conf.h
+++ b/src/libxl/libxl_conf.h
@@ -89,24 +89,6 @@ struct _libxlDriverPrivate {
 typedef struct _libxlEventHookInfo libxlEventHookInfo;
 typedef libxlEventHookInfo *libxlEventHookInfoPtr;
 
-typedef struct _libxlDomainObjPrivate libxlDomainObjPrivate;
-typedef libxlDomainObjPrivate *libxlDomainObjPrivatePtr;
-struct _libxlDomainObjPrivate {
-    virObjectLockable parent;
-
-    /* per domain log stream for libxl messages */
-    FILE *logger_file;
-    xentoollog_logger *logger;
-    /* per domain libxl ctx */
-    libxl_ctx *ctx;
-    /* console */
-    virChrdevsPtr devs;
-    libxl_evgen_domain_death *deathW;
-
-    /* list of libxl timeout registrations */
-    libxlEventHookInfoPtr timerRegistrations;
-};
-
 # define LIBXL_SAVE_MAGIC "libvirt-xml\n \0 \r"
 # define LIBXL_SAVE_VERSION 1
 
diff --git a/src/libxl/libxl_domain.c b/src/libxl/libxl_domain.c
new file mode 100644
index 0000000..1d03797
--- /dev/null
+++ b/src/libxl/libxl_domain.c
@@ -0,0 +1,469 @@
+/*---------------------------------------------------------------------------*/
+/*  Copyright (C) 2011-2013 SUSE LINUX Products GmbH, Nuernberg, Germany.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * Authors:
+ *     Jim Fehlig <jfehlig at suse.com>
+ */
+/*---------------------------------------------------------------------------*/
+
+#include <config.h>
+
+#include "libxl_domain.h"
+
+#include "viralloc.h"
+#include "virfile.h"
+#include "virerror.h"
+#include "virlog.h"
+#include "virstring.h"
+
+#define VIR_FROM_THIS VIR_FROM_LIBXL
+
+
+/* Append an event registration to the list of registrations */
+#define LIBXL_EV_REG_APPEND(head, add)                 \
+    do {                                               \
+        libxlEventHookInfoPtr temp;                    \
+        if (head) {                                    \
+            temp = head;                               \
+            while (temp->next)                         \
+                temp = temp->next;                     \
+            temp->next = add;                          \
+        } else {                                       \
+            head = add;                                \
+        }                                              \
+    } while (0)
+
+/* Remove an event registration from the list of registrations */
+#define LIBXL_EV_REG_REMOVE(head, del)                 \
+    do {                                               \
+        libxlEventHookInfoPtr temp;                    \
+        if (head == del) {                             \
+            head = head->next;                         \
+        } else {                                       \
+            temp = head;                               \
+            while (temp->next && temp->next != del)    \
+                temp = temp->next;                     \
+            if (temp->next) {                          \
+                temp->next = del->next;                \
+            }                                          \
+        }                                              \
+    } while (0)
+
+/* Object used to store info related to libxl event registrations */
+struct _libxlEventHookInfo {
+    libxlEventHookInfoPtr next;
+    libxlDomainObjPrivatePtr priv;
+    void *xl_priv;
+    int id;
+};
+
+static virClassPtr libxlDomainObjPrivateClass;
+
+static void
+libxlDomainObjPrivateDispose(void *obj);
+
+static int
+libxlDomainObjPrivateOnceInit(void)
+{
+    if (!(libxlDomainObjPrivateClass = virClassNew(virClassForObjectLockable(),
+                                                   "libxlDomainObjPrivate",
+                                                   sizeof(libxlDomainObjPrivate),
+                                                   libxlDomainObjPrivateDispose)))
+        return -1;
+
+    return 0;
+}
+
+VIR_ONCE_GLOBAL_INIT(libxlDomainObjPrivate)
+
+static void
+libxlDomainObjEventHookInfoFree(void *obj)
+{
+    libxlEventHookInfoPtr info = obj;
+
+    /* Drop reference on libxlDomainObjPrivate */
+    virObjectUnref(info->priv);
+    VIR_FREE(info);
+}
+
+static void
+libxlDomainObjFDEventCallback(int watch ATTRIBUTE_UNUSED,
+                              int fd,
+                              int vir_events,
+                              void *fd_info)
+{
+    libxlEventHookInfoPtr info = fd_info;
+    int events = 0;
+
+    virObjectLock(info->priv);
+    if (vir_events & VIR_EVENT_HANDLE_READABLE)
+        events |= POLLIN;
+    if (vir_events & VIR_EVENT_HANDLE_WRITABLE)
+        events |= POLLOUT;
+    if (vir_events & VIR_EVENT_HANDLE_ERROR)
+        events |= POLLERR;
+    if (vir_events & VIR_EVENT_HANDLE_HANGUP)
+        events |= POLLHUP;
+
+    virObjectUnlock(info->priv);
+    libxl_osevent_occurred_fd(info->priv->ctx, info->xl_priv, fd, 0, events);
+}
+
+static int
+libxlDomainObjFDRegisterEventHook(void *priv,
+                                  int fd,
+                                  void **hndp,
+                                  short events,
+                                  void *xl_priv)
+{
+    int vir_events = VIR_EVENT_HANDLE_ERROR;
+    libxlEventHookInfoPtr info;
+
+    if (VIR_ALLOC(info) < 0)
+        return -1;
+
+    info->priv = priv;
+    /*
+     * Take a reference on the domain object.  Reference is dropped in
+     * libxlDomainObjEventHookInfoFree, ensuring the domain object outlives
+     * the fd event objects.
+     */
+    virObjectRef(info->priv);
+    info->xl_priv = xl_priv;
+
+    if (events & POLLIN)
+        vir_events |= VIR_EVENT_HANDLE_READABLE;
+    if (events & POLLOUT)
+        vir_events |= VIR_EVENT_HANDLE_WRITABLE;
+
+    info->id = virEventAddHandle(fd, vir_events, libxlDomainObjFDEventCallback,
+                                 info, libxlDomainObjEventHookInfoFree);
+    if (info->id < 0) {
+        virObjectUnref(info->priv);
+        VIR_FREE(info);
+        return -1;
+    }
+
+    *hndp = info;
+
+    return 0;
+}
+
+static int
+libxlDomainObjFDModifyEventHook(void *priv ATTRIBUTE_UNUSED,
+                                int fd ATTRIBUTE_UNUSED,
+                                void **hndp,
+                                short events)
+{
+    libxlEventHookInfoPtr info = *hndp;
+    int vir_events = VIR_EVENT_HANDLE_ERROR;
+
+    virObjectLock(info->priv);
+    if (events & POLLIN)
+        vir_events |= VIR_EVENT_HANDLE_READABLE;
+    if (events & POLLOUT)
+        vir_events |= VIR_EVENT_HANDLE_WRITABLE;
+
+    virEventUpdateHandle(info->id, vir_events);
+    virObjectUnlock(info->priv);
+
+    return 0;
+}
+
+static void
+libxlDomainObjFDDeregisterEventHook(void *priv ATTRIBUTE_UNUSED,
+                                    int fd ATTRIBUTE_UNUSED,
+                                    void *hnd)
+{
+    libxlEventHookInfoPtr info = hnd;
+    libxlDomainObjPrivatePtr p = info->priv;
+
+    virObjectLock(p);
+    virEventRemoveHandle(info->id);
+    virObjectUnlock(p);
+}
+
+static void
+libxlDomainObjTimerCallback(int timer ATTRIBUTE_UNUSED, void *timer_info)
+{
+    libxlEventHookInfoPtr info = timer_info;
+    libxlDomainObjPrivatePtr p = info->priv;
+
+    virObjectLock(p);
+    /*
+     * libxl expects the event to be deregistered when calling
+     * libxl_osevent_occurred_timeout, but we dont want the event info
+     * destroyed.  Disable the timeout and only remove it after returning
+     * from libxl.
+     */
+    virEventUpdateTimeout(info->id, -1);
+    virObjectUnlock(p);
+    libxl_osevent_occurred_timeout(p->ctx, info->xl_priv);
+    virObjectLock(p);
+    /*
+     * Timeout could have been freed while the lock was dropped.
+     * Only remove it from the list if it still exists.
+     */
+    if (virEventRemoveTimeout(info->id) == 0)
+        LIBXL_EV_REG_REMOVE(p->timerRegistrations, info);
+    virObjectUnlock(p);
+}
+
+static int
+libxlDomainObjTimeoutRegisterEventHook(void *priv,
+                                       void **hndp,
+                                       struct timeval abs_t,
+                                       void *xl_priv)
+{
+    libxlEventHookInfoPtr info;
+    struct timeval now;
+    struct timeval res;
+    static struct timeval zero;
+    int timeout;
+
+    if (VIR_ALLOC(info) < 0)
+        return -1;
+
+    info->priv = priv;
+    /*
+     * Also take a reference on the domain object.  Reference is dropped in
+     * libxlDomainObjEventHookInfoFree, ensuring the domain object outlives the
+     * timeout event objects.
+     */
+    virObjectRef(info->priv);
+    info->xl_priv = xl_priv;
+
+    gettimeofday(&now, NULL);
+    timersub(&abs_t, &now, &res);
+    /* Ensure timeout is not overflowed */
+    if (timercmp(&res, &zero, <)) {
+        timeout = 0;
+    } else if (res.tv_sec > INT_MAX / 1000) {
+        timeout = INT_MAX;
+    } else {
+        timeout = res.tv_sec * 1000 + (res.tv_usec + 999) / 1000;
+    }
+    info->id = virEventAddTimeout(timeout, libxlDomainObjTimerCallback,
+                                  info, libxlDomainObjEventHookInfoFree);
+    if (info->id < 0) {
+        virObjectUnref(info->priv);
+        VIR_FREE(info);
+        return -1;
+    }
+
+    virObjectLock(info->priv);
+    LIBXL_EV_REG_APPEND(info->priv->timerRegistrations, info);
+    virObjectUnlock(info->priv);
+    *hndp = info;
+
+    return 0;
+}
+
+/*
+ * Note:  There are two changes wrt timeouts starting with xen-unstable
+ * changeset 26469:
+ *
+ * 1. Timeout modify callbacks will only be invoked with an abs_t of {0,0},
+ * i.e. make the timeout fire immediately.  Prior to this commit, timeout
+ * modify callbacks were never invoked.
+ *
+ * 2. Timeout deregister hooks will no longer be called.
+ */
+static int
+libxlDomainObjTimeoutModifyEventHook(void *priv ATTRIBUTE_UNUSED,
+                                     void **hndp,
+                                     struct timeval abs_t ATTRIBUTE_UNUSED)
+{
+    libxlEventHookInfoPtr info = *hndp;
+
+    virObjectLock(info->priv);
+    /* Make the timeout fire */
+    virEventUpdateTimeout(info->id, 0);
+    virObjectUnlock(info->priv);
+
+    return 0;
+}
+
+static void
+libxlDomainObjTimeoutDeregisterEventHook(void *priv ATTRIBUTE_UNUSED,
+                                         void *hnd)
+{
+    libxlEventHookInfoPtr info = hnd;
+    libxlDomainObjPrivatePtr p = info->priv;
+
+    virObjectLock(p);
+    /*
+     * Only remove the timeout from the list if removal from the
+     * event loop is successful.
+     */
+    if (virEventRemoveTimeout(info->id) == 0)
+        LIBXL_EV_REG_REMOVE(p->timerRegistrations, info);
+    virObjectUnlock(p);
+}
+
+
+static const libxl_osevent_hooks libxl_event_callbacks = {
+    .fd_register = libxlDomainObjFDRegisterEventHook,
+    .fd_modify = libxlDomainObjFDModifyEventHook,
+    .fd_deregister = libxlDomainObjFDDeregisterEventHook,
+    .timeout_register = libxlDomainObjTimeoutRegisterEventHook,
+    .timeout_modify = libxlDomainObjTimeoutModifyEventHook,
+    .timeout_deregister = libxlDomainObjTimeoutDeregisterEventHook,
+};
+
+static void *
+libxlDomainObjPrivateAlloc(void)
+{
+    libxlDomainObjPrivatePtr priv;
+
+    if (libxlDomainObjPrivateInitialize() < 0)
+        return NULL;
+
+    if (!(priv = virObjectLockableNew(libxlDomainObjPrivateClass)))
+        return NULL;
+
+    if (!(priv->devs = virChrdevAlloc())) {
+        virObjectUnref(priv);
+        return NULL;
+    }
+
+    return priv;
+}
+
+static void
+libxlDomainObjPrivateDispose(void *obj)
+{
+    libxlDomainObjPrivatePtr priv = obj;
+
+    if (priv->deathW)
+        libxl_evdisable_domain_death(priv->ctx, priv->deathW);
+
+    virChrdevFree(priv->devs);
+
+    xtl_logger_destroy(priv->logger);
+    if (priv->logger_file)
+        VIR_FORCE_FCLOSE(priv->logger_file);
+
+    libxl_ctx_free(priv->ctx);
+}
+
+static void
+libxlDomainObjPrivateFree(void *data)
+{
+    libxlDomainObjPrivatePtr priv = data;
+
+    if (priv->deathW) {
+        libxl_evdisable_domain_death(priv->ctx, priv->deathW);
+        priv->deathW = NULL;
+    }
+
+    virObjectUnref(priv);
+}
+
+virDomainXMLPrivateDataCallbacks libxlDomainXMLPrivateDataCallbacks = {
+    .alloc = libxlDomainObjPrivateAlloc,
+    .free = libxlDomainObjPrivateFree,
+};
+
+
+static int
+libxlDomainDeviceDefPostParse(virDomainDeviceDefPtr dev,
+                              virDomainDefPtr def,
+                              virCapsPtr caps ATTRIBUTE_UNUSED,
+                              void *opaque ATTRIBUTE_UNUSED)
+{
+    if (dev->type == VIR_DOMAIN_DEVICE_CHR &&
+        dev->data.chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_CONSOLE &&
+        dev->data.chr->targetType == VIR_DOMAIN_CHR_CONSOLE_TARGET_TYPE_NONE &&
+        STRNEQ(def->os.type, "hvm"))
+        dev->data.chr->targetType = VIR_DOMAIN_CHR_CONSOLE_TARGET_TYPE_XEN;
+
+    return 0;
+}
+
+virDomainDefParserConfig libxlDomainDefParserConfig = {
+    .macPrefix = { 0x00, 0x16, 0x3e },
+    .devicesPostParseCallback = libxlDomainDeviceDefPostParse,
+};
+
+int
+libxlDomainObjPrivateInitCtx(virDomainObjPtr vm)
+{
+    libxlDomainObjPrivatePtr priv = vm->privateData;
+    char *log_file;
+    int ret = -1;
+
+    if (priv->ctx)
+        return 0;
+
+    if (virAsprintf(&log_file, "%s/%s.log", LIBXL_LOG_DIR, vm->def->name) < 0)
+        return -1;
+
+    if ((priv->logger_file = fopen(log_file, "a")) == NULL)  {
+        virReportSystemError(errno,
+                             _("failed to open logfile %s"),
+                             log_file);
+        goto cleanup;
+    }
+
+    priv->logger =
+        (xentoollog_logger *)xtl_createlogger_stdiostream(priv->logger_file,
+                                                          XTL_DEBUG, 0);
+    if (!priv->logger) {
+        virReportError(VIR_ERR_INTERNAL_ERROR,
+                       _("cannot create libxenlight logger for domain %s"),
+                       vm->def->name);
+        goto cleanup;
+    }
+
+    if (libxl_ctx_alloc(&priv->ctx, LIBXL_VERSION, 0, priv->logger)) {
+        virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+                       _("Failed libxl context initialization"));
+        goto cleanup;
+    }
+
+    libxl_osevent_register_hooks(priv->ctx, &libxl_event_callbacks, priv);
+
+    ret = 0;
+
+cleanup:
+    VIR_FREE(log_file);
+    return ret;
+}
+
+void
+libxlDomainObjRegisteredTimeoutsCleanup(libxlDomainObjPrivatePtr priv)
+{
+    libxlEventHookInfoPtr info;
+
+    virObjectLock(priv);
+    info = priv->timerRegistrations;
+    while (info) {
+        /*
+         * libxl expects the event to be deregistered when calling
+         * libxl_osevent_occurred_timeout, but we dont want the event info
+         * destroyed.  Disable the timeout and only remove it after returning
+         * from libxl.
+         */
+        virEventUpdateTimeout(info->id, -1);
+        libxl_osevent_occurred_timeout(priv->ctx, info->xl_priv);
+        virEventRemoveTimeout(info->id);
+        info = info->next;
+    }
+    priv->timerRegistrations = NULL;
+    virObjectUnlock(priv);
+}
diff --git a/src/libxl/libxl_domain.h b/src/libxl/libxl_domain.h
new file mode 100644
index 0000000..2797d38
--- /dev/null
+++ b/src/libxl/libxl_domain.h
@@ -0,0 +1,61 @@
+/*---------------------------------------------------------------------------*/
+/*  Copyright (C) 2011-2013 SUSE LINUX Products GmbH, Nuernberg, Germany.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * Authors:
+ *     Jim Fehlig <jfehlig at suse.com>
+ */
+/*---------------------------------------------------------------------------*/
+
+#ifndef LIBXL_DOMAIN_H
+# define LIBXL_DOMAIN_H
+
+# include <libxl.h>
+
+# include "domain_conf.h"
+# include "libxl_conf.h"
+# include "virchrdev.h"
+
+typedef struct _libxlDomainObjPrivate libxlDomainObjPrivate;
+typedef libxlDomainObjPrivate *libxlDomainObjPrivatePtr;
+struct _libxlDomainObjPrivate {
+    virObjectLockable parent;
+
+    /* per domain log stream for libxl messages */
+    FILE *logger_file;
+    xentoollog_logger *logger;
+    /* per domain libxl ctx */
+    libxl_ctx *ctx;
+    /* console */
+    virChrdevsPtr devs;
+    libxl_evgen_domain_death *deathW;
+
+    /* list of libxl timeout registrations */
+    libxlEventHookInfoPtr timerRegistrations;
+};
+
+
+extern virDomainXMLPrivateDataCallbacks libxlDomainXMLPrivateDataCallbacks;
+extern virDomainDefParserConfig libxlDomainDefParserConfig;
+
+
+int
+libxlDomainObjPrivateInitCtx(virDomainObjPtr vm);
+
+void
+libxlDomainObjRegisteredTimeoutsCleanup(libxlDomainObjPrivatePtr priv);
+
+#endif /* LIBXL_DOMAIN_H */
diff --git a/src/libxl/libxl_driver.c b/src/libxl/libxl_driver.c
index 91beb30..ff4f6be 100644
--- a/src/libxl/libxl_driver.c
+++ b/src/libxl/libxl_driver.c
@@ -41,6 +41,7 @@
 #include "viralloc.h"
 #include "viruuid.h"
 #include "vircommand.h"
+#include "libxl_domain.h"
 #include "libxl_driver.h"
 #include "libxl_conf.h"
 #include "xen_xm.h"
@@ -63,45 +64,6 @@
 /* Number of Xen scheduler parameters */
 #define XEN_SCHED_CREDIT_NPARAM   2
 
-/* Append an event registration to the list of registrations */
-#define LIBXL_EV_REG_APPEND(head, add)                 \
-    do {                                               \
-        libxlEventHookInfoPtr temp;                    \
-        if (head) {                                    \
-            temp = head;                               \
-            while (temp->next)                         \
-                temp = temp->next;                     \
-            temp->next = add;                          \
-        } else {                                       \
-            head = add;                                \
-        }                                              \
-    } while (0)
-
-/* Remove an event registration from the list of registrations */
-#define LIBXL_EV_REG_REMOVE(head, del)                 \
-    do {                                               \
-        libxlEventHookInfoPtr temp;                    \
-        if (head == del) {                             \
-            head = head->next;                         \
-        } else {                                       \
-            temp = head;                               \
-            while (temp->next && temp->next != del)    \
-                temp = temp->next;                     \
-            if (temp->next) {                          \
-                temp->next = del->next;                \
-            }                                          \
-        }                                              \
-    } while (0)
-
-/* Object used to store info related to libxl event registrations */
-struct _libxlEventHookInfo {
-    libxlEventHookInfoPtr next;
-    libxlDomainObjPrivatePtr priv;
-    void *xl_priv;
-    int id;
-};
-
-static virClassPtr libxlDomainObjPrivateClass;
 
 static libxlDriverPrivatePtr libxl_driver = NULL;
 
@@ -115,24 +77,6 @@ libxlVmStart(libxlDriverPrivatePtr driver, virDomainObjPtr vm,
              bool start_paused, int restore_fd);
 
 static void
-libxlDomainObjPrivateDispose(void *obj);
-
-/* Function definitions */
-static int
-libxlDomainObjPrivateOnceInit(void)
-{
-    if (!(libxlDomainObjPrivateClass = virClassNew(virClassForObjectLockable(),
-                                                   "libxlDomainObjPrivate",
-                                                   sizeof(libxlDomainObjPrivate),
-                                                   libxlDomainObjPrivateDispose)))
-        return -1;
-
-    return 0;
-}
-
-VIR_ONCE_GLOBAL_INIT(libxlDomainObjPrivate)
-
-static void
 libxlDriverLock(libxlDriverPrivatePtr driver)
 {
     virMutexLock(&driver->lock);
@@ -144,382 +88,6 @@ libxlDriverUnlock(libxlDriverPrivatePtr driver)
     virMutexUnlock(&driver->lock);
 }
 
-static void
-libxlEventHookInfoFree(void *obj)
-{
-    libxlEventHookInfoPtr info = obj;
-
-    /* Drop reference on libxlDomainObjPrivate */
-    virObjectUnref(info->priv);
-    VIR_FREE(info);
-}
-
-static void
-libxlFDEventCallback(int watch ATTRIBUTE_UNUSED,
-                     int fd,
-                     int vir_events,
-                     void *fd_info)
-{
-    libxlEventHookInfoPtr info = fd_info;
-    int events = 0;
-
-    virObjectLock(info->priv);
-    if (vir_events & VIR_EVENT_HANDLE_READABLE)
-        events |= POLLIN;
-    if (vir_events & VIR_EVENT_HANDLE_WRITABLE)
-        events |= POLLOUT;
-    if (vir_events & VIR_EVENT_HANDLE_ERROR)
-        events |= POLLERR;
-    if (vir_events & VIR_EVENT_HANDLE_HANGUP)
-        events |= POLLHUP;
-
-    virObjectUnlock(info->priv);
-    libxl_osevent_occurred_fd(info->priv->ctx, info->xl_priv, fd, 0, events);
-}
-
-static int
-libxlFDRegisterEventHook(void *priv, int fd, void **hndp,
-                         short events, void *xl_priv)
-{
-    int vir_events = VIR_EVENT_HANDLE_ERROR;
-    libxlEventHookInfoPtr info;
-
-    if (VIR_ALLOC(info) < 0)
-        return -1;
-
-    info->priv = priv;
-    /*
-     * Take a reference on the domain object.  Reference is dropped in
-     * libxlEventHookInfoFree, ensuring the domain object outlives the fd
-     * event objects.
-     */
-    virObjectRef(info->priv);
-    info->xl_priv = xl_priv;
-
-    if (events & POLLIN)
-        vir_events |= VIR_EVENT_HANDLE_READABLE;
-    if (events & POLLOUT)
-        vir_events |= VIR_EVENT_HANDLE_WRITABLE;
-
-    info->id = virEventAddHandle(fd, vir_events, libxlFDEventCallback,
-                                 info, libxlEventHookInfoFree);
-    if (info->id < 0) {
-        virObjectUnref(info->priv);
-        VIR_FREE(info);
-        return -1;
-    }
-
-    *hndp = info;
-
-    return 0;
-}
-
-static int
-libxlFDModifyEventHook(void *priv ATTRIBUTE_UNUSED,
-                       int fd ATTRIBUTE_UNUSED,
-                       void **hndp,
-                       short events)
-{
-    libxlEventHookInfoPtr info = *hndp;
-    int vir_events = VIR_EVENT_HANDLE_ERROR;
-
-    virObjectLock(info->priv);
-    if (events & POLLIN)
-        vir_events |= VIR_EVENT_HANDLE_READABLE;
-    if (events & POLLOUT)
-        vir_events |= VIR_EVENT_HANDLE_WRITABLE;
-
-    virEventUpdateHandle(info->id, vir_events);
-    virObjectUnlock(info->priv);
-
-    return 0;
-}
-
-static void
-libxlFDDeregisterEventHook(void *priv ATTRIBUTE_UNUSED,
-                           int fd ATTRIBUTE_UNUSED,
-                           void *hnd)
-{
-    libxlEventHookInfoPtr info = hnd;
-    libxlDomainObjPrivatePtr p = info->priv;
-
-    virObjectLock(p);
-    virEventRemoveHandle(info->id);
-    virObjectUnlock(p);
-}
-
-static void
-libxlTimerCallback(int timer ATTRIBUTE_UNUSED, void *timer_info)
-{
-    libxlEventHookInfoPtr info = timer_info;
-    libxlDomainObjPrivatePtr p = info->priv;
-
-    virObjectLock(p);
-    /*
-     * libxl expects the event to be deregistered when calling
-     * libxl_osevent_occurred_timeout, but we dont want the event info
-     * destroyed.  Disable the timeout and only remove it after returning
-     * from libxl.
-     */
-    virEventUpdateTimeout(info->id, -1);
-    virObjectUnlock(p);
-    libxl_osevent_occurred_timeout(p->ctx, info->xl_priv);
-    virObjectLock(p);
-    /*
-     * Timeout could have been freed while the lock was dropped.
-     * Only remove it from the list if it still exists.
-     */
-    if (virEventRemoveTimeout(info->id) == 0)
-        LIBXL_EV_REG_REMOVE(p->timerRegistrations, info);
-    virObjectUnlock(p);
-}
-
-static int
-libxlTimeoutRegisterEventHook(void *priv,
-                              void **hndp,
-                              struct timeval abs_t,
-                              void *xl_priv)
-{
-    libxlEventHookInfoPtr info;
-    struct timeval now;
-    struct timeval res;
-    static struct timeval zero;
-    int timeout;
-
-    if (VIR_ALLOC(info) < 0)
-        return -1;
-
-    info->priv = priv;
-    /*
-     * Also take a reference on the domain object.  Reference is dropped in
-     * libxlEventHookInfoFree, ensuring the domain object outlives the timeout
-     * event objects.
-     */
-    virObjectRef(info->priv);
-    info->xl_priv = xl_priv;
-
-    gettimeofday(&now, NULL);
-    timersub(&abs_t, &now, &res);
-    /* Ensure timeout is not overflowed */
-    if (timercmp(&res, &zero, <))
-        timeout = 0;
-    else if (res.tv_sec > INT_MAX / 1000)
-        timeout = INT_MAX;
-    else
-        timeout = res.tv_sec * 1000 + (res.tv_usec + 999) / 1000;
-
-    info->id = virEventAddTimeout(timeout, libxlTimerCallback,
-                                  info, libxlEventHookInfoFree);
-    if (info->id < 0) {
-        virObjectUnref(info->priv);
-        VIR_FREE(info);
-        return -1;
-    }
-
-    virObjectLock(info->priv);
-    LIBXL_EV_REG_APPEND(info->priv->timerRegistrations, info);
-    virObjectUnlock(info->priv);
-    *hndp = info;
-
-    return 0;
-}
-
-/*
- * Note:  There are two changes wrt timeouts starting with xen-unstable
- * changeset 26469:
- *
- * 1. Timeout modify callbacks will only be invoked with an abs_t of {0,0},
- * i.e. make the timeout fire immediately.  Prior to this commit, timeout
- * modify callbacks were never invoked.
- *
- * 2. Timeout deregister hooks will no longer be called.
- */
-static int
-libxlTimeoutModifyEventHook(void *priv ATTRIBUTE_UNUSED,
-                            void **hndp,
-                            struct timeval abs_t ATTRIBUTE_UNUSED)
-{
-    libxlEventHookInfoPtr info = *hndp;
-
-    virObjectLock(info->priv);
-    /* Make the timeout fire */
-    virEventUpdateTimeout(info->id, 0);
-    virObjectUnlock(info->priv);
-
-    return 0;
-}
-
-static void
-libxlTimeoutDeregisterEventHook(void *priv ATTRIBUTE_UNUSED,
-                                void *hnd)
-{
-    libxlEventHookInfoPtr info = hnd;
-    libxlDomainObjPrivatePtr p = info->priv;
-
-    virObjectLock(p);
-    /*
-     * Only remove the timeout from the list if removal from the
-     * event loop is successful.
-     */
-    if (virEventRemoveTimeout(info->id) == 0)
-        LIBXL_EV_REG_REMOVE(p->timerRegistrations, info);
-    virObjectUnlock(p);
-}
-
-static void
-libxlRegisteredTimeoutsCleanup(libxlDomainObjPrivatePtr priv)
-{
-    libxlEventHookInfoPtr info;
-
-    virObjectLock(priv);
-    info = priv->timerRegistrations;
-    while (info) {
-        /*
-         * libxl expects the event to be deregistered when calling
-         * libxl_osevent_occurred_timeout, but we dont want the event info
-         * destroyed.  Disable the timeout and only remove it after returning
-         * from libxl.
-         */
-        virEventUpdateTimeout(info->id, -1);
-        libxl_osevent_occurred_timeout(priv->ctx, info->xl_priv);
-        virEventRemoveTimeout(info->id);
-        info = info->next;
-    }
-    priv->timerRegistrations = NULL;
-    virObjectUnlock(priv);
-}
-
-static const libxl_osevent_hooks libxl_event_callbacks = {
-    .fd_register = libxlFDRegisterEventHook,
-    .fd_modify = libxlFDModifyEventHook,
-    .fd_deregister = libxlFDDeregisterEventHook,
-    .timeout_register = libxlTimeoutRegisterEventHook,
-    .timeout_modify = libxlTimeoutModifyEventHook,
-    .timeout_deregister = libxlTimeoutDeregisterEventHook,
-};
-
-static int
-libxlDomainObjPrivateInitCtx(virDomainObjPtr vm)
-{
-    libxlDomainObjPrivatePtr priv = vm->privateData;
-    char *log_file;
-    int ret = -1;
-
-    if (priv->ctx)
-        return 0;
-
-    if (virAsprintf(&log_file, "%s/%s.log", LIBXL_LOG_DIR, vm->def->name) < 0)
-        return -1;
-
-    if ((priv->logger_file = fopen(log_file, "a")) == NULL)  {
-        virReportSystemError(errno,
-                             _("failed to open logfile %s"),
-                             log_file);
-        goto cleanup;
-    }
-
-    priv->logger =
-        (xentoollog_logger *)xtl_createlogger_stdiostream(priv->logger_file,
-                                                          XTL_DEBUG, 0);
-    if (!priv->logger) {
-        virReportError(VIR_ERR_INTERNAL_ERROR,
-                       _("cannot create libxenlight logger for domain %s"),
-                       vm->def->name);
-        goto cleanup;
-    }
-
-    if (libxl_ctx_alloc(&priv->ctx, LIBXL_VERSION, 0, priv->logger)) {
-        virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
-                       _("Failed libxl context initialization"));
-        goto cleanup;
-    }
-
-    libxl_osevent_register_hooks(priv->ctx, &libxl_event_callbacks, priv);
-
-    ret = 0;
-
-cleanup:
-    VIR_FREE(log_file);
-    return ret;
-}
-
-static void *
-libxlDomainObjPrivateAlloc(void)
-{
-    libxlDomainObjPrivatePtr priv;
-
-    if (libxlDomainObjPrivateInitialize() < 0)
-        return NULL;
-
-    if (!(priv = virObjectLockableNew(libxlDomainObjPrivateClass)))
-        return NULL;
-
-    if (!(priv->devs = virChrdevAlloc())) {
-        virObjectUnref(priv);
-        return NULL;
-    }
-
-    return priv;
-}
-
-static void
-libxlDomainObjPrivateDispose(void *obj)
-{
-    libxlDomainObjPrivatePtr priv = obj;
-
-    if (priv->deathW)
-        libxl_evdisable_domain_death(priv->ctx, priv->deathW);
-
-    virChrdevFree(priv->devs);
-
-    xtl_logger_destroy(priv->logger);
-    if (priv->logger_file)
-        VIR_FORCE_FCLOSE(priv->logger_file);
-
-    libxl_ctx_free(priv->ctx);
-}
-
-static void
-libxlDomainObjPrivateFree(void *data)
-{
-    libxlDomainObjPrivatePtr priv = data;
-
-    if (priv->deathW) {
-        libxl_evdisable_domain_death(priv->ctx, priv->deathW);
-        priv->deathW = NULL;
-    }
-
-    virObjectUnref(priv);
-}
-
-virDomainXMLPrivateDataCallbacks libxlDomainXMLPrivateDataCallbacks = {
-    .alloc = libxlDomainObjPrivateAlloc,
-    .free = libxlDomainObjPrivateFree,
-};
-
-
-static int
-libxlDomainDeviceDefPostParse(virDomainDeviceDefPtr dev,
-                              virDomainDefPtr def,
-                              virCapsPtr caps ATTRIBUTE_UNUSED,
-                              void *opaque ATTRIBUTE_UNUSED)
-{
-    if (dev->type == VIR_DOMAIN_DEVICE_CHR &&
-        dev->data.chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_CONSOLE &&
-        dev->data.chr->targetType == VIR_DOMAIN_CHR_CONSOLE_TARGET_TYPE_NONE &&
-        STRNEQ(def->os.type, "hvm"))
-        dev->data.chr->targetType = VIR_DOMAIN_CHR_CONSOLE_TARGET_TYPE_XEN;
-
-    return 0;
-}
-
-
-virDomainDefParserConfig libxlDomainDefParserConfig = {
-    .macPrefix = { 0x00, 0x16, 0x3e },
-    .devicesPostParseCallback = libxlDomainDeviceDefPostParse,
-};
-
-
 /* driver must be locked before calling */
 static void
 libxlDomainEventQueue(libxlDriverPrivatePtr driver, virDomainEventPtr event)
@@ -728,7 +296,7 @@ libxlVmCleanup(libxlDriverPrivatePtr driver,
         vm->newDef = NULL;
     }
 
-    libxlRegisteredTimeoutsCleanup(priv);
+    libxlDomainObjRegisteredTimeoutsCleanup(priv);
 }
 
 /*
-- 
1.8.1.4




More information about the libvir-list mailing list