[MAJOR] fixed some expiration dates on tasks

The time subsystem really needs fixing. It was still possible
that some tasks with expiration date below the millisecond in
the future caused busy loop around poll() waiting for the
timeout to happen.
This commit is contained in:
Willy Tarreau 2007-05-09 00:54:10 +02:00
parent 23677908dd
commit 7317eb5a1d
2 changed files with 21 additions and 5 deletions

View File

@ -277,9 +277,11 @@ static int event_srv_chk_r(int fd)
*/ */
int process_chk(struct task *t) int process_chk(struct task *t)
{ {
__label__ new_chk, out;
struct server *s = t->context; struct server *s = t->context;
struct sockaddr_in sa; struct sockaddr_in sa;
int fd; int fd;
int next_time;
//fprintf(stderr, "process_chk: task=%p\n", t); //fprintf(stderr, "process_chk: task=%p\n", t);
@ -289,7 +291,8 @@ int process_chk(struct task *t)
//fprintf(stderr, "process_chk: 2\n"); //fprintf(stderr, "process_chk: 2\n");
if (!tv_ms_le2(&t->expire, &now)) { /* not good time yet */ if (!tv_ms_le2(&t->expire, &now)) { /* not good time yet */
task_queue(t); /* restore t to its place in the task list */ task_queue(t); /* restore t to its place in the task list */
return tv_ms_remain2(&now, &t->expire); next_time = tv_ms_remain2(&now, &t->expire);
goto out;
} }
/* we don't send any health-checks when the proxy is stopped or when /* we don't send any health-checks when the proxy is stopped or when
@ -299,7 +302,8 @@ int process_chk(struct task *t)
while (tv_ms_le2(&t->expire, &now)) while (tv_ms_le2(&t->expire, &now))
tv_ms_add(&t->expire, &t->expire, s->inter); tv_ms_add(&t->expire, &t->expire, s->inter);
task_queue(t); /* restore t to its place in the task list */ task_queue(t); /* restore t to its place in the task list */
return tv_ms_remain2(&now, &t->expire); next_time = tv_ms_remain2(&now, &t->expire);
goto out;
} }
/* we'll initiate a new check */ /* we'll initiate a new check */
@ -508,7 +512,12 @@ int process_chk(struct task *t)
//fprintf(stderr, "process_chk: 11\n"); //fprintf(stderr, "process_chk: 11\n");
s->result = 0; s->result = 0;
task_queue(t); /* restore t to its place in the task list */ task_queue(t); /* restore t to its place in the task list */
return tv_ms_remain2(&now, &t->expire); next_time = tv_ms_remain2(&now, &t->expire);
out:
/* Ensure that we don't report sub-millisecond timeouts */
if (next_time != TIME_ETERNITY)
next_time++;
return next_time;
} }

View File

@ -88,6 +88,7 @@ struct task *task_queue(struct task *task)
*/ */
int wake_expired_tasks() int wake_expired_tasks()
{ {
__label__ out;
int slen; int slen;
struct task *task; struct task *task;
void *data; void *data;
@ -100,8 +101,10 @@ int wake_expired_tasks()
if (likely(timer_wq.data != NULL)) { if (likely(timer_wq.data != NULL)) {
task = LIST_ELEM(timer_wq.data, struct task *, qlist); task = LIST_ELEM(timer_wq.data, struct task *, qlist);
if (likely(__tv_isge(&task->expire, &now) > 0)) if (likely(__tv_isge(&task->expire, &now) > 0)) {
return tv_ms_remain(&now, &task->expire); next_time = tv_ms_remain(&now, &task->expire);
goto out;
}
} }
/* OK we lose. Let's scan the tree then. */ /* OK we lose. Let's scan the tree then. */
@ -127,6 +130,10 @@ int wake_expired_tasks()
task->state = TASK_RUNNING; task->state = TASK_RUNNING;
} }
} }
out:
/* Ensure that we don't report sub-millisecond timeouts */
if (next_time != TIME_ETERNITY)
next_time++;
return next_time; return next_time;
} }