Commit 4b48aaf9 authored by Dridi Boukelmoune's avatar Dridi Boukelmoune Committed by Lasse Karstensen

Barriers can be cyclic but not like semaphores

This is useful in HTTP loops where it's impossible to predict and use an
array of barriers. All cycles expect the same number of waiters, unlike
semaphores.
parent 315bdbcc
varnishtest "Barrier operations" varnishtest "Barrier operations"
barrier b1 cond 4 # bs -> server, bc -> client, bb -> both
barrier b2 cond 4 barrier bs cond 4
barrier bc cond 4
barrier bb cond 4 -cyclic
server s1 { server s1 {
rxreq rxreq
barrier b1 sync barrier bs sync
barrier bb sync
delay .9 delay .9
txresp txresp
} -start } -start
server s2 { server s2 {
rxreq rxreq
barrier b1 sync barrier bs sync
barrier bb sync
delay .6 delay .6
txresp txresp
} -start } -start
server s3 { server s3 {
rxreq rxreq
barrier b1 sync barrier bs sync
barrier bb sync
delay .2 delay .2
txresp txresp
} -start } -start
...@@ -28,25 +33,30 @@ client c1 -connect ${s1_sock} { ...@@ -28,25 +33,30 @@ client c1 -connect ${s1_sock} {
delay .2 delay .2
txreq txreq
rxresp rxresp
barrier b2 sync barrier bc sync
barrier bb sync
} -start } -start
client c2 -connect ${s2_sock} { client c2 -connect ${s2_sock} {
delay .6 delay .6
txreq txreq
rxresp rxresp
barrier b2 sync barrier bc sync
barrier bb sync
} -start } -start
client c3 -connect ${s3_sock} { client c3 -connect ${s3_sock} {
delay .9 delay .9
txreq txreq
rxresp rxresp
barrier b2 sync barrier bc sync
barrier bb sync
} -start } -start
# Wait for all servers to have received requests # Wait for all servers to have received requests
barrier b1 sync barrier bs sync
barrier bb sync
# Wait for all clients to have received responses # Wait for all clients to have received responses
barrier b2 sync barrier bc sync
barrier bb sync
...@@ -52,6 +52,7 @@ struct barrier { ...@@ -52,6 +52,7 @@ struct barrier {
unsigned waiters; unsigned waiters;
unsigned expected; unsigned expected;
unsigned cyclic;
enum barrier_e type; enum barrier_e type;
}; };
...@@ -122,6 +123,23 @@ barrier_sock(struct barrier *b, const char *av, struct vtclog *vl) ...@@ -122,6 +123,23 @@ barrier_sock(struct barrier *b, const char *av, struct vtclog *vl)
INCOMPL(); INCOMPL();
} }
static void
barrier_cyclic(struct barrier *b, struct vtclog *vl)
{
CHECK_OBJ_NOTNULL(b, BARRIER_MAGIC);
if (b->type == BARRIER_NONE)
vtc_log(vl, 0,
"Barrier(%s) use error: not initialized", b->name);
if (b->waiters != 0)
vtc_log(vl, 0,
"Barrier(%s) use error: already in use", b->name);
b->cyclic = 1;
}
/********************************************************************** /**********************************************************************
* Sync a barrier * Sync a barrier
*/ */
...@@ -148,6 +166,9 @@ barrier_cond_sync(struct barrier *b, struct vtclog *vl) ...@@ -148,6 +166,9 @@ barrier_cond_sync(struct barrier *b, struct vtclog *vl)
b->name, b->waiters, b->expected); b->name, b->waiters, b->expected);
AZ(pthread_cond_wait(&b->cond, &b->mtx)); AZ(pthread_cond_wait(&b->cond, &b->mtx));
} }
if (b->cyclic)
b->waiters = 0;
} }
static void static void
...@@ -189,6 +210,9 @@ cmd_barrier(CMD_ARGS) ...@@ -189,6 +210,9 @@ cmd_barrier(CMD_ARGS)
VTAILQ_FOREACH_SAFE(b, &barriers, list, b2) { VTAILQ_FOREACH_SAFE(b, &barriers, list, b2) {
AZ(pthread_mutex_lock(&b->mtx)); AZ(pthread_mutex_lock(&b->mtx));
assert(b->type != BARRIER_NONE); assert(b->type != BARRIER_NONE);
if (b->cyclic)
AZ(b->waiters);
else
assert(b->waiters == b->expected); assert(b->waiters == b->expected);
AZ(pthread_mutex_unlock(&b->mtx)); AZ(pthread_mutex_unlock(&b->mtx));
} }
...@@ -226,6 +250,10 @@ cmd_barrier(CMD_ARGS) ...@@ -226,6 +250,10 @@ cmd_barrier(CMD_ARGS)
barrier_sync(b, vl); barrier_sync(b, vl);
continue; continue;
} }
if (!strcmp(*av, "-cyclic")) {
barrier_cyclic(b, vl);
continue;
}
vtc_log(vl, 0, "Unknown barrier argument: %s", *av); vtc_log(vl, 0, "Unknown barrier argument: %s", *av);
} }
AZ(pthread_mutex_unlock(&b->mtx)); AZ(pthread_mutex_unlock(&b->mtx));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment