[libvirt] [RFC PATCHv2 1/4] config: Adding config driver

Adam Walters adam at pandorasboxen.com
Thu Jan 23 20:14:20 UTC 2014


This patch adds the source and header for a new driver, named config,
which provides the 'config:///' connection URI. This driver provides
access to non-domain-related configuration information, such as secret
or network definitions. This helps prevent circular dependencies between
drivers, including the current case between the QEMU and storage
drivers.

Signed-off-by: Adam Walters <adam at pandorasboxen.com>
---
 include/libvirt/virterror.h |   2 +
 src/config/config_driver.c  | 238 ++++++++++++++++++++++++++++++++++++++++++++
 src/config/config_driver.h  |  44 ++++++++
 src/util/virerror.c         |   2 +
 4 files changed, 286 insertions(+)
 create mode 100644 src/config/config_driver.c
 create mode 100644 src/config/config_driver.h

diff --git a/include/libvirt/virterror.h b/include/libvirt/virterror.h
index e31e9c4..0f25a65 100644
--- a/include/libvirt/virterror.h
+++ b/include/libvirt/virterror.h
@@ -121,6 +121,8 @@ typedef enum {
     VIR_FROM_ACCESS = 55,       /* Error from access control manager */
     VIR_FROM_SYSTEMD = 56,      /* Error from systemd code */
 
+    VIR_FROM_CONFIG = 57,       /* Error from config driver */
+
 # ifdef VIR_ENUM_SENTINELS
     VIR_ERR_DOMAIN_LAST
 # endif
diff --git a/src/config/config_driver.c b/src/config/config_driver.c
new file mode 100644
index 0000000..c64b532
--- /dev/null
+++ b/src/config/config_driver.c
@@ -0,0 +1,238 @@
+/*
+ * config_driver.c: core driver methods for accessing configs
+ *
+ * Copyright (C) 2013 Adam Walters
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * Author: Adam Walters <adam at pandorasboxen.com>
+ */
+#include <config.h>
+#include <string.h>
+
+#include "internal.h"
+#include "datatypes.h"
+#include "driver.h"
+#include "virlog.h"
+#include "viralloc.h"
+#include "virerror.h"
+#include "virstring.h"
+#include "viraccessapicheck.h"
+#include "nodeinfo.h"
+#include "config_driver.h"
+
+#define VIR_FROM_THIS VIR_FROM_CONFIG
+
+virConfigDriverPtr config_driver = NULL;
+
+static int configStateCleanup(void) {
+    if (config_driver == NULL)
+        return -1;
+
+    virObjectUnref(config_driver->closeCallbacks);
+
+    virSysinfoDefFree(config_driver->hostsysinfo);
+
+    virMutexDestroy(&config_driver->lock);
+    VIR_FREE(config_driver);
+
+    return 0;
+}
+
+static int configStateInitialize(bool privileged,
+                                 virStateInhibitCallback callback ATTRIBUTE_UNUSED,
+                                 void *opaque ATTRIBUTE_UNUSED)
+{
+    if (!privileged) {
+        VIR_INFO("Not running privileged, disabling driver");
+        return 0;
+    }
+
+    if (VIR_ALLOC(config_driver) < 0)
+        return -1;
+
+    if (virMutexInit(&config_driver->lock) < 0) {
+        VIR_ERROR(_("cannot initialize mutex"));
+        VIR_FREE(config_driver);
+        return -1;
+    }
+
+    config_driver->hostsysinfo = virSysinfoRead();
+
+    if (!(config_driver->closeCallbacks = virCloseCallbacksNew()))
+        goto cleanup;
+
+    return 0;
+
+cleanup:
+    configStateCleanup();
+    return -1;
+}
+
+static int configStateReload(void) {
+    return 0;
+}
+
+static virDrvOpenStatus configConnectOpen(virConnectPtr conn,
+                                          virConnectAuthPtr auth ATTRIBUTE_UNUSED,
+                                          unsigned int flags)
+{
+    virDrvOpenStatus ret = VIR_DRV_OPEN_ERROR;
+    virCheckFlags(VIR_CONNECT_RO, VIR_DRV_OPEN_ERROR);
+
+    if (conn->uri != NULL) {
+        /* If URI isn't 'config', decline the connection */
+        if (conn->uri->scheme == NULL ||
+            STRNEQ(conn->uri->scheme, "config")) {
+            ret = VIR_DRV_OPEN_DECLINED;
+            goto cleanup;
+        }
+
+        /* Allow remote driver to deal with URIs with hostname set */
+        if (conn->uri->server != NULL) {
+            ret = VIR_DRV_OPEN_DECLINED;
+            goto cleanup;
+        }
+
+        if (config_driver == NULL) {
+            virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+                           _("config state driver is not active"));
+            goto cleanup;
+        }
+    } else {
+        ret = VIR_DRV_OPEN_DECLINED;
+        goto cleanup;
+    }
+
+    if (virConnectOpenEnsureACL(conn) < 0)
+        goto cleanup;
+
+    conn->privateData = config_driver;
+
+    ret = VIR_DRV_OPEN_SUCCESS;
+cleanup:
+    return ret;
+}
+
+static int configConnectClose(virConnectPtr conn ATTRIBUTE_UNUSED)
+{
+    /* Cleanup callbacks on config_driver */
+    /* Set conn->privateData to NULL */
+    return 0;
+}
+
+static int
+configConnectSupportsFeature(virConnectPtr conn, int feature ATTRIBUTE_UNUSED)
+{
+    if (virConnectSupportsFeatureEnsureACL(conn) < 0)
+        return -1;
+
+    return 0;
+}
+
+static const char *configConnectGetType(virConnectPtr conn ATTRIBUTE_UNUSED) {
+    if (virConnectGetTypeEnsureACL(conn) < 0)
+        return NULL;
+
+    return "config";
+}
+
+static int configConnectIsSecure(virConnectPtr conn ATTRIBUTE_UNUSED)
+{
+    return 1;
+}
+
+static int configConnectIsEncrypted(virConnectPtr conn ATTRIBUTE_UNUSED)
+{
+    return 0;
+}
+
+static char *configConnectGetHostname(virConnectPtr conn)
+{
+    if (virConnectGetHostnameEnsureACL(conn) < 0)
+        return NULL;
+
+    return virGetHostname();
+}
+
+static char *
+configConnectGetSysinfo(virConnectPtr conn, unsigned int flags)
+{
+    virConfigDriverPtr driver = conn->privateData;
+    virBuffer buf = VIR_BUFFER_INITIALIZER;
+
+    virCheckFlags(0, NULL);
+
+    if (virConnectGetSysinfoEnsureACL(conn) < 0)
+        return NULL;
+
+    if (!driver->hostsysinfo) {
+        return NULL;
+    }
+
+    if (virSysinfoFormat(&buf, driver->hostsysinfo) < 0)
+        return NULL;
+
+    if (virBufferError(&buf)) {
+        virReportOOMError();
+        return NULL;
+    }
+
+    return virBufferContentAndReset(&buf);
+}
+
+static int
+configNodeGetInfo(virConnectPtr conn,
+                  virNodeInfoPtr nodeinfo)
+{
+    if (virNodeGetInfoEnsureACL(conn) < 0)
+        return -1;
+
+    return nodeGetInfo(nodeinfo);
+}
+
+static int configConnectIsAlive(virConnectPtr conn ATTRIBUTE_UNUSED)
+{
+    return 1;
+}
+
+static virDriver configDriver = {
+    .name = "config",
+    .connectOpen = configConnectOpen, /* 1.2.2 */
+    .connectClose = configConnectClose, /* 1.2.2 */
+    .connectSupportsFeature = configConnectSupportsFeature, /* 1.2.2 */
+    .connectGetType = configConnectGetType, /* 1.2.2 */
+    .connectGetHostname = configConnectGetHostname, /* 1.2.2 */
+    .connectGetSysinfo = configConnectGetSysinfo, /* 1.2.2 */
+    .nodeGetInfo = configNodeGetInfo, /* 1.2.2 */
+    .connectIsEncrypted = configConnectIsEncrypted, /* 1.2.2 */
+    .connectIsSecure = configConnectIsSecure, /* 1.2.2 */
+    .connectIsAlive = configConnectIsAlive, /* 1.2.2 */
+};
+
+
+static virStateDriver configStateDriver = {
+    .name = "config",
+    .stateInitialize = configStateInitialize,
+    .stateCleanup = configStateCleanup,
+    .stateReload = configStateReload,
+    .stateDrvType = VIR_DRV_STATE_DRV_LIBVIRT,
+};
+
+int configRegister(void) {
+    virRegisterDriver(&configDriver);
+    virRegisterStateDriver(&configStateDriver);
+    return 0;
+}
diff --git a/src/config/config_driver.h b/src/config/config_driver.h
new file mode 100644
index 0000000..c74af71
--- /dev/null
+++ b/src/config/config_driver.h
@@ -0,0 +1,44 @@
+/*
+ * config_driver.h: core driver methods for accessing configs
+ *
+ * Copyright (C) 2013 Adam Walters
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * Author: Adam Walters <adam at pandorasboxen.com>
+ */
+
+#ifndef __CONFIG_DRIVER_H__
+# define __CONFIG_DRIVER_H__
+
+# include "virsysinfo.h"
+# include "virclosecallbacks.h"
+
+typedef struct _virConfigDriver virConfigDriver;
+typedef virConfigDriver *virConfigDriverPtr;
+
+struct _virConfigDriver {
+    virMutex lock;
+
+    /* Immutable pointer, lockless APIs*/
+    virSysinfoDefPtr hostsysinfo;
+
+    /* Immutable pointer, self-locking APIs*/
+    virCloseCallbacksPtr closeCallbacks;
+};
+
+int configRegister(void);
+
+#endif /* __CONFIG_DRIVER_H__ */
diff --git a/src/util/virerror.c b/src/util/virerror.c
index f0c159f..a16a517 100644
--- a/src/util/virerror.c
+++ b/src/util/virerror.c
@@ -124,6 +124,8 @@ VIR_ENUM_IMPL(virErrorDomain, VIR_ERR_DOMAIN_LAST,
 
               "Access Manager", /* 55 */
               "Systemd",
+
+              "Config Driver", /* 57 */
     )
 
 
-- 
1.8.5.2




More information about the libvir-list mailing list