Hi, Dan
I think this patch itself is good for cleanup.
But for libvirt.c itself, the code is very huge.
since this patch adds code to libvirt.(over 6000 lines).
Is there any plan to split libvirt.c in future?
I am just afraid expand the libvirt.c code like qemu/vl.c.
Thanks
Atsushi SAKAI
"Daniel P. Berrange" <berrange(a)redhat.com> wrote:
The hash.c file contains a nice generic implementation of hash tables, and
then adds a bunch of code for creating/deleting virDomainPtr, virConnectPtr,
virNetworkPtr and virStoragePoolPtr objects which is totally unrelated to
hash tables.
The internal.h file also contains function signatures for a bunch of
APIs which are exported in the libvirt.so, but not part of the official
public API in libvirt/libvirt.h. Their impl is mostly in libvirt.c,
along with the aforementioned stuff from hash.c
To improve internal modularization / cross-file dependancies, this patch
tries to isolate the impl of all exported functions in libvirt.c, and for
those API which are part of the public API, place their declaration in
the src/libvirt.h file.
So, the src/libvirt.h file gets the following exported, but not public
funtions, with the impl of the virGetXXX/virUnrefXXX moving out of hash.c
and into libvirt.c to be alongside other impls of public APIs.
virConnectPtr virGetConnect(void);
int virUnrefConnect(virConnectPtr conn);
virDomainPtr __virGetDomain(virConnectPtr conn,
const char *name,
const unsigned char *uuid);
int virUnrefDomain(virDomainPtr domain);
virNetworkPtr __virGetNetwork(virConnectPtr conn,
const char *name,
const unsigned char *uuid);
int virUnrefNetwork(virNetworkPtr network);
virStoragePoolPtr __virGetStoragePool(virConnectPtr conn,
const char *name,
const unsigned char *uuid);
int virUnrefStoragePool(virStoragePoolPtr pool);
virStorageVolPtr __virGetStorageVol(virConnectPtr conn,
const char *pool,
const char *name,
const char *key);
int virUnrefStorageVol(virStorageVolPtr vol);
int __virStateInitialize(void);
int __virStateCleanup(void);
int __virStateReload(void);
int __virStateActive(void);
int __virStateSigDispatcher(siginfo_t *siginfo);
int __virDrvSupportsFeature (virConnectPtr conn, int feature);
int __virDomainMigratePrepare (virConnectPtr dconn,
char **cookie,
int *cookielen,
const char *uri_in,
char **uri_out,
unsigned long flags,
const char *dname,
unsigned long bandwidth);
int __virDomainMigratePerform (virDomainPtr domain,
const char *cookie,
int cookielen,
const char *uri,
unsigned long flags,
const char *dname,
unsigned long bandwidth);
virDomainPtr __virDomainMigrateFinish (virConnectPtr dconn,
const char *dname,
const char *cookie,
int cookielen,
const char *uri,
unsigned long flags);
Finally, the files for internal hypervisor drivers need to include this
new libvirt.h file.
This is step 2 in cleaning up the definitions visible in internal.h
As before, there should be no functional change in this patch, merely
a bunch of code moving, and #include fixups
b/src/libvirt.h | 98 ++++++
qemud/qemud.c | 2
qemud/remote.c | 2
src/hash.c | 726 -------------------------------------------------
src/internal.h | 52 ---
src/libvirt.c | 728 ++++++++++++++++++++++++++++++++++++++++++++++++++
src/lxc_driver.c | 1
src/network_driver.c | 1
src/openvz_driver.c | 1
src/proxy_internal.h | 3
src/qemu_driver.c | 1
src/remote_internal.c | 1
src/storage_driver.c | 1
src/test.c | 1
src/xen_internal.c | 1
src/xend_internal.c | 1
src/xm_internal.c | 1
src/xs_internal.c | 1
18 files changed, 842 insertions(+), 780 deletions(-)
Daniel
diff -r ef2d00e6bc78 qemud/qemud.c
--- a/qemud/qemud.c Wed Oct 29 11:36:21 2008 +0000
+++ b/qemud/qemud.c Wed Oct 29 11:48:08 2008 +0000
@@ -49,7 +49,7 @@
#include <signal.h>
#include <netdb.h>
-#include "internal.h"
+#include "libvirt.h"
#include "qemud.h"
#include "util.h"
diff -r ef2d00e6bc78 qemud/remote.c
--- a/qemud/remote.c Wed Oct 29 11:36:21 2008 +0000
+++ b/qemud/remote.c Wed Oct 29 11:48:08 2008 +0000
@@ -48,7 +48,7 @@
#include <polkit-dbus/polkit-dbus.h>
#endif
-#include "internal.h"
+#include "libvirt.h"
#include "qemud.h"
#include "memory.h"
diff -r ef2d00e6bc78 src/hash.c
--- a/src/hash.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/hash.c Wed Oct 29 11:48:08 2008 +0000
@@ -25,6 +25,7 @@
#include <libxml/threads.h>
#include "virterror.h"
+#include "libvirt.h"
#include "hash.h"
#include "memory.h"
@@ -594,728 +595,3 @@
return (NULL);
}
-/************************************************************************
- * *
- * Domain and Connections allocations *
- * *
- ************************************************************************/
-
-/**
- * virDomainFreeName:
- * @domain: a domain object
- *
- * Destroy the domain object, this is just used by the domain hash callback.
- *
- * Returns 0 in case of success and -1 in case of failure.
- */
-static int
-virDomainFreeName(virDomainPtr domain, const char *name ATTRIBUTE_UNUSED)
-{
- return (virDomainFree(domain));
-}
-
-/**
- * virNetworkFreeName:
- * @network: a network object
- *
- * Destroy the network object, this is just used by the network hash callback.
- *
- * Returns 0 in case of success and -1 in case of failure.
- */
-static int
-virNetworkFreeName(virNetworkPtr network, const char *name ATTRIBUTE_UNUSED)
-{
- return (virNetworkFree(network));
-}
-
-/**
- * virStoragePoolFreeName:
- * @pool: a pool object
- *
- * Destroy the pool object, this is just used by the pool hash callback.
- *
- * Returns 0 in case of success and -1 in case of failure.
- */
-static int
-virStoragePoolFreeName(virStoragePoolPtr pool, const char *name ATTRIBUTE_UNUSED)
-{
- return (virStoragePoolFree(pool));
-}
-
-/**
- * virStorageVolFreeName:
- * @vol: a vol object
- *
- * Destroy the vol object, this is just used by the vol hash callback.
- *
- * Returns 0 in case of success and -1 in case of failure.
- */
-static int
-virStorageVolFreeName(virStorageVolPtr vol, const char *name ATTRIBUTE_UNUSED)
-{
- return (virStorageVolFree(vol));
-}
-
-/**
- * virGetConnect:
- *
- * Allocates a new hypervisor connection structure
- *
- * Returns a new pointer or NULL in case of error.
- */
-virConnectPtr
-virGetConnect(void) {
- virConnectPtr ret;
-
- if (VIR_ALLOC(ret) < 0) {
- virHashError(NULL, VIR_ERR_NO_MEMORY, "%s", _("allocating
connection"));
- goto failed;
- }
- ret->magic = VIR_CONNECT_MAGIC;
- ret->driver = NULL;
- ret->networkDriver = NULL;
- ret->privateData = NULL;
- ret->networkPrivateData = NULL;
- ret->domains = virHashCreate(20);
- if (ret->domains == NULL)
- goto failed;
- ret->networks = virHashCreate(20);
- if (ret->networks == NULL)
- goto failed;
- ret->storagePools = virHashCreate(20);
- if (ret->storagePools == NULL)
- goto failed;
- ret->storageVols = virHashCreate(20);
- if (ret->storageVols == NULL)
- goto failed;
-
- pthread_mutex_init(&ret->lock, NULL);
-
- ret->refs = 1;
- return(ret);
-
-failed:
- if (ret != NULL) {
- if (ret->domains != NULL)
- virHashFree(ret->domains, (virHashDeallocator) virDomainFreeName);
- if (ret->networks != NULL)
- virHashFree(ret->networks, (virHashDeallocator) virNetworkFreeName);
- if (ret->storagePools != NULL)
- virHashFree(ret->storagePools, (virHashDeallocator)
virStoragePoolFreeName);
- if (ret->storageVols != NULL)
- virHashFree(ret->storageVols, (virHashDeallocator)
virStorageVolFreeName);
-
- pthread_mutex_destroy(&ret->lock);
- VIR_FREE(ret);
- }
- return(NULL);
-}
-
-/**
- * virReleaseConnect:
- * @conn: the hypervisor connection to release
- *
- * Unconditionally release all memory associated with a connection.
- * The conn.lock mutex must be held prior to calling this, and will
- * be released prior to this returning. The connection obj must not
- * be used once this method returns.
- */
-static void
-virReleaseConnect(virConnectPtr conn) {
- DEBUG("release connection %p %s", conn, conn->name);
- if (conn->domains != NULL)
- virHashFree(conn->domains, (virHashDeallocator) virDomainFreeName);
- if (conn->networks != NULL)
- virHashFree(conn->networks, (virHashDeallocator) virNetworkFreeName);
- if (conn->storagePools != NULL)
- virHashFree(conn->storagePools, (virHashDeallocator)
virStoragePoolFreeName);
- if (conn->storageVols != NULL)
- virHashFree(conn->storageVols, (virHashDeallocator) virStorageVolFreeName);
-
- virResetError(&conn->err);
- if (virLastErr.conn == conn)
- virLastErr.conn = NULL;
-
- VIR_FREE(conn->name);
-
- pthread_mutex_unlock(&conn->lock);
- pthread_mutex_destroy(&conn->lock);
- VIR_FREE(conn);
-}
-
-/**
- * virUnrefConnect:
- * @conn: the hypervisor connection to unreference
- *
- * Unreference the connection. If the use count drops to zero, the structure is
- * actually freed.
- *
- * Returns the reference count or -1 in case of failure.
- */
-int
-virUnrefConnect(virConnectPtr conn) {
- int refs;
-
- if ((!VIR_IS_CONNECT(conn))) {
- virHashError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(-1);
- }
- pthread_mutex_lock(&conn->lock);
- DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
- conn->refs--;
- refs = conn->refs;
- if (refs == 0) {
- virReleaseConnect(conn);
- /* Already unlocked mutex */
- return (0);
- }
- pthread_mutex_unlock(&conn->lock);
- return (refs);
-}
-
-/**
- * virGetDomain:
- * @conn: the hypervisor connection
- * @name: pointer to the domain name
- * @uuid: pointer to the uuid
- *
- * Lookup if the domain is already registered for that connection,
- * if yes return a new pointer to it, if no allocate a new structure,
- * and register it in the table. In any case a corresponding call to
- * virUnrefDomain() is needed to not leak data.
- *
- * Returns a pointer to the domain, or NULL in case of failure
- */
-virDomainPtr
-__virGetDomain(virConnectPtr conn, const char *name, const unsigned char *uuid) {
- virDomainPtr ret = NULL;
-
- if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
- virHashError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(NULL);
- }
- pthread_mutex_lock(&conn->lock);
-
- /* TODO search by UUID first as they are better differenciators */
-
- ret = (virDomainPtr) virHashLookup(conn->domains, name);
- /* TODO check the UUID */
- if (ret == NULL) {
- if (VIR_ALLOC(ret) < 0) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
domain"));
- goto error;
- }
- ret->name = strdup(name);
- if (ret->name == NULL) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
domain"));
- goto error;
- }
- ret->magic = VIR_DOMAIN_MAGIC;
- ret->conn = conn;
- ret->id = -1;
- if (uuid != NULL)
- memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
-
- if (virHashAddEntry(conn->domains, name, ret) < 0) {
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("failed to add domain to connection hash
table"));
- goto error;
- }
- conn->refs++;
- DEBUG("New hash entry %p", ret);
- } else {
- DEBUG("Existing hash entry %p: refs now %d", ret, ret->refs+1);
- }
- ret->refs++;
- pthread_mutex_unlock(&conn->lock);
- return(ret);
-
- error:
- pthread_mutex_unlock(&conn->lock);
- if (ret != NULL) {
- VIR_FREE(ret->name);
- VIR_FREE(ret);
- }
- return(NULL);
-}
-
-/**
- * virReleaseDomain:
- * @domain: the domain to release
- *
- * Unconditionally release all memory associated with a domain.
- * The conn.lock mutex must be held prior to calling this, and will
- * be released prior to this returning. The domain obj must not
- * be used once this method returns.
- *
- * It will also unreference the associated connection object,
- * which may also be released if its ref count hits zero.
- */
-static void
-virReleaseDomain(virDomainPtr domain) {
- virConnectPtr conn = domain->conn;
- DEBUG("release domain %p %s", domain, domain->name);
-
- /* TODO search by UUID first as they are better differenciators */
- if (virHashRemoveEntry(conn->domains, domain->name, NULL) < 0)
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("domain missing from connection hash
table"));
-
- if (conn->err.dom == domain)
- conn->err.dom = NULL;
- if (virLastErr.dom == domain)
- virLastErr.dom = NULL;
- domain->magic = -1;
- domain->id = -1;
- VIR_FREE(domain->name);
- VIR_FREE(domain);
-
- DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
- conn->refs--;
- if (conn->refs == 0) {
- virReleaseConnect(conn);
- /* Already unlocked mutex */
- return;
- }
-
- pthread_mutex_unlock(&conn->lock);
-}
-
-
-/**
- * virUnrefDomain:
- * @domain: the domain to unreference
- *
- * Unreference the domain. If the use count drops to zero, the structure is
- * actually freed.
- *
- * Returns the reference count or -1 in case of failure.
- */
-int
-virUnrefDomain(virDomainPtr domain) {
- int refs;
-
- if (!VIR_IS_CONNECTED_DOMAIN(domain)) {
- virHashError(domain->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(-1);
- }
- pthread_mutex_lock(&domain->conn->lock);
- DEBUG("unref domain %p %s %d", domain, domain->name, domain->refs);
- domain->refs--;
- refs = domain->refs;
- if (refs == 0) {
- virReleaseDomain(domain);
- /* Already unlocked mutex */
- return (0);
- }
-
- pthread_mutex_unlock(&domain->conn->lock);
- return (refs);
-}
-
-/**
- * virGetNetwork:
- * @conn: the hypervisor connection
- * @name: pointer to the network name
- * @uuid: pointer to the uuid
- *
- * Lookup if the network is already registered for that connection,
- * if yes return a new pointer to it, if no allocate a new structure,
- * and register it in the table. In any case a corresponding call to
- * virUnrefNetwork() is needed to not leak data.
- *
- * Returns a pointer to the network, or NULL in case of failure
- */
-virNetworkPtr
-__virGetNetwork(virConnectPtr conn, const char *name, const unsigned char *uuid) {
- virNetworkPtr ret = NULL;
-
- if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
- virHashError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(NULL);
- }
- pthread_mutex_lock(&conn->lock);
-
- /* TODO search by UUID first as they are better differenciators */
-
- ret = (virNetworkPtr) virHashLookup(conn->networks, name);
- /* TODO check the UUID */
- if (ret == NULL) {
- if (VIR_ALLOC(ret) < 0) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
network"));
- goto error;
- }
- ret->name = strdup(name);
- if (ret->name == NULL) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
network"));
- goto error;
- }
- ret->magic = VIR_NETWORK_MAGIC;
- ret->conn = conn;
- if (uuid != NULL)
- memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
-
- if (virHashAddEntry(conn->networks, name, ret) < 0) {
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("failed to add network to connection
hash table"));
- goto error;
- }
- conn->refs++;
- }
- ret->refs++;
- pthread_mutex_unlock(&conn->lock);
- return(ret);
-
- error:
- pthread_mutex_unlock(&conn->lock);
- if (ret != NULL) {
- VIR_FREE(ret->name);
- VIR_FREE(ret);
- }
- return(NULL);
-}
-
-/**
- * virReleaseNetwork:
- * @network: the network to release
- *
- * Unconditionally release all memory associated with a network.
- * The conn.lock mutex must be held prior to calling this, and will
- * be released prior to this returning. The network obj must not
- * be used once this method returns.
- *
- * It will also unreference the associated connection object,
- * which may also be released if its ref count hits zero.
- */
-static void
-virReleaseNetwork(virNetworkPtr network) {
- virConnectPtr conn = network->conn;
- DEBUG("release network %p %s", network, network->name);
-
- /* TODO search by UUID first as they are better differenciators */
- if (virHashRemoveEntry(conn->networks, network->name, NULL) < 0)
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("network missing from connection hash
table"));
-
- if (
conn->err.net == network)
-
conn->err.net = NULL;
- if (
virLastErr.net == network)
-
virLastErr.net = NULL;
-
- network->magic = -1;
- VIR_FREE(network->name);
- VIR_FREE(network);
-
- DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
- conn->refs--;
- if (conn->refs == 0) {
- virReleaseConnect(conn);
- /* Already unlocked mutex */
- return;
- }
-
- pthread_mutex_unlock(&conn->lock);
-}
-
-
-/**
- * virUnrefNetwork:
- * @network: the network to unreference
- *
- * Unreference the network. If the use count drops to zero, the structure is
- * actually freed.
- *
- * Returns the reference count or -1 in case of failure.
- */
-int
-virUnrefNetwork(virNetworkPtr network) {
- int refs;
-
- if (!VIR_IS_CONNECTED_NETWORK(network)) {
- virHashError(network->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(-1);
- }
- pthread_mutex_lock(&network->conn->lock);
- DEBUG("unref network %p %s %d", network, network->name,
network->refs);
- network->refs--;
- refs = network->refs;
- if (refs == 0) {
- virReleaseNetwork(network);
- /* Already unlocked mutex */
- return (0);
- }
-
- pthread_mutex_unlock(&network->conn->lock);
- return (refs);
-}
-
-
-/**
- * virGetStoragePool:
- * @conn: the hypervisor connection
- * @name: pointer to the storage pool name
- * @uuid: pointer to the uuid
- *
- * Lookup if the storage pool is already registered for that connection,
- * if yes return a new pointer to it, if no allocate a new structure,
- * and register it in the table. In any case a corresponding call to
- * virFreeStoragePool() is needed to not leak data.
- *
- * Returns a pointer to the network, or NULL in case of failure
- */
-virStoragePoolPtr
-__virGetStoragePool(virConnectPtr conn, const char *name, const unsigned char *uuid) {
- virStoragePoolPtr ret = NULL;
-
- if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
- virHashError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(NULL);
- }
- pthread_mutex_lock(&conn->lock);
-
- /* TODO search by UUID first as they are better differenciators */
-
- ret = (virStoragePoolPtr) virHashLookup(conn->storagePools, name);
- /* TODO check the UUID */
- if (ret == NULL) {
- if (VIR_ALLOC(ret) < 0) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
storage pool"));
- goto error;
- }
- ret->name = strdup(name);
- if (ret->name == NULL) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
storage pool"));
- goto error;
- }
- ret->magic = VIR_STORAGE_POOL_MAGIC;
- ret->conn = conn;
- if (uuid != NULL)
- memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
-
- if (virHashAddEntry(conn->storagePools, name, ret) < 0) {
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("failed to add storage pool to
connection hash table"));
- goto error;
- }
- conn->refs++;
- }
- ret->refs++;
- pthread_mutex_unlock(&conn->lock);
- return(ret);
-
-error:
- pthread_mutex_unlock(&conn->lock);
- if (ret != NULL) {
- VIR_FREE(ret->name);
- VIR_FREE(ret);
- }
- return(NULL);
-}
-
-
-/**
- * virReleaseStoragePool:
- * @pool: the pool to release
- *
- * Unconditionally release all memory associated with a pool.
- * The conn.lock mutex must be held prior to calling this, and will
- * be released prior to this returning. The pool obj must not
- * be used once this method returns.
- *
- * It will also unreference the associated connection object,
- * which may also be released if its ref count hits zero.
- */
-static void
-virReleaseStoragePool(virStoragePoolPtr pool) {
- virConnectPtr conn = pool->conn;
- DEBUG("release pool %p %s", pool, pool->name);
-
- /* TODO search by UUID first as they are better differenciators */
- if (virHashRemoveEntry(conn->storagePools, pool->name, NULL) < 0)
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("pool missing from connection hash
table"));
-
- pool->magic = -1;
- VIR_FREE(pool->name);
- VIR_FREE(pool);
-
- DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
- conn->refs--;
- if (conn->refs == 0) {
- virReleaseConnect(conn);
- /* Already unlocked mutex */
- return;
- }
-
- pthread_mutex_unlock(&conn->lock);
-}
-
-
-/**
- * virUnrefStoragePool:
- * @pool: the pool to unreference
- *
- * Unreference the pool. If the use count drops to zero, the structure is
- * actually freed.
- *
- * Returns the reference count or -1 in case of failure.
- */
-int
-virUnrefStoragePool(virStoragePoolPtr pool) {
- int refs;
-
- if (!VIR_IS_CONNECTED_STORAGE_POOL(pool)) {
- virHashError(pool->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(-1);
- }
- pthread_mutex_lock(&pool->conn->lock);
- DEBUG("unref pool %p %s %d", pool, pool->name, pool->refs);
- pool->refs--;
- refs = pool->refs;
- if (refs == 0) {
- virReleaseStoragePool(pool);
- /* Already unlocked mutex */
- return (0);
- }
-
- pthread_mutex_unlock(&pool->conn->lock);
- return (refs);
-}
-
-
-/**
- * virGetStorageVol:
- * @conn: the hypervisor connection
- * @pool: pool owning the volume
- * @name: pointer to the storage vol name
- * @uuid: pointer to the uuid
- *
- * Lookup if the storage vol is already registered for that connection,
- * if yes return a new pointer to it, if no allocate a new structure,
- * and register it in the table. In any case a corresponding call to
- * virFreeStorageVol() is needed to not leak data.
- *
- * Returns a pointer to the storage vol, or NULL in case of failure
- */
-virStorageVolPtr
-__virGetStorageVol(virConnectPtr conn, const char *pool, const char *name, const char
*key) {
- virStorageVolPtr ret = NULL;
-
- if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (key == NULL)) {
- virHashError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(NULL);
- }
- pthread_mutex_lock(&conn->lock);
-
- ret = (virStorageVolPtr) virHashLookup(conn->storageVols, key);
- if (ret == NULL) {
- if (VIR_ALLOC(ret) < 0) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
storage vol"));
- goto error;
- }
- ret->pool = strdup(pool);
- if (ret->pool == NULL) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
storage vol"));
- goto error;
- }
- ret->name = strdup(name);
- if (ret->name == NULL) {
- virHashError(conn, VIR_ERR_NO_MEMORY, "%s", _("allocating
storage vol"));
- goto error;
- }
- strncpy(ret->key, key, sizeof(ret->key)-1);
- ret->key[sizeof(ret->key)-1] = '\0';
- ret->magic = VIR_STORAGE_VOL_MAGIC;
- ret->conn = conn;
-
- if (virHashAddEntry(conn->storageVols, key, ret) < 0) {
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("failed to add storage vol to connection
hash table"));
- goto error;
- }
- conn->refs++;
- }
- ret->refs++;
- pthread_mutex_unlock(&conn->lock);
- return(ret);
-
-error:
- pthread_mutex_unlock(&conn->lock);
- if (ret != NULL) {
- VIR_FREE(ret->name);
- VIR_FREE(ret->pool);
- VIR_FREE(ret);
- }
- return(NULL);
-}
-
-
-/**
- * virReleaseStorageVol:
- * @vol: the vol to release
- *
- * Unconditionally release all memory associated with a vol.
- * The conn.lock mutex must be held prior to calling this, and will
- * be released prior to this returning. The vol obj must not
- * be used once this method returns.
- *
- * It will also unreference the associated connection object,
- * which may also be released if its ref count hits zero.
- */
-static void
-virReleaseStorageVol(virStorageVolPtr vol) {
- virConnectPtr conn = vol->conn;
- DEBUG("release vol %p %s", vol, vol->name);
-
- /* TODO search by UUID first as they are better differenciators */
- if (virHashRemoveEntry(conn->storageVols, vol->key, NULL) < 0)
- virHashError(conn, VIR_ERR_INTERNAL_ERROR,
- "%s", _("vol missing from connection hash
table"));
-
- vol->magic = -1;
- VIR_FREE(vol->name);
- VIR_FREE(vol->pool);
- VIR_FREE(vol);
-
- DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
- conn->refs--;
- if (conn->refs == 0) {
- virReleaseConnect(conn);
- /* Already unlocked mutex */
- return;
- }
-
- pthread_mutex_unlock(&conn->lock);
-}
-
-
-/**
- * virUnrefStorageVol:
- * @vol: the vol to unreference
- *
- * Unreference the vol. If the use count drops to zero, the structure is
- * actually freed.
- *
- * Returns the reference count or -1 in case of failure.
- */
-int
-virUnrefStorageVol(virStorageVolPtr vol) {
- int refs;
-
- if (!VIR_IS_CONNECTED_STORAGE_VOL(vol)) {
- virHashError(vol->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
- return(-1);
- }
- pthread_mutex_lock(&vol->conn->lock);
- DEBUG("unref vol %p %s %d", vol, vol->name, vol->refs);
- vol->refs--;
- refs = vol->refs;
- if (refs == 0) {
- virReleaseStorageVol(vol);
- /* Already unlocked mutex */
- return (0);
- }
-
- pthread_mutex_unlock(&vol->conn->lock);
- return (refs);
-}
diff -r ef2d00e6bc78 src/internal.h
--- a/src/internal.h Wed Oct 29 11:36:21 2008 +0000
+++ b/src/internal.h Wed Oct 29 11:48:08 2008 +0000
@@ -295,58 +295,6 @@
};
-
-/************************************************************************
- * *
- * API for domain/connections (de)allocations and lookups *
- * *
- ************************************************************************/
-
-virConnectPtr virGetConnect (void);
-int virUnrefConnect (virConnectPtr conn);
-virDomainPtr __virGetDomain (virConnectPtr conn,
- const char *name,
- const unsigned char *uuid);
-int virUnrefDomain (virDomainPtr domain);
-virNetworkPtr __virGetNetwork (virConnectPtr conn,
- const char *name,
- const unsigned char *uuid);
-int virUnrefNetwork (virNetworkPtr network);
-
-virStoragePoolPtr __virGetStoragePool (virConnectPtr conn,
- const char *name,
- const unsigned char *uuid);
-int virUnrefStoragePool (virStoragePoolPtr pool);
-virStorageVolPtr __virGetStorageVol (virConnectPtr conn,
- const char *pool,
- const char *name,
- const char *key);
-int virUnrefStorageVol (virStorageVolPtr vol);
-
-#define virGetDomain(c,n,u) __virGetDomain((c),(n),(u))
-#define virGetNetwork(c,n,u) __virGetNetwork((c),(n),(u))
-#define virGetStoragePool(c,n,u) __virGetStoragePool((c),(n),(u))
-#define virGetStorageVol(c,p,n,u) __virGetStorageVol((c),(p),(n),(u))
-
-#ifdef WITH_LIBVIRTD
-int __virStateInitialize(void);
-int __virStateCleanup(void);
-int __virStateReload(void);
-int __virStateActive(void);
-int __virStateSigDispatcher(siginfo_t *siginfo);
-#define virStateInitialize() __virStateInitialize()
-#define virStateCleanup() __virStateCleanup()
-#define virStateReload() __virStateReload()
-#define virStateActive() __virStateActive()
-#define virStateSigDispatcher(s) __virStateSigDispatcher(s)
-#endif
-
-int __virDrvSupportsFeature (virConnectPtr conn, int feature);
-
-int __virDomainMigratePrepare (virConnectPtr dconn, char **cookie, int *cookielen, const
char *uri_in, char **uri_out, unsigned long flags, const char *dname, unsigned long
bandwidth);
-int __virDomainMigratePerform (virDomainPtr domain, const char *cookie, int cookielen,
const char *uri, unsigned long flags, const char *dname, unsigned long bandwidth);
-virDomainPtr __virDomainMigrateFinish (virConnectPtr dconn, const char *dname, const
char *cookie, int cookielen, const char *uri, unsigned long flags);
-
/**
* Domain Event Notification
*/
diff -r ef2d00e6bc78 src/libvirt.c
--- a/src/libvirt.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/libvirt.c Wed Oct 29 11:48:08 2008 +0000
@@ -32,6 +32,7 @@
#endif
#include "virterror.h"
+#include "libvirt.h"
#include "driver.h"
#include "uuid.h"
@@ -5570,3 +5571,730 @@
return 0;
}
+
+
+/************************************************************************
+ * *
+ * Domain and Connections allocations *
+ * *
+ ************************************************************************/
+
+/**
+ * virDomainFreeName:
+ * @domain: a domain object
+ *
+ * Destroy the domain object, this is just used by the domain hash callback.
+ *
+ * Returns 0 in case of success and -1 in case of failure.
+ */
+static int
+virDomainFreeName(virDomainPtr domain, const char *name ATTRIBUTE_UNUSED)
+{
+ return (virDomainFree(domain));
+}
+
+/**
+ * virNetworkFreeName:
+ * @network: a network object
+ *
+ * Destroy the network object, this is just used by the network hash callback.
+ *
+ * Returns 0 in case of success and -1 in case of failure.
+ */
+static int
+virNetworkFreeName(virNetworkPtr network, const char *name ATTRIBUTE_UNUSED)
+{
+ return (virNetworkFree(network));
+}
+
+/**
+ * virStoragePoolFreeName:
+ * @pool: a pool object
+ *
+ * Destroy the pool object, this is just used by the pool hash callback.
+ *
+ * Returns 0 in case of success and -1 in case of failure.
+ */
+static int
+virStoragePoolFreeName(virStoragePoolPtr pool, const char *name ATTRIBUTE_UNUSED)
+{
+ return (virStoragePoolFree(pool));
+}
+
+/**
+ * virStorageVolFreeName:
+ * @vol: a vol object
+ *
+ * Destroy the vol object, this is just used by the vol hash callback.
+ *
+ * Returns 0 in case of success and -1 in case of failure.
+ */
+static int
+virStorageVolFreeName(virStorageVolPtr vol, const char *name ATTRIBUTE_UNUSED)
+{
+ return (virStorageVolFree(vol));
+}
+
+/**
+ * virGetConnect:
+ *
+ * Allocates a new hypervisor connection structure
+ *
+ * Returns a new pointer or NULL in case of error.
+ */
+virConnectPtr
+virGetConnect(void) {
+ virConnectPtr ret;
+
+ if (VIR_ALLOC(ret) < 0) {
+ virLibConnError(NULL, VIR_ERR_NO_MEMORY, _("allocating connection"));
+ goto failed;
+ }
+ ret->magic = VIR_CONNECT_MAGIC;
+ ret->driver = NULL;
+ ret->networkDriver = NULL;
+ ret->privateData = NULL;
+ ret->networkPrivateData = NULL;
+ ret->domains = virHashCreate(20);
+ if (ret->domains == NULL)
+ goto failed;
+ ret->networks = virHashCreate(20);
+ if (ret->networks == NULL)
+ goto failed;
+ ret->storagePools = virHashCreate(20);
+ if (ret->storagePools == NULL)
+ goto failed;
+ ret->storageVols = virHashCreate(20);
+ if (ret->storageVols == NULL)
+ goto failed;
+
+ pthread_mutex_init(&ret->lock, NULL);
+
+ ret->refs = 1;
+ return(ret);
+
+failed:
+ if (ret != NULL) {
+ if (ret->domains != NULL)
+ virHashFree(ret->domains, (virHashDeallocator) virDomainFreeName);
+ if (ret->networks != NULL)
+ virHashFree(ret->networks, (virHashDeallocator) virNetworkFreeName);
+ if (ret->storagePools != NULL)
+ virHashFree(ret->storagePools, (virHashDeallocator)
virStoragePoolFreeName);
+ if (ret->storageVols != NULL)
+ virHashFree(ret->storageVols, (virHashDeallocator)
virStorageVolFreeName);
+
+ pthread_mutex_destroy(&ret->lock);
+ VIR_FREE(ret);
+ }
+ return(NULL);
+}
+
+/**
+ * virReleaseConnect:
+ * @conn: the hypervisor connection to release
+ *
+ * Unconditionally release all memory associated with a connection.
+ * The conn.lock mutex must be held prior to calling this, and will
+ * be released prior to this returning. The connection obj must not
+ * be used once this method returns.
+ */
+static void
+virReleaseConnect(virConnectPtr conn) {
+ DEBUG("release connection %p %s", conn, conn->name);
+ if (conn->domains != NULL)
+ virHashFree(conn->domains, (virHashDeallocator) virDomainFreeName);
+ if (conn->networks != NULL)
+ virHashFree(conn->networks, (virHashDeallocator) virNetworkFreeName);
+ if (conn->storagePools != NULL)
+ virHashFree(conn->storagePools, (virHashDeallocator)
virStoragePoolFreeName);
+ if (conn->storageVols != NULL)
+ virHashFree(conn->storageVols, (virHashDeallocator) virStorageVolFreeName);
+
+ virResetError(&conn->err);
+ if (virLastErr.conn == conn)
+ virLastErr.conn = NULL;
+
+ VIR_FREE(conn->name);
+
+ pthread_mutex_unlock(&conn->lock);
+ pthread_mutex_destroy(&conn->lock);
+ VIR_FREE(conn);
+}
+
+/**
+ * virUnrefConnect:
+ * @conn: the hypervisor connection to unreference
+ *
+ * Unreference the connection. If the use count drops to zero, the structure is
+ * actually freed.
+ *
+ * Returns the reference count or -1 in case of failure.
+ */
+int
+virUnrefConnect(virConnectPtr conn) {
+ int refs;
+
+ if ((!VIR_IS_CONNECT(conn))) {
+ virLibConnError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(-1);
+ }
+ pthread_mutex_lock(&conn->lock);
+ DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
+ conn->refs--;
+ refs = conn->refs;
+ if (refs == 0) {
+ virReleaseConnect(conn);
+ /* Already unlocked mutex */
+ return (0);
+ }
+ pthread_mutex_unlock(&conn->lock);
+ return (refs);
+}
+
+/**
+ * virGetDomain:
+ * @conn: the hypervisor connection
+ * @name: pointer to the domain name
+ * @uuid: pointer to the uuid
+ *
+ * Lookup if the domain is already registered for that connection,
+ * if yes return a new pointer to it, if no allocate a new structure,
+ * and register it in the table. In any case a corresponding call to
+ * virUnrefDomain() is needed to not leak data.
+ *
+ * Returns a pointer to the domain, or NULL in case of failure
+ */
+virDomainPtr
+__virGetDomain(virConnectPtr conn, const char *name, const unsigned char *uuid) {
+ virDomainPtr ret = NULL;
+
+ if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
+ virLibConnError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(NULL);
+ }
+ pthread_mutex_lock(&conn->lock);
+
+ /* TODO search by UUID first as they are better differenciators */
+
+ ret = (virDomainPtr) virHashLookup(conn->domains, name);
+ /* TODO check the UUID */
+ if (ret == NULL) {
+ if (VIR_ALLOC(ret) < 0) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating domain"));
+ goto error;
+ }
+ ret->name = strdup(name);
+ if (ret->name == NULL) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating domain"));
+ goto error;
+ }
+ ret->magic = VIR_DOMAIN_MAGIC;
+ ret->conn = conn;
+ ret->id = -1;
+ if (uuid != NULL)
+ memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
+
+ if (virHashAddEntry(conn->domains, name, ret) < 0) {
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("failed to add domain to connection hash
table"));
+ goto error;
+ }
+ conn->refs++;
+ DEBUG("New hash entry %p", ret);
+ } else {
+ DEBUG("Existing hash entry %p: refs now %d", ret, ret->refs+1);
+ }
+ ret->refs++;
+ pthread_mutex_unlock(&conn->lock);
+ return(ret);
+
+ error:
+ pthread_mutex_unlock(&conn->lock);
+ if (ret != NULL) {
+ VIR_FREE(ret->name);
+ VIR_FREE(ret);
+ }
+ return(NULL);
+}
+
+/**
+ * virReleaseDomain:
+ * @domain: the domain to release
+ *
+ * Unconditionally release all memory associated with a domain.
+ * The conn.lock mutex must be held prior to calling this, and will
+ * be released prior to this returning. The domain obj must not
+ * be used once this method returns.
+ *
+ * It will also unreference the associated connection object,
+ * which may also be released if its ref count hits zero.
+ */
+static void
+virReleaseDomain(virDomainPtr domain) {
+ virConnectPtr conn = domain->conn;
+ DEBUG("release domain %p %s", domain, domain->name);
+
+ /* TODO search by UUID first as they are better differenciators */
+ if (virHashRemoveEntry(conn->domains, domain->name, NULL) < 0)
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("domain missing from connection hash table"));
+
+ if (conn->err.dom == domain)
+ conn->err.dom = NULL;
+ if (virLastErr.dom == domain)
+ virLastErr.dom = NULL;
+ domain->magic = -1;
+ domain->id = -1;
+ VIR_FREE(domain->name);
+ VIR_FREE(domain);
+
+ DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
+ conn->refs--;
+ if (conn->refs == 0) {
+ virReleaseConnect(conn);
+ /* Already unlocked mutex */
+ return;
+ }
+
+ pthread_mutex_unlock(&conn->lock);
+}
+
+
+/**
+ * virUnrefDomain:
+ * @domain: the domain to unreference
+ *
+ * Unreference the domain. If the use count drops to zero, the structure is
+ * actually freed.
+ *
+ * Returns the reference count or -1 in case of failure.
+ */
+int
+virUnrefDomain(virDomainPtr domain) {
+ int refs;
+
+ if (!VIR_IS_CONNECTED_DOMAIN(domain)) {
+ virLibConnError(domain->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(-1);
+ }
+ pthread_mutex_lock(&domain->conn->lock);
+ DEBUG("unref domain %p %s %d", domain, domain->name, domain->refs);
+ domain->refs--;
+ refs = domain->refs;
+ if (refs == 0) {
+ virReleaseDomain(domain);
+ /* Already unlocked mutex */
+ return (0);
+ }
+
+ pthread_mutex_unlock(&domain->conn->lock);
+ return (refs);
+}
+
+/**
+ * virGetNetwork:
+ * @conn: the hypervisor connection
+ * @name: pointer to the network name
+ * @uuid: pointer to the uuid
+ *
+ * Lookup if the network is already registered for that connection,
+ * if yes return a new pointer to it, if no allocate a new structure,
+ * and register it in the table. In any case a corresponding call to
+ * virUnrefNetwork() is needed to not leak data.
+ *
+ * Returns a pointer to the network, or NULL in case of failure
+ */
+virNetworkPtr
+__virGetNetwork(virConnectPtr conn, const char *name, const unsigned char *uuid) {
+ virNetworkPtr ret = NULL;
+
+ if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
+ virLibConnError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(NULL);
+ }
+ pthread_mutex_lock(&conn->lock);
+
+ /* TODO search by UUID first as they are better differenciators */
+
+ ret = (virNetworkPtr) virHashLookup(conn->networks, name);
+ /* TODO check the UUID */
+ if (ret == NULL) {
+ if (VIR_ALLOC(ret) < 0) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating
network"));
+ goto error;
+ }
+ ret->name = strdup(name);
+ if (ret->name == NULL) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating
network"));
+ goto error;
+ }
+ ret->magic = VIR_NETWORK_MAGIC;
+ ret->conn = conn;
+ if (uuid != NULL)
+ memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
+
+ if (virHashAddEntry(conn->networks, name, ret) < 0) {
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("failed to add network to connection hash
table"));
+ goto error;
+ }
+ conn->refs++;
+ }
+ ret->refs++;
+ pthread_mutex_unlock(&conn->lock);
+ return(ret);
+
+ error:
+ pthread_mutex_unlock(&conn->lock);
+ if (ret != NULL) {
+ VIR_FREE(ret->name);
+ VIR_FREE(ret);
+ }
+ return(NULL);
+}
+
+/**
+ * virReleaseNetwork:
+ * @network: the network to release
+ *
+ * Unconditionally release all memory associated with a network.
+ * The conn.lock mutex must be held prior to calling this, and will
+ * be released prior to this returning. The network obj must not
+ * be used once this method returns.
+ *
+ * It will also unreference the associated connection object,
+ * which may also be released if its ref count hits zero.
+ */
+static void
+virReleaseNetwork(virNetworkPtr network) {
+ virConnectPtr conn = network->conn;
+ DEBUG("release network %p %s", network, network->name);
+
+ /* TODO search by UUID first as they are better differenciators */
+ if (virHashRemoveEntry(conn->networks, network->name, NULL) < 0)
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("network missing from connection hash table"));
+
+ if (
conn->err.net == network)
+
conn->err.net = NULL;
+ if (
virLastErr.net == network)
+
virLastErr.net = NULL;
+
+ network->magic = -1;
+ VIR_FREE(network->name);
+ VIR_FREE(network);
+
+ DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
+ conn->refs--;
+ if (conn->refs == 0) {
+ virReleaseConnect(conn);
+ /* Already unlocked mutex */
+ return;
+ }
+
+ pthread_mutex_unlock(&conn->lock);
+}
+
+
+/**
+ * virUnrefNetwork:
+ * @network: the network to unreference
+ *
+ * Unreference the network. If the use count drops to zero, the structure is
+ * actually freed.
+ *
+ * Returns the reference count or -1 in case of failure.
+ */
+int
+virUnrefNetwork(virNetworkPtr network) {
+ int refs;
+
+ if (!VIR_IS_CONNECTED_NETWORK(network)) {
+ virLibConnError(network->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(-1);
+ }
+ pthread_mutex_lock(&network->conn->lock);
+ DEBUG("unref network %p %s %d", network, network->name,
network->refs);
+ network->refs--;
+ refs = network->refs;
+ if (refs == 0) {
+ virReleaseNetwork(network);
+ /* Already unlocked mutex */
+ return (0);
+ }
+
+ pthread_mutex_unlock(&network->conn->lock);
+ return (refs);
+}
+
+
+/**
+ * virGetStoragePool:
+ * @conn: the hypervisor connection
+ * @name: pointer to the storage pool name
+ * @uuid: pointer to the uuid
+ *
+ * Lookup if the storage pool is already registered for that connection,
+ * if yes return a new pointer to it, if no allocate a new structure,
+ * and register it in the table. In any case a corresponding call to
+ * virFreeStoragePool() is needed to not leak data.
+ *
+ * Returns a pointer to the network, or NULL in case of failure
+ */
+virStoragePoolPtr
+__virGetStoragePool(virConnectPtr conn, const char *name, const unsigned char *uuid) {
+ virStoragePoolPtr ret = NULL;
+
+ if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (uuid == NULL)) {
+ virLibConnError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(NULL);
+ }
+ pthread_mutex_lock(&conn->lock);
+
+ /* TODO search by UUID first as they are better differenciators */
+
+ ret = (virStoragePoolPtr) virHashLookup(conn->storagePools, name);
+ /* TODO check the UUID */
+ if (ret == NULL) {
+ if (VIR_ALLOC(ret) < 0) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating storage
pool"));
+ goto error;
+ }
+ ret->name = strdup(name);
+ if (ret->name == NULL) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating storage
pool"));
+ goto error;
+ }
+ ret->magic = VIR_STORAGE_POOL_MAGIC;
+ ret->conn = conn;
+ if (uuid != NULL)
+ memcpy(&(ret->uuid[0]), uuid, VIR_UUID_BUFLEN);
+
+ if (virHashAddEntry(conn->storagePools, name, ret) < 0) {
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("failed to add storage pool to connection hash
table"));
+ goto error;
+ }
+ conn->refs++;
+ }
+ ret->refs++;
+ pthread_mutex_unlock(&conn->lock);
+ return(ret);
+
+error:
+ pthread_mutex_unlock(&conn->lock);
+ if (ret != NULL) {
+ VIR_FREE(ret->name);
+ VIR_FREE(ret);
+ }
+ return(NULL);
+}
+
+
+/**
+ * virReleaseStoragePool:
+ * @pool: the pool to release
+ *
+ * Unconditionally release all memory associated with a pool.
+ * The conn.lock mutex must be held prior to calling this, and will
+ * be released prior to this returning. The pool obj must not
+ * be used once this method returns.
+ *
+ * It will also unreference the associated connection object,
+ * which may also be released if its ref count hits zero.
+ */
+static void
+virReleaseStoragePool(virStoragePoolPtr pool) {
+ virConnectPtr conn = pool->conn;
+ DEBUG("release pool %p %s", pool, pool->name);
+
+ /* TODO search by UUID first as they are better differenciators */
+ if (virHashRemoveEntry(conn->storagePools, pool->name, NULL) < 0)
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("pool missing from connection hash table"));
+
+ pool->magic = -1;
+ VIR_FREE(pool->name);
+ VIR_FREE(pool);
+
+ DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
+ conn->refs--;
+ if (conn->refs == 0) {
+ virReleaseConnect(conn);
+ /* Already unlocked mutex */
+ return;
+ }
+
+ pthread_mutex_unlock(&conn->lock);
+}
+
+
+/**
+ * virUnrefStoragePool:
+ * @pool: the pool to unreference
+ *
+ * Unreference the pool. If the use count drops to zero, the structure is
+ * actually freed.
+ *
+ * Returns the reference count or -1 in case of failure.
+ */
+int
+virUnrefStoragePool(virStoragePoolPtr pool) {
+ int refs;
+
+ if (!VIR_IS_CONNECTED_STORAGE_POOL(pool)) {
+ virLibConnError(pool->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(-1);
+ }
+ pthread_mutex_lock(&pool->conn->lock);
+ DEBUG("unref pool %p %s %d", pool, pool->name, pool->refs);
+ pool->refs--;
+ refs = pool->refs;
+ if (refs == 0) {
+ virReleaseStoragePool(pool);
+ /* Already unlocked mutex */
+ return (0);
+ }
+
+ pthread_mutex_unlock(&pool->conn->lock);
+ return (refs);
+}
+
+
+/**
+ * virGetStorageVol:
+ * @conn: the hypervisor connection
+ * @pool: pool owning the volume
+ * @name: pointer to the storage vol name
+ * @uuid: pointer to the uuid
+ *
+ * Lookup if the storage vol is already registered for that connection,
+ * if yes return a new pointer to it, if no allocate a new structure,
+ * and register it in the table. In any case a corresponding call to
+ * virFreeStorageVol() is needed to not leak data.
+ *
+ * Returns a pointer to the storage vol, or NULL in case of failure
+ */
+virStorageVolPtr
+__virGetStorageVol(virConnectPtr conn, const char *pool, const char *name, const char
*key) {
+ virStorageVolPtr ret = NULL;
+
+ if ((!VIR_IS_CONNECT(conn)) || (name == NULL) || (key == NULL)) {
+ virLibConnError(conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(NULL);
+ }
+ pthread_mutex_lock(&conn->lock);
+
+ ret = (virStorageVolPtr) virHashLookup(conn->storageVols, key);
+ if (ret == NULL) {
+ if (VIR_ALLOC(ret) < 0) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating storage
vol"));
+ goto error;
+ }
+ ret->pool = strdup(pool);
+ if (ret->pool == NULL) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating storage
vol"));
+ goto error;
+ }
+ ret->name = strdup(name);
+ if (ret->name == NULL) {
+ virLibConnError(conn, VIR_ERR_NO_MEMORY, _("allocating storage
vol"));
+ goto error;
+ }
+ strncpy(ret->key, key, sizeof(ret->key)-1);
+ ret->key[sizeof(ret->key)-1] = '\0';
+ ret->magic = VIR_STORAGE_VOL_MAGIC;
+ ret->conn = conn;
+
+ if (virHashAddEntry(conn->storageVols, key, ret) < 0) {
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("failed to add storage vol to connection hash
table"));
+ goto error;
+ }
+ conn->refs++;
+ }
+ ret->refs++;
+ pthread_mutex_unlock(&conn->lock);
+ return(ret);
+
+error:
+ pthread_mutex_unlock(&conn->lock);
+ if (ret != NULL) {
+ VIR_FREE(ret->name);
+ VIR_FREE(ret->pool);
+ VIR_FREE(ret);
+ }
+ return(NULL);
+}
+
+
+/**
+ * virReleaseStorageVol:
+ * @vol: the vol to release
+ *
+ * Unconditionally release all memory associated with a vol.
+ * The conn.lock mutex must be held prior to calling this, and will
+ * be released prior to this returning. The vol obj must not
+ * be used once this method returns.
+ *
+ * It will also unreference the associated connection object,
+ * which may also be released if its ref count hits zero.
+ */
+static void
+virReleaseStorageVol(virStorageVolPtr vol) {
+ virConnectPtr conn = vol->conn;
+ DEBUG("release vol %p %s", vol, vol->name);
+
+ /* TODO search by UUID first as they are better differenciators */
+ if (virHashRemoveEntry(conn->storageVols, vol->key, NULL) < 0)
+ virLibConnError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("vol missing from connection hash table"));
+
+ vol->magic = -1;
+ VIR_FREE(vol->name);
+ VIR_FREE(vol->pool);
+ VIR_FREE(vol);
+
+ DEBUG("unref connection %p %s %d", conn, conn->name, conn->refs);
+ conn->refs--;
+ if (conn->refs == 0) {
+ virReleaseConnect(conn);
+ /* Already unlocked mutex */
+ return;
+ }
+
+ pthread_mutex_unlock(&conn->lock);
+}
+
+
+/**
+ * virUnrefStorageVol:
+ * @vol: the vol to unreference
+ *
+ * Unreference the vol. If the use count drops to zero, the structure is
+ * actually freed.
+ *
+ * Returns the reference count or -1 in case of failure.
+ */
+int
+virUnrefStorageVol(virStorageVolPtr vol) {
+ int refs;
+
+ if (!VIR_IS_CONNECTED_STORAGE_VOL(vol)) {
+ virLibConnError(vol->conn, VIR_ERR_INVALID_ARG, __FUNCTION__);
+ return(-1);
+ }
+ pthread_mutex_lock(&vol->conn->lock);
+ DEBUG("unref vol %p %s %d", vol, vol->name, vol->refs);
+ vol->refs--;
+ refs = vol->refs;
+ if (refs == 0) {
+ virReleaseStorageVol(vol);
+ /* Already unlocked mutex */
+ return (0);
+ }
+
+ pthread_mutex_unlock(&vol->conn->lock);
+ return (refs);
+}
diff -r ef2d00e6bc78 src/libvirt.h
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/libvirt.h Wed Oct 29 11:48:08 2008 +0000
@@ -0,0 +1,98 @@
+/*
+ * libvirt.h: publically exported APIs, not for public use
+ *
+ * Copyright (C) 2006-2008 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, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ */
+
+#ifndef __LIBVIRT_H_
+#define __LIBVIRT_H_
+
+#include "internal.h"
+
+
+/************************************************************************
+ * *
+ * API for domain/connections (de)allocations and lookups *
+ * *
+ ************************************************************************/
+
+virConnectPtr virGetConnect(void);
+int virUnrefConnect(virConnectPtr conn);
+virDomainPtr __virGetDomain(virConnectPtr conn,
+ const char *name,
+ const unsigned char *uuid);
+int virUnrefDomain(virDomainPtr domain);
+virNetworkPtr __virGetNetwork(virConnectPtr conn,
+ const char *name,
+ const unsigned char *uuid);
+int virUnrefNetwork(virNetworkPtr network);
+
+virStoragePoolPtr __virGetStoragePool(virConnectPtr conn,
+ const char *name,
+ const unsigned char *uuid);
+int virUnrefStoragePool(virStoragePoolPtr pool);
+virStorageVolPtr __virGetStorageVol(virConnectPtr conn,
+ const char *pool,
+ const char *name,
+ const char *key);
+int virUnrefStorageVol(virStorageVolPtr vol);
+
+#define virGetDomain(c,n,u) __virGetDomain((c),(n),(u))
+#define virGetNetwork(c,n,u) __virGetNetwork((c),(n),(u))
+#define virGetStoragePool(c,n,u) __virGetStoragePool((c),(n),(u))
+#define virGetStorageVol(c,p,n,u) __virGetStorageVol((c),(p),(n),(u))
+
+#ifdef WITH_LIBVIRTD
+int __virStateInitialize(void);
+int __virStateCleanup(void);
+int __virStateReload(void);
+int __virStateActive(void);
+int __virStateSigDispatcher(siginfo_t *siginfo);
+#define virStateInitialize() __virStateInitialize()
+#define virStateCleanup() __virStateCleanup()
+#define virStateReload() __virStateReload()
+#define virStateActive() __virStateActive()
+#define virStateSigDispatcher(s) __virStateSigDispatcher(s)
+#endif
+
+int __virDrvSupportsFeature (virConnectPtr conn, int feature);
+
+int __virDomainMigratePrepare (virConnectPtr dconn,
+ char **cookie,
+ int *cookielen,
+ const char *uri_in,
+ char **uri_out,
+ unsigned long flags,
+ const char *dname,
+ unsigned long bandwidth);
+int __virDomainMigratePerform (virDomainPtr domain,
+ const char *cookie,
+ int cookielen,
+ const char *uri,
+ unsigned long flags,
+ const char *dname,
+ unsigned long bandwidth);
+virDomainPtr __virDomainMigrateFinish (virConnectPtr dconn,
+ const char *dname,
+ const char *cookie,
+ int cookielen,
+ const char *uri,
+ unsigned long flags);
+
+
+#endif
diff -r ef2d00e6bc78 src/lxc_driver.c
--- a/src/lxc_driver.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/lxc_driver.c Wed Oct 29 11:48:08 2008 +0000
@@ -36,6 +36,7 @@
#include <wait.h>
#include "virterror.h"
+#include "libvirt.h"
#include "lxc_conf.h"
#include "lxc_container.h"
#include "lxc_driver.h"
diff -r ef2d00e6bc78 src/network_driver.c
--- a/src/network_driver.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/network_driver.c Wed Oct 29 11:48:08 2008 +0000
@@ -45,6 +45,7 @@
#include <sys/ioctl.h>
#include "virterror.h"
+#include "libvirt.h"
#include "network_driver.h"
#include "network_conf.h"
#include "driver.h"
diff -r ef2d00e6bc78 src/openvz_driver.c
--- a/src/openvz_driver.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/openvz_driver.c Wed Oct 29 11:48:08 2008 +0000
@@ -48,6 +48,7 @@
#include <sys/wait.h>
#include "virterror.h"
+#include "libvirt.h"
#include "openvz_driver.h"
#include "event.h"
#include "buf.h"
diff -r ef2d00e6bc78 src/proxy_internal.h
--- a/src/proxy_internal.h Wed Oct 29 11:36:21 2008 +0000
+++ b/src/proxy_internal.h Wed Oct 29 11:48:08 2008 +0000
@@ -12,7 +12,8 @@
#ifndef __LIBVIR_PROXY_H__
#define __LIBVIR_PROXY_H__
-#include "libvirt/libvirt.h"
+#include "internal.h"
+#include "libvirt.h"
#define PROXY_SOCKET_PATH "/tmp/livirt_proxy_conn"
#define PROXY_PROTO_VERSION 1
diff -r ef2d00e6bc78 src/qemu_driver.c
--- a/src/qemu_driver.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/qemu_driver.c Wed Oct 29 11:48:08 2008 +0000
@@ -53,6 +53,7 @@
#endif
#include "virterror.h"
+#include "libvirt.h"
#include "qemu_driver.h"
#include "qemu_conf.h"
#include "c-ctype.h"
diff -r ef2d00e6bc78 src/remote_internal.c
--- a/src/remote_internal.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/remote_internal.c Wed Oct 29 11:48:08 2008 +0000
@@ -74,6 +74,7 @@
#endif
#include "virterror.h"
+#include "libvirt.h"
#include "driver.h"
#include "buf.h"
#include "qparams.h"
diff -r ef2d00e6bc78 src/storage_driver.c
--- a/src/storage_driver.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/storage_driver.c Wed Oct 29 11:48:08 2008 +0000
@@ -33,6 +33,7 @@
#include <string.h>
#include "virterror.h"
+#include "libvirt.h"
#include "driver.h"
#include "util.h"
#include "storage_driver.h"
diff -r ef2d00e6bc78 src/test.c
--- a/src/test.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/test.c Wed Oct 29 11:48:08 2008 +0000
@@ -32,6 +32,7 @@
#include "virterror.h"
+#include "libvirt.h"
#include "test.h"
#include "buf.h"
#include "util.h"
diff -r ef2d00e6bc78 src/xen_internal.c
--- a/src/xen_internal.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/xen_internal.c Wed Oct 29 11:48:08 2008 +0000
@@ -41,6 +41,7 @@
#include <xen/sched.h>
#include "virterror.h"
+#include "libvirt.h"
#include "driver.h"
#include "util.h"
#include "xen_unified.h"
diff -r ef2d00e6bc78 src/xend_internal.c
--- a/src/xend_internal.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/xend_internal.c Wed Oct 29 11:48:08 2008 +0000
@@ -33,6 +33,7 @@
#include <errno.h>
#include "virterror.h"
+#include "libvirt.h"
#include "xend_internal.h"
#include "driver.h"
#include "util.h"
diff -r ef2d00e6bc78 src/xm_internal.c
--- a/src/xm_internal.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/xm_internal.c Wed Oct 29 11:48:08 2008 +0000
@@ -36,6 +36,7 @@
#include <xen/dom0_ops.h>
#include "virterror.h"
+#include "libvirt.h"
#include "xm_internal.h"
#include "xen_unified.h"
#include "xend_internal.h"
diff -r ef2d00e6bc78 src/xs_internal.c
--- a/src/xs_internal.c Wed Oct 29 11:36:21 2008 +0000
+++ b/src/xs_internal.c Wed Oct 29 11:48:08 2008 +0000
@@ -27,6 +27,7 @@
#include <xs.h>
#include "virterror.h"
+#include "libvirt.h"
#include "driver.h"
#include "xen_unified.h"
#include "xs_internal.h"
--
|: 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 :|
--
Libvir-list mailing list
Libvir-list(a)redhat.com
https://www.redhat.com/mailman/listinfo/libvir-list