libratbox: event: continually adjust ish event times
When events are scheduled to run at a random +/- 1/3rd of the specified frequency it can vary considerably for the longer timers (particularly try_connections), so adjust the frequency to a different random interval of the original frequency every time the event runs.
This commit is contained in:
parent
eb1b303d56
commit
8ace0906ad
1 changed files with 46 additions and 45 deletions
|
@ -76,6 +76,27 @@ rb_event_find(EVH * func, void *arg)
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static
|
||||||
|
struct ev_entry *
|
||||||
|
rb_event_add_common(const char *name, EVH * func, void *arg, time_t when, time_t frequency)
|
||||||
|
{
|
||||||
|
struct ev_entry *ev;
|
||||||
|
ev = rb_malloc(sizeof(struct ev_entry));
|
||||||
|
ev->func = func;
|
||||||
|
ev->name = rb_strndup(name, EV_NAME_LEN);
|
||||||
|
ev->arg = arg;
|
||||||
|
ev->when = rb_current_time() + when;
|
||||||
|
ev->next = when;
|
||||||
|
ev->frequency = frequency;
|
||||||
|
|
||||||
|
if((ev->when < event_time_min) || (event_time_min == -1))
|
||||||
|
event_time_min = ev->when;
|
||||||
|
|
||||||
|
rb_dlinkAdd(ev, &ev->node, &event_list);
|
||||||
|
rb_io_sched_event(ev, when);
|
||||||
|
return ev;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* struct ev_entry *
|
* struct ev_entry *
|
||||||
* rb_event_add(const char *name, EVH *func, void *arg, time_t when)
|
* rb_event_add(const char *name, EVH *func, void *arg, time_t when)
|
||||||
|
@ -93,22 +114,8 @@ rb_event_add(const char *name, EVH * func, void *arg, time_t when)
|
||||||
"%d seconds", name, (int) when);
|
"%d seconds", name, (int) when);
|
||||||
when = 1;
|
when = 1;
|
||||||
}
|
}
|
||||||
struct ev_entry *ev;
|
|
||||||
ev = rb_malloc(sizeof(struct ev_entry));
|
|
||||||
ev->func = func;
|
|
||||||
ev->name = rb_strndup(name, EV_NAME_LEN);
|
|
||||||
ev->arg = arg;
|
|
||||||
ev->when = rb_current_time() + when;
|
|
||||||
ev->next = when;
|
|
||||||
ev->frequency = when;
|
|
||||||
|
|
||||||
if((ev->when < event_time_min) || (event_time_min == -1))
|
return rb_event_add_common(name, func, arg, when, when);
|
||||||
{
|
|
||||||
event_time_min = ev->when;
|
|
||||||
}
|
|
||||||
rb_dlinkAdd(ev, &ev->node, &event_list);
|
|
||||||
rb_io_sched_event(ev, when);
|
|
||||||
return ev;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
struct ev_entry *
|
struct ev_entry *
|
||||||
|
@ -119,21 +126,8 @@ rb_event_addonce(const char *name, EVH * func, void *arg, time_t when)
|
||||||
"%d seconds", name, (int) when);
|
"%d seconds", name, (int) when);
|
||||||
when = 1;
|
when = 1;
|
||||||
}
|
}
|
||||||
struct ev_entry *ev;
|
|
||||||
ev = rb_malloc(sizeof(struct ev_entry));
|
|
||||||
ev->func = func;
|
|
||||||
ev->name = rb_strndup(name, EV_NAME_LEN);
|
|
||||||
ev->arg = arg;
|
|
||||||
ev->when = rb_current_time() + when;
|
|
||||||
ev->next = when;
|
|
||||||
ev->frequency = 0;
|
|
||||||
|
|
||||||
if((ev->when < event_time_min) || (event_time_min == -1))
|
return rb_event_add_common(name, func, arg, when, 0);
|
||||||
event_time_min = ev->when;
|
|
||||||
|
|
||||||
rb_dlinkAdd(ev, &ev->node, &event_list);
|
|
||||||
rb_io_sched_event(ev, when);
|
|
||||||
return ev;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -168,6 +162,17 @@ rb_event_find_delete(EVH * func, void *arg)
|
||||||
rb_event_delete(rb_event_find(func, arg));
|
rb_event_delete(rb_event_find(func, arg));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static time_t
|
||||||
|
rb_event_frequency(time_t frequency)
|
||||||
|
{
|
||||||
|
if(frequency < 0)
|
||||||
|
{
|
||||||
|
const time_t two_third = (2 * abs(frequency)) / 3;
|
||||||
|
frequency = two_third + ((rand() % 1000) * two_third) / 1000;
|
||||||
|
}
|
||||||
|
return frequency;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* struct ev_entry *
|
* struct ev_entry *
|
||||||
* rb_event_addish(const char *name, EVH *func, void *arg, time_t delta_isa)
|
* rb_event_addish(const char *name, EVH *func, void *arg, time_t delta_isa)
|
||||||
|
@ -181,16 +186,11 @@ rb_event_find_delete(EVH * func, void *arg)
|
||||||
struct ev_entry *
|
struct ev_entry *
|
||||||
rb_event_addish(const char *name, EVH * func, void *arg, time_t delta_ish)
|
rb_event_addish(const char *name, EVH * func, void *arg, time_t delta_ish)
|
||||||
{
|
{
|
||||||
|
delta_ish = abs(delta_ish);
|
||||||
if(delta_ish >= 3.0)
|
if(delta_ish >= 3.0)
|
||||||
{
|
delta_ish = -delta_ish;
|
||||||
const time_t two_third = (2 * delta_ish) / 3;
|
return rb_event_add_common(name, func, arg,
|
||||||
delta_ish = two_third + ((rand() % 1000) * two_third) / 1000;
|
rb_event_frequency(delta_ish), delta_ish);
|
||||||
/*
|
|
||||||
* XXX I hate the above magic, I don't even know if its right.
|
|
||||||
* Grr. -- adrian
|
|
||||||
*/
|
|
||||||
}
|
|
||||||
return rb_event_add(name, func, arg, delta_ish);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -204,7 +204,7 @@ rb_run_event(struct ev_entry *ev)
|
||||||
rb_event_delete(ev);
|
rb_event_delete(ev);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
ev->when = rb_current_time() + ev->frequency;
|
ev->when = rb_current_time() + rb_event_frequency(ev->frequency);
|
||||||
if((ev->when < event_time_min) || (event_time_min == -1))
|
if((ev->when < event_time_min) || (event_time_min == -1))
|
||||||
event_time_min = ev->when;
|
event_time_min = ev->when;
|
||||||
}
|
}
|
||||||
|
@ -237,7 +237,7 @@ rb_event_run(void)
|
||||||
/* event is scheduled more than once */
|
/* event is scheduled more than once */
|
||||||
if(ev->frequency)
|
if(ev->frequency)
|
||||||
{
|
{
|
||||||
ev->when = rb_current_time() + ev->frequency;
|
ev->when = rb_current_time() + rb_event_frequency(ev->frequency);
|
||||||
if((ev->when < event_time_min) || (event_time_min == -1))
|
if((ev->when < event_time_min) || (event_time_min == -1))
|
||||||
event_time_min = ev->when;
|
event_time_min = ev->when;
|
||||||
}
|
}
|
||||||
|
@ -302,8 +302,8 @@ rb_dump_events(void (*func) (char *, void *), void *ptr)
|
||||||
RB_DLINK_FOREACH(dptr, event_list.head)
|
RB_DLINK_FOREACH(dptr, event_list.head)
|
||||||
{
|
{
|
||||||
ev = dptr->data;
|
ev = dptr->data;
|
||||||
snprintf(buf, len, "%-28s %-4ld seconds", ev->name,
|
snprintf(buf, len, "%-28s %-4ld seconds (frequency=%d)", ev->name,
|
||||||
ev->when - (long)rb_current_time());
|
ev->when - (long)rb_current_time(), (int)ev->frequency);
|
||||||
func(buf, ptr);
|
func(buf, ptr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -337,11 +337,12 @@ rb_event_update(struct ev_entry *ev, time_t freq)
|
||||||
|
|
||||||
ev->frequency = freq;
|
ev->frequency = freq;
|
||||||
|
|
||||||
/* update when its scheduled to run if its higher
|
/* update when it's scheduled to run if it's higher
|
||||||
* than the new frequency
|
* than the new frequency
|
||||||
*/
|
*/
|
||||||
if((rb_current_time() + freq) < ev->when)
|
time_t next = rb_event_frequency(freq);
|
||||||
ev->when = rb_current_time() + freq;
|
if((rb_current_time() + next) < ev->when)
|
||||||
|
ev->when = rb_current_time() + next;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue