[libvirt] PATCH: Support events for define/undefine in QEMU

Daniel P. Berrange berrange at redhat.com
Fri Nov 14 17:51:22 UTC 2008


This patch adds support for the DEFINED and UNDEFINED events in the
QEMU drive. This was more involved than I expected, because when the
daemon gets SIGHUP it re-loads config files and we need to broadcast
events for each new config file it finds. So I had to add a callback
to the internal virDomainLoadAllConfigs method.

The LoadConfig method also had a bogus line of code resetting the
domain state to SHUTOFF, which made all your active VMs suddenlly
appear inactive, after the daemon got SIGHUP !

Daniel

diff --git a/src/domain_conf.c b/src/domain_conf.c
--- a/src/domain_conf.c
+++ b/src/domain_conf.c
@@ -3242,18 +3242,20 @@ virDomainObjPtr virDomainLoadConfig(virC
                                     virDomainObjListPtr doms,
                                     const char *configDir,
                                     const char *autostartDir,
-                                    const char *name)
+                                    const char *name,
+                                    virDomainLoadConfigNotify notify,
+                                    void *opaque)
 {
     char *configFile = NULL, *autostartLink = NULL;
     virDomainDefPtr def = NULL;
     virDomainObjPtr dom;
     int autostart;
+    int newVM = 1;
 
     if ((configFile = virDomainConfigFile(conn, configDir, name)) == NULL)
         goto error;
     if ((autostartLink = virDomainConfigFile(conn, autostartDir, name)) == NULL)
         goto error;
-
 
     if ((autostart = virFileLinkPointsTo(autostartLink, configFile)) < 0)
         goto error;
@@ -3261,11 +3263,16 @@ virDomainObjPtr virDomainLoadConfig(virC
     if (!(def = virDomainDefParseFile(conn, caps, configFile)))
         goto error;
 
+    if (virDomainFindByName(doms, def->name))
+        newVM = 0;
+
     if (!(dom = virDomainAssignDef(conn, doms, def)))
         goto error;
 
-    dom->state = VIR_DOMAIN_SHUTOFF;
     dom->autostart = autostart;
+
+    if (notify)
+        (*notify)(dom, newVM, opaque);
 
     return dom;
 
@@ -3280,7 +3287,9 @@ int virDomainLoadAllConfigs(virConnectPt
                             virCapsPtr caps,
                             virDomainObjListPtr doms,
                             const char *configDir,
-                            const char *autostartDir)
+                            const char *autostartDir,
+                            virDomainLoadConfigNotify notify,
+                            void *opaque)
 {
     DIR *dir;
     struct dirent *entry;
@@ -3310,7 +3319,9 @@ int virDomainLoadAllConfigs(virConnectPt
                                   doms,
                                   configDir,
                                   autostartDir,
-                                  entry->d_name);
+                                  entry->d_name,
+                                  notify,
+                                  opaque);
         if (dom)
             dom->persistent = 1;
     }
diff --git a/src/domain_conf.h b/src/domain_conf.h
--- a/src/domain_conf.h
+++ b/src/domain_conf.h
@@ -549,18 +549,26 @@ int virDomainSaveConfig(virConnectPtr co
                         const char *configDir,
                         virDomainDefPtr def);
 
+typedef void (*virDomainLoadConfigNotify)(virDomainObjPtr dom,
+                                          int newDomain,
+                                          void *opaque);
+
 virDomainObjPtr virDomainLoadConfig(virConnectPtr conn,
                                     virCapsPtr caps,
                                     virDomainObjListPtr doms,
                                     const char *configDir,
                                     const char *autostartDir,
-                                    const char *name);
+                                    const char *name,
+                                    virDomainLoadConfigNotify notify,
+                                    void *opaque);
 
 int virDomainLoadAllConfigs(virConnectPtr conn,
                             virCapsPtr caps,
                             virDomainObjListPtr doms,
                             const char *configDir,
-                            const char *autostartDir);
+                            const char *autostartDir,
+                            virDomainLoadConfigNotify notify,
+                            void *opaque);
 
 int virDomainDeleteConfig(virConnectPtr conn,
                           const char *configDir,
diff --git a/src/lxc_driver.c b/src/lxc_driver.c
--- a/src/lxc_driver.c
+++ b/src/lxc_driver.c
@@ -1017,7 +1017,8 @@ static int lxcStartup(void)
                                 lxc_driver->caps,
                                 &lxc_driver->domains,
                                 lxc_driver->configDir,
-                                lxc_driver->autostartDir) < 0) {
+                                lxc_driver->autostartDir,
+                                NULL, NULL) < 0) {
         lxcShutdown();
         return -1;
     }
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
--- a/src/qemu_driver.c
+++ b/src/qemu_driver.c
@@ -226,7 +226,8 @@ qemudStartup(void) {
                                 qemu_driver->caps,
                                 &qemu_driver->domains,
                                 qemu_driver->configDir,
-                                qemu_driver->autostartDir) < 0) {
+                                qemu_driver->autostartDir,
+                                NULL, NULL) < 0) {
         qemudShutdown();
         return -1;
     }
@@ -241,6 +242,16 @@ qemudStartup(void) {
     VIR_FREE(base);
     VIR_FREE(qemu_driver);
     return -1;
+}
+
+static void qemudNotifyLoadDomain(virDomainObjPtr vm, int newVM, void *opaque)
+{
+    struct qemud_driver *driver = opaque;
+
+    if (newVM)
+        qemudDomainEventDispatch(driver, vm,
+                                 VIR_DOMAIN_EVENT_DEFINED,
+                                 VIR_DOMAIN_EVENT_DEFINED_ADDED);
 }
 
 /**
@@ -258,7 +269,8 @@ qemudReload(void) {
                             qemu_driver->caps,
                             &qemu_driver->domains,
                             qemu_driver->configDir,
-                            qemu_driver->autostartDir);
+                            qemu_driver->autostartDir,
+                            qemudNotifyLoadDomain, qemu_driver);
 
     qemudAutostartConfigs(qemu_driver);
 
@@ -2356,9 +2368,14 @@ static virDomainPtr qemudDomainDefine(vi
     virDomainDefPtr def;
     virDomainObjPtr vm;
     virDomainPtr dom;
+    int newVM = 1;
 
     if (!(def = virDomainDefParseString(conn, driver->caps, xml)))
         return NULL;
+
+    vm = virDomainFindByName(&driver->domains, def->name);
+    if (vm)
+        newVM = 0;
 
     if (!(vm = virDomainAssignDef(conn,
                                   &driver->domains,
@@ -2375,6 +2392,12 @@ static virDomainPtr qemudDomainDefine(vi
                                 vm);
         return NULL;
     }
+
+    qemudDomainEventDispatch(driver, vm,
+                             VIR_DOMAIN_EVENT_DEFINED,
+                             newVM ?
+                             VIR_DOMAIN_EVENT_DEFINED_ADDED :
+                             VIR_DOMAIN_EVENT_DEFINED_UPDATED);
 
     dom = virGetDomain(conn, vm->def->name, vm->def->uuid);
     if (dom) dom->id = vm->def->id;
@@ -2405,6 +2428,8 @@ static int qemudDomainUndefine(virDomain
 
     if (virDomainDeleteConfig(dom->conn, driver->configDir, driver->autostartDir, vm) < 0)
         return -1;
+
+    qemudDomainEventDispatch(driver, vm, VIR_DOMAIN_EVENT_UNDEFINED, 0);
 
     virDomainRemoveInactive(&driver->domains,
                             vm);


-- 
|: Red Hat, Engineering, London   -o-   http://people.redhat.com/berrange/ :|
|: http://libvirt.org  -o-  http://virt-manager.org  -o-  http://ovirt.org :|
|: http://autobuild.org       -o-         http://search.cpan.org/~danberr/ :|
|: GnuPG: 7D3B9505  -o-  F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :|




More information about the libvir-list mailing list