mirror of
https://github.com/libevent/libevent.git
synced 2025-01-31 09:12:55 +08:00
Make max_dispatch_interval able to apply only to low-priority events
Suggested by Alexander Drozdov
This commit is contained in:
parent
a9866aa8c1
commit
a37a0c0e35
@ -275,6 +275,7 @@ struct event_base {
|
|||||||
|
|
||||||
struct timeval max_dispatch_time;
|
struct timeval max_dispatch_time;
|
||||||
int max_dispatch_callbacks;
|
int max_dispatch_callbacks;
|
||||||
|
int limit_callbacks_after_prio;
|
||||||
|
|
||||||
/* Notify main thread to wake up break, etc. */
|
/* Notify main thread to wake up break, etc. */
|
||||||
/** True if the base already has a pending notify, and we don't need
|
/** True if the base already has a pending notify, and we don't need
|
||||||
@ -304,6 +305,7 @@ struct event_config {
|
|||||||
int n_cpus_hint;
|
int n_cpus_hint;
|
||||||
struct timeval max_dispatch_interval;
|
struct timeval max_dispatch_interval;
|
||||||
int max_dispatch_callbacks;
|
int max_dispatch_callbacks;
|
||||||
|
int limit_callbacks_after_prio;
|
||||||
enum event_method_feature require_features;
|
enum event_method_feature require_features;
|
||||||
enum event_base_config_flag flags;
|
enum event_base_config_flag flags;
|
||||||
};
|
};
|
||||||
|
22
event.c
22
event.c
@ -587,16 +587,23 @@ event_base_new_with_config(const struct event_config *cfg)
|
|||||||
should_check_environment =
|
should_check_environment =
|
||||||
!(cfg && (cfg->flags & EVENT_BASE_FLAG_IGNORE_ENV));
|
!(cfg && (cfg->flags & EVENT_BASE_FLAG_IGNORE_ENV));
|
||||||
|
|
||||||
if (cfg)
|
if (cfg) {
|
||||||
memcpy(&base->max_dispatch_time,
|
memcpy(&base->max_dispatch_time,
|
||||||
&cfg->max_dispatch_interval, sizeof(struct timeval));
|
&cfg->max_dispatch_interval, sizeof(struct timeval));
|
||||||
else
|
base->limit_callbacks_after_prio =
|
||||||
|
cfg->limit_callbacks_after_prio;
|
||||||
|
} else {
|
||||||
base->max_dispatch_time.tv_sec = -1;
|
base->max_dispatch_time.tv_sec = -1;
|
||||||
|
base->limit_callbacks_after_prio = 1;
|
||||||
|
}
|
||||||
if (cfg && cfg->max_dispatch_callbacks >= 0) {
|
if (cfg && cfg->max_dispatch_callbacks >= 0) {
|
||||||
base->max_dispatch_callbacks = cfg->max_dispatch_callbacks;
|
base->max_dispatch_callbacks = cfg->max_dispatch_callbacks;
|
||||||
} else {
|
} else {
|
||||||
base->max_dispatch_callbacks = INT_MAX;
|
base->max_dispatch_callbacks = INT_MAX;
|
||||||
}
|
}
|
||||||
|
if (base->max_dispatch_callbacks == INT_MAX &&
|
||||||
|
base->max_dispatch_time.tv_sec == -1)
|
||||||
|
base->limit_callbacks_after_prio = INT_MAX;
|
||||||
|
|
||||||
for (i = 0; eventops[i] && !base->evbase; i++) {
|
for (i = 0; eventops[i] && !base->evbase; i++) {
|
||||||
if (cfg != NULL) {
|
if (cfg != NULL) {
|
||||||
@ -924,6 +931,7 @@ event_config_new(void)
|
|||||||
TAILQ_INIT(&cfg->entries);
|
TAILQ_INIT(&cfg->entries);
|
||||||
cfg->max_dispatch_interval.tv_sec = -1;
|
cfg->max_dispatch_interval.tv_sec = -1;
|
||||||
cfg->max_dispatch_callbacks = INT_MAX;
|
cfg->max_dispatch_callbacks = INT_MAX;
|
||||||
|
cfg->limit_callbacks_after_prio = 1;
|
||||||
|
|
||||||
return (cfg);
|
return (cfg);
|
||||||
}
|
}
|
||||||
@ -995,7 +1003,7 @@ event_config_set_num_cpus_hint(struct event_config *cfg, int cpus)
|
|||||||
|
|
||||||
int
|
int
|
||||||
event_config_set_max_dispatch_interval(struct event_config *cfg,
|
event_config_set_max_dispatch_interval(struct event_config *cfg,
|
||||||
const struct timeval *max_interval, int max_callbacks)
|
const struct timeval *max_interval, int max_callbacks, int min_priority)
|
||||||
{
|
{
|
||||||
if (max_interval)
|
if (max_interval)
|
||||||
memcpy(&cfg->max_dispatch_interval, max_interval,
|
memcpy(&cfg->max_dispatch_interval, max_interval,
|
||||||
@ -1003,7 +1011,10 @@ event_config_set_max_dispatch_interval(struct event_config *cfg,
|
|||||||
else
|
else
|
||||||
cfg->max_dispatch_interval.tv_sec = -1;
|
cfg->max_dispatch_interval.tv_sec = -1;
|
||||||
cfg->max_dispatch_callbacks =
|
cfg->max_dispatch_callbacks =
|
||||||
max_callbacks >= 0 ? max_callbacks : INT_MAX ;
|
max_callbacks >= 0 ? max_callbacks : INT_MAX;
|
||||||
|
if (min_priority <= 0)
|
||||||
|
min_priority = 1;
|
||||||
|
cfg->limit_callbacks_after_prio = min_priority;
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1428,6 +1439,7 @@ event_process_active(struct event_base *base)
|
|||||||
const struct timeval *endtime;
|
const struct timeval *endtime;
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
const int maxcb = base->max_dispatch_callbacks;
|
const int maxcb = base->max_dispatch_callbacks;
|
||||||
|
const int limit_after_prio = base->limit_callbacks_after_prio;
|
||||||
if (base->max_dispatch_time.tv_sec >= 0) {
|
if (base->max_dispatch_time.tv_sec >= 0) {
|
||||||
evutil_gettimeofday(&tv, NULL);
|
evutil_gettimeofday(&tv, NULL);
|
||||||
evutil_timeradd(&base->max_dispatch_time, &tv, &tv);
|
evutil_timeradd(&base->max_dispatch_time, &tv, &tv);
|
||||||
@ -1439,7 +1451,7 @@ event_process_active(struct event_base *base)
|
|||||||
for (i = 0; i < base->nactivequeues; ++i) {
|
for (i = 0; i < base->nactivequeues; ++i) {
|
||||||
if (TAILQ_FIRST(&base->activequeues[i]) != NULL) {
|
if (TAILQ_FIRST(&base->activequeues[i]) != NULL) {
|
||||||
activeq = &base->activequeues[i];
|
activeq = &base->activequeues[i];
|
||||||
if (i == 0)
|
if (i < limit_after_prio)
|
||||||
c = event_process_active_single_queue(base, activeq,
|
c = event_process_active_single_queue(base, activeq,
|
||||||
INT_MAX, NULL);
|
INT_MAX, NULL);
|
||||||
else
|
else
|
||||||
|
@ -550,9 +550,23 @@ int event_config_set_num_cpus_hint(struct event_config *cfg, int cpus);
|
|||||||
* avoid priority inversions where multiple low-priority events keep us from
|
* avoid priority inversions where multiple low-priority events keep us from
|
||||||
* polling for high-priority events, but at the expense of slightly decreasing
|
* polling for high-priority events, but at the expense of slightly decreasing
|
||||||
* the throughput. Use it with caution!
|
* the throughput. Use it with caution!
|
||||||
|
*
|
||||||
|
* @param cfg The event_base configuration object.
|
||||||
|
* @param max_interval An interval after which Libevent should stop running
|
||||||
|
* callbacks and check for more events, or NULL if there should be
|
||||||
|
* no such interval.
|
||||||
|
* @param max_callbacks A number of callbacks after which Libevent should
|
||||||
|
* stop running callbacks and check for more events, or -1 if there
|
||||||
|
* should be no such limit.
|
||||||
|
* @param min_priority A priority below which max_interval and max_callbacks
|
||||||
|
* should not be enforced. If this is set to 0, they are enforced
|
||||||
|
* for events of every priority; if it's set to 1, they're enforced
|
||||||
|
* for events of priority 1 and above, and so on.
|
||||||
|
* @return 0 on success, -1 on failure.
|
||||||
**/
|
**/
|
||||||
int event_config_set_max_dispatch_interval(struct event_config *cfg,
|
int event_config_set_max_dispatch_interval(struct event_config *cfg,
|
||||||
const struct timeval *max_interval, int max_callbacks);
|
const struct timeval *max_interval, int max_callbacks,
|
||||||
|
int min_priority);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Initialize the event API.
|
Initialize the event API.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user