diff --git a/src/libvirt_probes.d b/src/libvirt_probes.d index 3b138a9adf..807239fe82 100644 --- a/src/libvirt_probes.d +++ b/src/libvirt_probes.d @@ -77,9 +77,7 @@ provider libvirt { # file: src/rpc/virkeepalive.c # prefix: rpc - probe rpc_keepalive_new(void *ka, void *client, int refs); - probe rpc_keepalive_ref(void *ka, void *client, int refs); - probe rpc_keepalive_free(void *ka, void *client, int refs); + probe rpc_keepalive_new(void *ka, void *client); probe rpc_keepalive_start(void *ka, void *client, int interval, int count); probe rpc_keepalive_stop(void *ka, void *client); probe rpc_keepalive_send(void *ka, void *client, int prog, int vers, int proc); diff --git a/src/rpc/virkeepalive.c b/src/rpc/virkeepalive.c index ffb059e4b8..7ff125efad 100644 --- a/src/rpc/virkeepalive.c +++ b/src/rpc/virkeepalive.c @@ -35,7 +35,8 @@ #define VIR_FROM_THIS VIR_FROM_RPC struct _virKeepAlive { - int refs; + virObject object; + virMutex lock; int interval; @@ -52,6 +53,21 @@ struct _virKeepAlive { }; +static virClassPtr virKeepAliveClass; +static void virKeepAliveDispose(void *obj); + +static int virKeepAliveOnceInit(void) +{ + if (!(virKeepAliveClass = virClassNew("virKeepAlive", + sizeof(virKeepAlive), + virKeepAliveDispose))) + return -1; + + return 0; +} + +VIR_ONCE_GLOBAL_INIT(virKeepAlive) + static void virKeepAliveLock(virKeepAlivePtr ka) { @@ -165,7 +181,7 @@ virKeepAliveTimer(int timer ATTRIBUTE_UNUSED, void *opaque) if (!dead && !msg) goto cleanup; - ka->refs++; + virObjectRef(ka); virKeepAliveUnlock(ka); if (dead) { @@ -176,20 +192,13 @@ virKeepAliveTimer(int timer ATTRIBUTE_UNUSED, void *opaque) } virKeepAliveLock(ka); - ka->refs--; + virObjectUnref(ka); cleanup: virKeepAliveUnlock(ka); } -static void -virKeepAliveTimerFree(void *opaque) -{ - virKeepAliveFree(opaque); -} - - virKeepAlivePtr virKeepAliveNew(int interval, unsigned int count, @@ -202,17 +211,17 @@ virKeepAliveNew(int interval, VIR_DEBUG("client=%p, interval=%d, count=%u", client, interval, count); - if (VIR_ALLOC(ka) < 0) { - virReportOOMError(); + if (virKeepAliveInitialize() < 0) + return NULL; + + if (!(ka = virObjectNew(virKeepAliveClass))) return NULL; - } if (virMutexInit(&ka->lock) < 0) { VIR_FREE(ka); return NULL; } - ka->refs = 1; ka->interval = interval; ka->count = count; ka->countToDeath = count; @@ -223,44 +232,20 @@ virKeepAliveNew(int interval, ka->freeCB = freeCB; PROBE(RPC_KEEPALIVE_NEW, - "ka=%p client=%p refs=%d", - ka, ka->client, ka->refs); + "ka=%p client=%p", + ka, ka->client); return ka; } void -virKeepAliveRef(virKeepAlivePtr ka) +virKeepAliveDispose(void *obj) { - virKeepAliveLock(ka); - ka->refs++; - PROBE(RPC_KEEPALIVE_REF, - "ka=%p client=%p refs=%d", - ka, ka->client, ka->refs); - virKeepAliveUnlock(ka); -} - - -void -virKeepAliveFree(virKeepAlivePtr ka) -{ - if (!ka) - return; - - virKeepAliveLock(ka); - PROBE(RPC_KEEPALIVE_FREE, - "ka=%p client=%p refs=%d", - ka, ka->client, ka->refs); - - if (--ka->refs > 0) { - virKeepAliveUnlock(ka); - return; - } + virKeepAlivePtr ka = obj; virMutexDestroy(&ka->lock); ka->freeCB(ka->client); - VIR_FREE(ka); } @@ -311,12 +296,12 @@ virKeepAliveStart(virKeepAlivePtr ka, timeout = ka->interval - delay; ka->intervalStart = now - (ka->interval - timeout); ka->timer = virEventAddTimeout(timeout * 1000, virKeepAliveTimer, - ka, virKeepAliveTimerFree); + ka, virObjectFreeCallback); if (ka->timer < 0) goto cleanup; /* the timer now has another reference to this object */ - ka->refs++; + virObjectRef(ka); ret = 0; cleanup: diff --git a/src/rpc/virkeepalive.h b/src/rpc/virkeepalive.h index 52e1d046e6..0f77f340b3 100644 --- a/src/rpc/virkeepalive.h +++ b/src/rpc/virkeepalive.h @@ -24,6 +24,7 @@ # define __VIR_KEEPALIVE_H__ # include "virnetmessage.h" +# include "virobject.h" typedef int (*virKeepAliveSendFunc)(void *client, virNetMessagePtr msg); typedef void (*virKeepAliveDeadFunc)(void *client); @@ -42,9 +43,6 @@ virKeepAlivePtr virKeepAliveNew(int interval, ATTRIBUTE_NONNULL(3) ATTRIBUTE_NONNULL(4) ATTRIBUTE_NONNULL(5) ATTRIBUTE_NONNULL(6); -void virKeepAliveRef(virKeepAlivePtr ka); -void virKeepAliveFree(virKeepAlivePtr ka); - int virKeepAliveStart(virKeepAlivePtr ka, int interval, unsigned int count); diff --git a/src/rpc/virnetclient.c b/src/rpc/virnetclient.c index 58c80e2ba0..6d8c1327cc 100644 --- a/src/rpc/virnetclient.c +++ b/src/rpc/virnetclient.c @@ -361,7 +361,7 @@ error: VIR_FORCE_CLOSE(wakeupFD[1]); if (ka) { virKeepAliveStop(ka); - virKeepAliveFree(ka); + virObjectUnref(ka); } virNetClientFree(client); return NULL; @@ -551,7 +551,7 @@ virNetClientCloseLocked(virNetClientPtr client) if (ka) { virKeepAliveStop(ka); - virKeepAliveFree(ka); + virObjectUnref(ka); } if (closeCb) closeCb(client, closeReason, closeOpaque); diff --git a/src/rpc/virnetserverclient.c b/src/rpc/virnetserverclient.c index 471cca0f8e..3a6439da29 100644 --- a/src/rpc/virnetserverclient.c +++ b/src/rpc/virnetserverclient.c @@ -629,7 +629,7 @@ void virNetServerClientClose(virNetServerClientPtr client) client->keepalive = NULL; client->refs++; virNetServerClientUnlock(client); - virKeepAliveFree(ka); + virObjectUnref(ka); virNetServerClientLock(client); client->refs--; } @@ -1199,7 +1199,7 @@ cleanup: virNetServerClientUnlock(client); if (ka) virKeepAliveStop(ka); - virKeepAliveFree(ka); + virObjectUnref(ka); return ret; }