daemon, threads: plug a memory leak

* daemon/libvirtd.c (qemudStartWorker, qemudStartEventLoop): Avoid
leaking pthread_attr resources.
* src/util/threads-pthread.c (virThreadCreate): Likewise.
This commit is contained in:
Eric Blake 2010-12-10 17:35:58 -07:00
parent e414dab4d6
commit 6e9a29c887
2 changed files with 45 additions and 18 deletions

View File

@ -1600,15 +1600,20 @@ static void *qemudWorker(void *data)
} }
} }
static int qemudStartWorker(struct qemud_server *server, static int
struct qemud_worker *worker) { qemudStartWorker(struct qemud_server *server,
struct qemud_worker *worker)
{
pthread_attr_t attr; pthread_attr_t attr;
pthread_attr_init(&attr); int ret = -1;
if (pthread_attr_init(&attr) != 0)
return -1;
/* We want to join workers, so don't detach them */ /* We want to join workers, so don't detach them */
/*pthread_attr_setdetachstate(&attr, 1);*/ /*pthread_attr_setdetachstate(&attr, 1);*/
if (worker->hasThread) if (worker->hasThread)
return -1; goto cleanup;
worker->server = server; worker->server = server;
worker->hasThread = 1; worker->hasThread = 1;
@ -1621,10 +1626,13 @@ static int qemudStartWorker(struct qemud_server *server,
worker) != 0) { worker) != 0) {
worker->hasThread = 0; worker->hasThread = 0;
worker->server = NULL; worker->server = NULL;
return -1; goto cleanup;
} }
return 0; ret = 0;
cleanup:
pthread_attr_destroy(&attr);
return ret;
} }
@ -2414,9 +2422,14 @@ cleanup:
} }
static int qemudStartEventLoop(struct qemud_server *server) { static int
qemudStartEventLoop(struct qemud_server *server)
{
pthread_attr_t attr; pthread_attr_t attr;
pthread_attr_init(&attr); int ret = -1;
if (pthread_attr_init(&attr) != 0)
return -1;
/* We want to join the eventloop, so don't detach it */ /* We want to join the eventloop, so don't detach it */
/*pthread_attr_setdetachstate(&attr, 1);*/ /*pthread_attr_setdetachstate(&attr, 1);*/
@ -2424,11 +2437,14 @@ static int qemudStartEventLoop(struct qemud_server *server) {
&attr, &attr,
qemudRunLoop, qemudRunLoop,
server) != 0) server) != 0)
return -1; goto cleanup;
server->hasEventThread = 1; server->hasEventThread = 1;
return 0; ret = 0;
cleanup:
pthread_attr_destroy(&attr);
return ret;
} }

View File

@ -157,9 +157,15 @@ int virThreadCreate(virThreadPtr thread,
{ {
struct virThreadArgs *args; struct virThreadArgs *args;
pthread_attr_t attr; pthread_attr_t attr;
pthread_attr_init(&attr); int ret = -1;
if (VIR_ALLOC(args) < 0) int err;
return -1;
if ((err = pthread_attr_init(&attr)) != 0)
goto cleanup;
if (VIR_ALLOC(args) < 0) {
err = ENOMEM;
goto cleanup;
}
args->func = func; args->func = func;
args->opaque = opaque; args->opaque = opaque;
@ -167,14 +173,19 @@ int virThreadCreate(virThreadPtr thread,
if (!joinable) if (!joinable)
pthread_attr_setdetachstate(&attr, 1); pthread_attr_setdetachstate(&attr, 1);
int ret = pthread_create(&thread->thread, &attr, virThreadHelper, args); err = pthread_create(&thread->thread, &attr, virThreadHelper, args);
if (ret != 0) { if (err != 0) {
VIR_FREE(args); VIR_FREE(args);
errno = ret; goto cleanup;
return -1;
} }
/* New thread owns 'args' in success case, so don't free */ /* New thread owns 'args' in success case, so don't free */
return 0;
ret = 0;
cleanup:
pthread_attr_destroy(&attr);
if (ret < 0)
errno = err;
return ret;
} }
void virThreadSelf(virThreadPtr thread) void virThreadSelf(virThreadPtr thread)