lxccontainer: lxc_container_{get,put}()

Signed-off-by: Christian Brauner <christian.brauner@ubuntu.com>
This commit is contained in:
Christian Brauner 2018-02-24 15:15:54 +01:00
parent 70849dc234
commit 045552aabe
No known key found for this signature in database
GPG Key ID: 8EB056D53EECB12D

View File

@ -281,19 +281,21 @@ static void lxc_container_free(struct lxc_container *c)
free(c); free(c);
} }
/* /* Consider the following case:
* Consider the following case: *
freer | racing get()er * |====================================================================|
================================================================== * | freer | racing get()er |
lxc_container_put() | lxc_container_get() * |====================================================================|
\ lxclock(c->privlock) | c->numthreads < 1? (no) * | lxc_container_put() | lxc_container_get() |
\ c->numthreads = 0 | \ lxclock(c->privlock) -> waits * | \ lxclock(c->privlock) | c->numthreads < 1? (no) |
\ lxcunlock() | \ * | \ c->numthreads = 0 | \ lxclock(c->privlock) -> waits |
\ lxc_container_free() | \ lxclock() returns * | \ lxcunlock() | \ |
| \ c->numthreads < 1 -> return 0 * | \ lxc_container_free() | \ lxclock() returns |
\ \ (free stuff) | * | | \ c->numthreads < 1 -> return 0 |
\ \ sem_destroy(privlock) | * | \ \ (free stuff) | |
* | \ \ sem_destroy(privlock) | |
* |_______________________________|____________________________________|
*
* When the get()er checks numthreads the first time, one of the following * When the get()er checks numthreads the first time, one of the following
* is true: * is true:
* 1. freer has set numthreads = 0. get() returns 0 * 1. freer has set numthreads = 0. get() returns 0
@ -326,6 +328,7 @@ int lxc_container_get(struct lxc_container *c)
c->numthreads++; c->numthreads++;
container_mem_unlock(c); container_mem_unlock(c);
return 1; return 1;
} }
@ -333,14 +336,18 @@ int lxc_container_put(struct lxc_container *c)
{ {
if (!c) if (!c)
return -1; return -1;
if (container_mem_lock(c)) if (container_mem_lock(c))
return -1; return -1;
if (--c->numthreads < 1) { if (--c->numthreads < 1) {
container_mem_unlock(c); container_mem_unlock(c);
lxc_container_free(c); lxc_container_free(c);
return 1; return 1;
} }
container_mem_unlock(c); container_mem_unlock(c);
return 0; return 0;
} }