mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2024-12-22 13:45:38 +00:00
Fix 100% libvirt CPU usage when --timeout is set
This commit is contained in:
parent
31135bff29
commit
9a86716446
10
ChangeLog
10
ChangeLog
@ -1,3 +1,13 @@
|
||||
Fri Feb 6 14:43:10 GMT 2009 Daniel P. Berrange <berrange@redhat.com>
|
||||
|
||||
Fix 100% CPU bound loop when libvirtd --timeout is used
|
||||
* qemud/event.c: Don't assume pthread_t is equivalent to an
|
||||
int, explicitly track whether event loop is active with a
|
||||
flag independantly of the threadLeader variable
|
||||
* qemud/qemud.c: Don't register/unregister shutdown timer
|
||||
on each loop. Register once, and activate/deactivate when
|
||||
required
|
||||
|
||||
Thu Feb 5 19:28:10 GMT 2009 John Levon <john.levon@sun.com>
|
||||
|
||||
* src/domain_conf.c: Check the last error, not the last
|
||||
|
@ -68,6 +68,7 @@ struct virEventTimeout {
|
||||
/* State for the main event loop */
|
||||
struct virEventLoop {
|
||||
pthread_mutex_t lock;
|
||||
int running;
|
||||
pthread_t leader;
|
||||
int wakeupfd[2];
|
||||
int handlesCount;
|
||||
@ -521,6 +522,7 @@ int virEventRunOnce(void) {
|
||||
int ret, timeout, nfds;
|
||||
|
||||
virEventLock();
|
||||
eventLoop.running = 1;
|
||||
eventLoop.leader = pthread_self();
|
||||
if ((nfds = virEventMakePollFDs(&fds)) < 0) {
|
||||
virEventUnlock();
|
||||
@ -572,7 +574,7 @@ int virEventRunOnce(void) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
eventLoop.leader = 0;
|
||||
eventLoop.running = 0;
|
||||
virEventUnlock();
|
||||
return 0;
|
||||
}
|
||||
@ -611,7 +613,9 @@ int virEventInit(void)
|
||||
static int virEventInterruptLocked(void)
|
||||
{
|
||||
char c = '\0';
|
||||
if (pthread_self() == eventLoop.leader)
|
||||
|
||||
if (!eventLoop.running ||
|
||||
pthread_self() == eventLoop.leader)
|
||||
return 0;
|
||||
|
||||
if (safewrite(eventLoop.wakeupfd[1], &c, sizeof(c)) != sizeof(c))
|
||||
|
@ -2031,11 +2031,15 @@ static int qemudOneLoop(void) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void qemudInactiveTimer(int timer ATTRIBUTE_UNUSED, void *data) {
|
||||
static void qemudInactiveTimer(int timerid, void *data) {
|
||||
struct qemud_server *server = (struct qemud_server *)data;
|
||||
DEBUG0("Got inactive timer expiry");
|
||||
if (!virStateActive()) {
|
||||
DEBUG0("No state active, shutting down");
|
||||
|
||||
if (virStateActive() ||
|
||||
server->clients) {
|
||||
DEBUG0("Timer expired but still active, not shutting down");
|
||||
virEventUpdateTimeoutImpl(timerid, -1);
|
||||
} else {
|
||||
DEBUG0("Timer expired and inactive, shutting down");
|
||||
server->shutdown = 1;
|
||||
}
|
||||
}
|
||||
@ -2066,9 +2070,18 @@ static void qemudFreeClient(struct qemud_client *client) {
|
||||
static int qemudRunLoop(struct qemud_server *server) {
|
||||
int timerid = -1;
|
||||
int ret = -1, i;
|
||||
int timerActive = 0;
|
||||
|
||||
virMutexLock(&server->lock);
|
||||
|
||||
if (timeout > 0 &&
|
||||
(timerid = virEventAddTimeoutImpl(-1,
|
||||
qemudInactiveTimer,
|
||||
server, NULL)) < 0) {
|
||||
VIR_ERROR0(_("Failed to register shutdown timeout"));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (min_workers > max_workers)
|
||||
max_workers = min_workers;
|
||||
|
||||
@ -2089,11 +2102,21 @@ static int qemudRunLoop(struct qemud_server *server) {
|
||||
* if any drivers have active state, if not
|
||||
* shutdown after timeout seconds
|
||||
*/
|
||||
if (timeout > 0 && !virStateActive() && !server->clients) {
|
||||
timerid = virEventAddTimeoutImpl(timeout*1000,
|
||||
qemudInactiveTimer,
|
||||
server, NULL);
|
||||
DEBUG("Scheduling shutdown timer %d", timerid);
|
||||
if (timeout > 0) {
|
||||
if (timerActive) {
|
||||
if (server->clients) {
|
||||
DEBUG("Deactivating shutdown timer %d", timerid);
|
||||
virEventUpdateTimeoutImpl(timerid, -1);
|
||||
timerActive = 0;
|
||||
}
|
||||
} else {
|
||||
if (!virStateActive() &&
|
||||
!server->clients) {
|
||||
DEBUG("Activating shutdown timer %d", timerid);
|
||||
virEventUpdateTimeoutImpl(timerid, timeout * 1000);
|
||||
timerActive = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
virMutexUnlock(&server->lock);
|
||||
@ -2147,15 +2170,6 @@ static int qemudRunLoop(struct qemud_server *server) {
|
||||
}
|
||||
}
|
||||
|
||||
/* Unregister any timeout that's active, since we
|
||||
* just had an event processed
|
||||
*/
|
||||
if (timerid != -1) {
|
||||
DEBUG("Removing shutdown timer %d", timerid);
|
||||
virEventRemoveTimeoutImpl(timerid);
|
||||
timerid = -1;
|
||||
}
|
||||
|
||||
if (server->shutdown) {
|
||||
ret = 0;
|
||||
break;
|
||||
|
Loading…
Reference in New Issue
Block a user