mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-01-25 10:03:49 +03:00
Add a virObjectLockable class holding a mutex
A great many virObject instances require a mutex, so introduce a convenient class for this which provides a mutex. This avoids repeating the tedious init/destroy code Signed-off-by: Daniel P. Berrange <berrange@redhat.com>
This commit is contained in:
parent
69218922e8
commit
b545f65d16
@ -1770,13 +1770,17 @@ virNodeSuspendGetTargetMask;
|
|||||||
|
|
||||||
# virobject.h
|
# virobject.h
|
||||||
virClassForObject;
|
virClassForObject;
|
||||||
|
virClassForObjectLockable;
|
||||||
virClassIsDerivedFrom;
|
virClassIsDerivedFrom;
|
||||||
virClassName;
|
virClassName;
|
||||||
virClassNew;
|
virClassNew;
|
||||||
virObjectFreeCallback;
|
virObjectFreeCallback;
|
||||||
virObjectIsClass;
|
virObjectIsClass;
|
||||||
|
virObjectLock;
|
||||||
|
virObjectLockableNew;
|
||||||
virObjectNew;
|
virObjectNew;
|
||||||
virObjectRef;
|
virObjectRef;
|
||||||
|
virObjectUnlock;
|
||||||
virObjectUnref;
|
virObjectUnref;
|
||||||
|
|
||||||
|
|
||||||
|
@ -43,6 +43,9 @@ struct _virClass {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static virClassPtr virObjectClass;
|
static virClassPtr virObjectClass;
|
||||||
|
static virClassPtr virObjectLockableClass;
|
||||||
|
|
||||||
|
static void virObjectLockableDispose(void *anyobj);
|
||||||
|
|
||||||
static int virObjectOnceInit(void)
|
static int virObjectOnceInit(void)
|
||||||
{
|
{
|
||||||
@ -52,6 +55,12 @@ static int virObjectOnceInit(void)
|
|||||||
NULL)))
|
NULL)))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
|
if (!(virObjectLockableClass = virClassNew(virObjectClass,
|
||||||
|
"virObjectLockable",
|
||||||
|
sizeof(virObjectLockable),
|
||||||
|
virObjectLockableDispose)))
|
||||||
|
return -1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -72,6 +81,20 @@ virClassPtr virClassForObject(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* virClassForObjectLockable:
|
||||||
|
*
|
||||||
|
* Returns the class instance for the virObjectLockable type
|
||||||
|
*/
|
||||||
|
virClassPtr virClassForObjectLockable(void)
|
||||||
|
{
|
||||||
|
if (!virObjectInitialize() < 0)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
return virObjectLockableClass;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* virClassNew:
|
* virClassNew:
|
||||||
* @parent: the parent class
|
* @parent: the parent class
|
||||||
@ -180,6 +203,38 @@ void *virObjectNew(virClassPtr klass)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void *virObjectLockableNew(virClassPtr klass)
|
||||||
|
{
|
||||||
|
virObjectLockablePtr obj;
|
||||||
|
|
||||||
|
if (!virClassIsDerivedFrom(klass, virClassForObjectLockable())) {
|
||||||
|
virReportInvalidArg(klass,
|
||||||
|
_("Class %s must derive from virObjectLockable"),
|
||||||
|
virClassName(klass));
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(obj = virObjectNew(klass)))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if (virMutexInit(&obj->lock) < 0) {
|
||||||
|
virReportSystemError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||||
|
_("Unable to initialize mutex"));
|
||||||
|
virObjectUnref(obj);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void virObjectLockableDispose(void *anyobj)
|
||||||
|
{
|
||||||
|
virObjectLockablePtr obj = anyobj;
|
||||||
|
|
||||||
|
virMutexDestroy(&obj->lock);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* virObjectUnref:
|
* virObjectUnref:
|
||||||
* @anyobj: any instance of virObjectPtr
|
* @anyobj: any instance of virObjectPtr
|
||||||
@ -209,8 +264,6 @@ bool virObjectUnref(void *anyobj)
|
|||||||
klass = klass->parent;
|
klass = klass->parent;
|
||||||
}
|
}
|
||||||
|
|
||||||
virMutexDestroy(&obj->lock);
|
|
||||||
|
|
||||||
/* Clear & poison object */
|
/* Clear & poison object */
|
||||||
memset(obj, 0, obj->klass->objectSize);
|
memset(obj, 0, obj->klass->objectSize);
|
||||||
obj->magic = 0xDEADBEEF;
|
obj->magic = 0xDEADBEEF;
|
||||||
@ -243,6 +296,53 @@ void *virObjectRef(void *anyobj)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* virObjectLock:
|
||||||
|
* @anyobj: any instance of virObjectLockablePtr
|
||||||
|
*
|
||||||
|
* Acquire a lock on @anyobj. The lock must be
|
||||||
|
* released by virObjectUnlock.
|
||||||
|
*
|
||||||
|
* The caller is expected to have acquired a reference
|
||||||
|
* on the object before locking it (eg virObjectRef).
|
||||||
|
* The object must be unlocked before releasing this
|
||||||
|
* reference.
|
||||||
|
*/
|
||||||
|
void virObjectLock(void *anyobj)
|
||||||
|
{
|
||||||
|
virObjectLockablePtr obj = anyobj;
|
||||||
|
|
||||||
|
if (!virObjectIsClass(obj, virObjectLockableClass)) {
|
||||||
|
VIR_WARN("Object %p (%s) is not a virObjectLockable instance",
|
||||||
|
obj, obj ? obj->parent.klass->name : "(unknown)");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
virMutexLock(&obj->lock);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* virObjectUnlock:
|
||||||
|
* @anyobj: any instance of virObjectLockablePtr
|
||||||
|
*
|
||||||
|
* Release a lock on @anyobj. The lock must have been
|
||||||
|
* acquired by virObjectLock.
|
||||||
|
*/
|
||||||
|
void virObjectUnlock(void *anyobj)
|
||||||
|
{
|
||||||
|
virObjectLockablePtr obj = anyobj;
|
||||||
|
|
||||||
|
if (!virObjectIsClass(obj, virObjectLockableClass)) {
|
||||||
|
VIR_WARN("Object %p (%s) is not a virObjectLockable instance",
|
||||||
|
obj, obj ? obj->parent.klass->name : "(unknown)");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
virMutexUnlock(&obj->lock);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* virObjectIsClass:
|
* virObjectIsClass:
|
||||||
* @anyobj: any instance of virObjectPtr
|
* @anyobj: any instance of virObjectPtr
|
||||||
|
@ -23,6 +23,7 @@
|
|||||||
# define __VIR_OBJECT_H__
|
# define __VIR_OBJECT_H__
|
||||||
|
|
||||||
# include "internal.h"
|
# include "internal.h"
|
||||||
|
# include "virthread.h"
|
||||||
|
|
||||||
typedef struct _virClass virClass;
|
typedef struct _virClass virClass;
|
||||||
typedef virClass *virClassPtr;
|
typedef virClass *virClassPtr;
|
||||||
@ -30,6 +31,9 @@ typedef virClass *virClassPtr;
|
|||||||
typedef struct _virObject virObject;
|
typedef struct _virObject virObject;
|
||||||
typedef virObject *virObjectPtr;
|
typedef virObject *virObjectPtr;
|
||||||
|
|
||||||
|
typedef struct _virObjectLockable virObjectLockable;
|
||||||
|
typedef virObjectLockable *virObjectLockablePtr;
|
||||||
|
|
||||||
typedef void (*virObjectDisposeCallback)(void *obj);
|
typedef void (*virObjectDisposeCallback)(void *obj);
|
||||||
|
|
||||||
struct _virObject {
|
struct _virObject {
|
||||||
@ -38,7 +42,14 @@ struct _virObject {
|
|||||||
virClassPtr klass;
|
virClassPtr klass;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct _virObjectLockable {
|
||||||
|
virObject parent;
|
||||||
|
virMutex lock;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
virClassPtr virClassForObject(void);
|
virClassPtr virClassForObject(void);
|
||||||
|
virClassPtr virClassForObjectLockable(void);
|
||||||
|
|
||||||
virClassPtr virClassNew(virClassPtr parent,
|
virClassPtr virClassNew(virClassPtr parent,
|
||||||
const char *name,
|
const char *name,
|
||||||
@ -64,4 +75,13 @@ bool virObjectIsClass(void *obj,
|
|||||||
|
|
||||||
void virObjectFreeCallback(void *opaque);
|
void virObjectFreeCallback(void *opaque);
|
||||||
|
|
||||||
|
void *virObjectLockableNew(virClassPtr klass)
|
||||||
|
ATTRIBUTE_NONNULL(1);
|
||||||
|
|
||||||
|
void virObjectLock(void *lockableobj)
|
||||||
|
ATTRIBUTE_NONNULL(1);
|
||||||
|
void virObjectUnlock(void *lockableobj)
|
||||||
|
ATTRIBUTE_NONNULL(1);
|
||||||
|
|
||||||
|
|
||||||
#endif /* __VIR_OBJECT_H */
|
#endif /* __VIR_OBJECT_H */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user