loop.c | loop.c | |||
---|---|---|---|---|
skipping to change at line 29 | skipping to change at line 29 | |||
* along with libqb. If not, see <http://www.gnu.org/licenses/>. | * along with libqb. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | */ | |||
#include "os_base.h" | #include "os_base.h" | |||
#include <qb/qbdefs.h> | #include <qb/qbdefs.h> | |||
#include <qb/qblist.h> | #include <qb/qblist.h> | |||
#include <qb/qbloop.h> | #include <qb/qbloop.h> | |||
#include "loop_int.h" | #include "loop_int.h" | |||
#include "util_int.h" | #include "util_int.h" | |||
static int32_t qb_loop_run_level(struct qb_loop_level *level) | static int32_t | |||
qb_loop_run_level(struct qb_loop_level *level) | ||||
{ | { | |||
struct qb_loop_item *job; | struct qb_loop_item *job; | |||
struct qb_list_head *iter; | struct qb_list_head *iter; | |||
int32_t processed = 0; | int32_t processed = 0; | |||
Ill_have_another: | Ill_have_another: | |||
iter = level->job_head.next; | iter = level->job_head.next; | |||
if (iter != &level->job_head) { | if (iter != &level->job_head) { | |||
job = qb_list_entry(iter, struct qb_loop_item, list); | job = qb_list_entry(iter, struct qb_loop_item, list); | |||
qb_list_del (&job->list); | qb_list_del(&job->list); | |||
qb_list_init (&job->list); | qb_list_init(&job->list); | |||
job->source->dispatch_and_take_back(job, level->priority); | job->source->dispatch_and_take_back(job, level->priority); | |||
level->todo--; | level->todo--; | |||
processed++; | processed++; | |||
if (level->l->stop_requested) { | if (level->l->stop_requested) { | |||
return processed; | return processed; | |||
} | } | |||
if (processed < level->to_process) { | if (processed < level->to_process) { | |||
goto Ill_have_another; | goto Ill_have_another; | |||
} | } | |||
} | } | |||
return processed; | return processed; | |||
} | } | |||
void qb_loop_level_item_add(struct qb_loop_level *level, | void | |||
struct qb_loop_item *job) | qb_loop_level_item_add(struct qb_loop_level *level, struct qb_loop_item *jo | |||
b) | ||||
{ | { | |||
qb_list_init(&job->list); | qb_list_init(&job->list); | |||
qb_list_add_tail(&job->list, &level->job_head); | qb_list_add_tail(&job->list, &level->job_head); | |||
level->todo++; | level->todo++; | |||
} | } | |||
void qb_loop_level_item_del(struct qb_loop_level *level, | void | |||
struct qb_loop_item *job) | qb_loop_level_item_del(struct qb_loop_level *level, struct qb_loop_item *jo | |||
b) | ||||
{ | { | |||
qb_list_del(&job->list); | qb_list_del(&job->list); | |||
qb_list_init(&job->list); | qb_list_init(&job->list); | |||
level->todo--; | level->todo--; | |||
} | } | |||
struct qb_loop * qb_loop_create(void) | struct qb_loop * | |||
qb_loop_create(void) | ||||
{ | { | |||
struct qb_loop *l = malloc(sizeof(struct qb_loop)); | struct qb_loop *l = malloc(sizeof(struct qb_loop)); | |||
int32_t p; | int32_t p; | |||
if (l == NULL) { | ||||
return NULL; | ||||
} | ||||
for (p = QB_LOOP_LOW; p <= QB_LOOP_HIGH; p++) { | for (p = QB_LOOP_LOW; p <= QB_LOOP_HIGH; p++) { | |||
l->level[p].priority = p; | l->level[p].priority = p; | |||
l->level[p].to_process = 4; | l->level[p].to_process = 4; | |||
l->level[p].todo = 0; | l->level[p].todo = 0; | |||
l->level[p].l = l; | l->level[p].l = l; | |||
qb_list_init(&l->level[p].job_head); | qb_list_init(&l->level[p].job_head); | |||
qb_list_init(&l->level[p].wait_head); | qb_list_init(&l->level[p].wait_head); | |||
} | } | |||
l->stop_requested = QB_FALSE; | l->stop_requested = QB_FALSE; | |||
// install sources | ||||
l->timer_source = qb_loop_timer_create(l); | l->timer_source = qb_loop_timer_create(l); | |||
l->job_source = qb_loop_jobs_create(l); | l->job_source = qb_loop_jobs_create(l); | |||
l->fd_source = qb_loop_poll_create(l); | l->fd_source = qb_loop_poll_create(l); | |||
l->signal_source = qb_loop_signals_create(l); | l->signal_source = qb_loop_signals_create(l); | |||
return l; | return l; | |||
} | } | |||
void qb_loop_destroy(struct qb_loop * l) | void | |||
qb_loop_destroy(struct qb_loop *l) | ||||
{ | { | |||
qb_loop_timer_destroy(l); | qb_loop_timer_destroy(l); | |||
qb_loop_jobs_destroy(l); | qb_loop_jobs_destroy(l); | |||
qb_loop_poll_destroy(l); | qb_loop_poll_destroy(l); | |||
qb_loop_signals_destroy(l); | qb_loop_signals_destroy(l); | |||
free(l); | free(l); | |||
} | } | |||
void qb_loop_stop(struct qb_loop *l) | void | |||
qb_loop_stop(struct qb_loop *l) | ||||
{ | { | |||
l->stop_requested = QB_TRUE; | l->stop_requested = QB_TRUE; | |||
} | } | |||
void qb_loop_run(struct qb_loop *l) | void | |||
qb_loop_run(struct qb_loop *l) | ||||
{ | { | |||
int32_t p; | int32_t p; | |||
int32_t p_stop = QB_LOOP_LOW; | int32_t p_stop = QB_LOOP_LOW; | |||
int32_t todo = 0; | int32_t todo = 0; | |||
int32_t ms_timeout; | int32_t ms_timeout; | |||
do { | do { | |||
if (p_stop == QB_LOOP_LOW) { | if (p_stop == QB_LOOP_LOW) { | |||
p_stop = QB_LOOP_HIGH; | p_stop = QB_LOOP_HIGH; | |||
} else { | } else { | |||
skipping to change at line 141 | skipping to change at line 148 | |||
ms_timeout = 0; | ms_timeout = 0; | |||
} else { | } else { | |||
todo = 0; | todo = 0; | |||
if (l->timer_source) { | if (l->timer_source) { | |||
ms_timeout = qb_loop_timer_msec_duration_to_ expire(l->timer_source); | ms_timeout = qb_loop_timer_msec_duration_to_ expire(l->timer_source); | |||
} else { | } else { | |||
ms_timeout = -1; | ms_timeout = -1; | |||
} | } | |||
} | } | |||
todo += l->fd_source->poll(l->fd_source, ms_timeout); | todo += l->fd_source->poll(l->fd_source, ms_timeout); | |||
// qb_poll_print(l); | ||||
for (p = QB_LOOP_HIGH; p >= p_stop; p--) { | for (p = QB_LOOP_HIGH; p >= p_stop; p--) { | |||
todo -= qb_loop_run_level(&l->level[p]); | todo -= qb_loop_run_level(&l->level[p]); | |||
if (l->stop_requested) { | if (l->stop_requested) { | |||
return; | return; | |||
} | } | |||
} | } | |||
} while (!l->stop_requested); | } while (!l->stop_requested); | |||
} | } | |||
End of changes. 12 change blocks. | ||||
14 lines changed or deleted | 22 lines changed or added | |||
This html diff was produced by rfcdiff 1.41. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ |