This is a self-locking wrapper around virHashTable. Only a limited set
of APIs are implemented now (the ones which are used in the following
patch) as more can be added on demand.
Signed-off-by: Jiri Denemark <jdenemar(a)redhat.com>
---
src/libvirt_private.syms | 3 ++
src/util/virhash.c | 81 ++++++++++++++++++++++++++++++++++++++++++++++++
src/util/virhash.h | 10 ++++++
3 files changed, 94 insertions(+)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 1566d11..377b7d8 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -1482,6 +1482,9 @@ virHashEqual;
virHashForEach;
virHashFree;
virHashGetItems;
+virHashLockableNew;
+virHashLockableSteal;
+virHashLockableUpdate;
virHashLookup;
virHashRemoveAll;
virHashRemoveEntry;
diff --git a/src/util/virhash.c b/src/util/virhash.c
index e3c1880..0f3934f 100644
--- a/src/util/virhash.c
+++ b/src/util/virhash.c
@@ -31,6 +31,7 @@
#include "virhashcode.h"
#include "virrandom.h"
#include "virstring.h"
+#include "virobject.h"
#define VIR_FROM_THIS VIR_FROM_NONE
@@ -76,6 +77,28 @@ struct _virHashTable {
virHashKeyFree keyFree;
};
+struct _virHashLockable {
+ virObjectLockable parent;
+ virHashTablePtr hash;
+};
+
+static virClassPtr virHashLockableClass;
+static void virHashLockableDispose(void *obj);
+
+static int virHashLockableOnceInit(void)
+{
+ virHashLockableClass = virClassNew(virClassForObjectLockable(),
+ "virHashLockable",
+ sizeof(virHashLockable),
+ virHashLockableDispose);
+ if (!virHashLockableClass)
+ return -1;
+ else
+ return 0;
+}
+VIR_ONCE_GLOBAL_INIT(virHashLockable)
+
+
static uint32_t virHashStrCode(const void *name, uint32_t seed)
{
return virHashCodeGen(name, strlen(name), seed);
@@ -178,6 +201,36 @@ virHashTablePtr virHashCreate(ssize_t size, virHashDataFree
dataFree)
virHashStrFree);
}
+
+virHashLockablePtr
+virHashLockableNew(ssize_t size,
+ virHashDataFree dataFree)
+{
+ virHashLockablePtr hash;
+
+ if (virHashLockableInitialize() < 0)
+ return NULL;
+
+ if (!(hash = virObjectLockableNew(virHashLockableClass)))
+ return NULL;
+
+ if (!(hash->hash = virHashCreate(size, dataFree))) {
+ virObjectUnref(hash);
+ return NULL;
+ }
+ return hash;
+}
+
+
+static void
+virHashLockableDispose(void *obj)
+{
+ virHashLockablePtr hash = obj;
+
+ virHashFree(hash->hash);
+}
+
+
/**
* virHashGrow:
* @table: the hash table
@@ -360,6 +413,21 @@ virHashUpdateEntry(virHashTablePtr table, const void *name,
return virHashAddOrUpdateEntry(table, name, userdata, true);
}
+int
+virHashLockableUpdate(virHashLockablePtr table,
+ const void *name,
+ void *userdata)
+{
+ int ret;
+
+ virObjectLock(table);
+ ret = virHashAddOrUpdateEntry(table->hash, name, userdata, true);
+ virObjectUnlock(table);
+
+ return ret;
+}
+
+
/**
* virHashLookup:
* @table: the hash table
@@ -409,6 +477,19 @@ void *virHashSteal(virHashTablePtr table, const void *name)
return data;
}
+void *
+virHashLockableSteal(virHashLockablePtr table,
+ const void *name)
+{
+ void *data;
+
+ virObjectLock(table);
+ data = virHashSteal(table->hash, name);
+ virObjectUnlock(table);
+
+ return data;
+}
+
/**
* virHashSize:
diff --git a/src/util/virhash.h b/src/util/virhash.h
index a137137..bef20fd 100644
--- a/src/util/virhash.h
+++ b/src/util/virhash.h
@@ -21,6 +21,9 @@
typedef struct _virHashTable virHashTable;
typedef virHashTable *virHashTablePtr;
+typedef struct _virHashLockable virHashLockable;
+typedef virHashLockable *virHashLockablePtr;
+
/*
* function types:
*/
@@ -101,6 +104,8 @@ typedef void (*virHashKeyFree)(void *name);
*/
virHashTablePtr virHashCreate(ssize_t size,
virHashDataFree dataFree);
+virHashLockablePtr virHashLockableNew(ssize_t size,
+ virHashDataFree dataFree);
virHashTablePtr virHashCreateFull(ssize_t size,
virHashDataFree dataFree,
virHashKeyCode keyCode,
@@ -119,6 +124,9 @@ int virHashAddEntry(virHashTablePtr table,
int virHashUpdateEntry(virHashTablePtr table,
const void *name,
void *userdata);
+int virHashLockableUpdate(virHashLockablePtr table,
+ const void *name,
+ void *userdata);
/*
* Remove an entry from the hash table.
@@ -140,6 +148,8 @@ void *virHashLookup(const virHashTable *table, const void *name);
* Retrieve & remove the userdata.
*/
void *virHashSteal(virHashTablePtr table, const void *name);
+void *virHashLockableSteal(virHashLockablePtr table,
+ const void *name);
/*
* Get the hash table's key/value pairs and have them optionally sorted.
--
2.4.5