Explicitly track whether the buck is held in remote client

Instead of inferring whether the buck is held from the waitDispatch
pointer, use an explicit 'bool haveTheBuck' field

* src/rpc/virnetclient.c: Explicitly track the buck
This commit is contained in:
Daniel P. Berrange 2011-11-11 15:28:41 +00:00
parent 2501d27e18
commit fa9595003d

View File

@ -88,6 +88,8 @@ struct _virNetClient {
/* List of threads currently waiting for dispatch */ /* List of threads currently waiting for dispatch */
virNetClientCallPtr waitDispatch; virNetClientCallPtr waitDispatch;
/* True if a thread holds the buck */
bool haveTheBuck;
size_t nstreams; size_t nstreams;
virNetClientStreamPtr *streams; virNetClientStreamPtr *streams;
@ -1218,12 +1220,13 @@ static int virNetClientIO(virNetClientPtr client,
thiscall->msg->bufferLength, thiscall->msg->bufferLength,
client->waitDispatch); client->waitDispatch);
/* Check to see if another thread is dispatching */
if (client->waitDispatch) {
char ignore = 1;
/* Stick ourselves on the end of the wait queue */ /* Stick ourselves on the end of the wait queue */
virNetClientCallQueue(&client->waitDispatch, thiscall); virNetClientCallQueue(&client->waitDispatch, thiscall);
/* Check to see if another thread is dispatching */
if (client->haveTheBuck) {
char ignore = 1;
/* Force other thread to wakeup from poll */ /* Force other thread to wakeup from poll */
if (safewrite(client->wakeupSendFD, &ignore, sizeof(ignore)) != sizeof(ignore)) { if (safewrite(client->wakeupSendFD, &ignore, sizeof(ignore)) != sizeof(ignore)) {
virNetClientCallRemove(&client->waitDispatch, thiscall); virNetClientCallRemove(&client->waitDispatch, thiscall);
@ -1259,12 +1262,11 @@ static int virNetClientIO(virNetClientPtr client,
} }
/* Grr, someone passed the buck onto us ... */ /* Grr, someone passed the buck onto us ... */
} else {
/* We're the first to arrive */
virNetClientCallQueue(&client->waitDispatch, thiscall);
} }
VIR_DEBUG("We have the buck %p %p", client->waitDispatch, thiscall); VIR_DEBUG("We have the buck %p %p", client->waitDispatch, thiscall);
client->haveTheBuck = true;
/* /*
* The buck stops here! * The buck stops here!
* *
@ -1290,6 +1292,8 @@ static int virNetClientIO(virNetClientPtr client,
virGetLastError()) virGetLastError())
rv = -1; rv = -1;
client->haveTheBuck = false;
cleanup: cleanup:
VIR_DEBUG("All done with our call %p %p %d", client->waitDispatch, thiscall, rv); VIR_DEBUG("All done with our call %p %p %d", client->waitDispatch, thiscall, rv);
return rv; return rv;
@ -1308,7 +1312,7 @@ void virNetClientIncomingEvent(virNetSocketPtr sock,
goto done; goto done;
/* This should be impossible, but it doesn't hurt to check */ /* This should be impossible, but it doesn't hurt to check */
if (client->waitDispatch) if (client->haveTheBuck)
goto done; goto done;
VIR_DEBUG("Event fired %p %d", sock, events); VIR_DEBUG("Event fired %p %d", sock, events);