From 0955e3d45b6e992308e2d51fcbf28a9f9376f788 Mon Sep 17 00:00:00 2001 From: Marc-André Lureau Date: Sun, 5 Apr 2009 02:13:43 +0300 Subject: Base mainloop on pa_rtclock_now() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Move the mainloop to monotonic based time events. Introduces 4 helper functions: pa_{context,core}_rttime_{new,restart}(), that fill correctly a timeval with the rtclock flag set if the mainloop supports it. Both mainloop-test and mainloop-test-glib works with rt and timeval based time events. PulseAudio and clients should be fully functional. This patch has received several iterations, and this one as been largely untested. Signed-off-by: Marc-André Lureau --- src/modules/module-card-restore.c | 12 ++++-------- src/modules/module-combine.c | 15 ++++----------- src/modules/module-default-device-restore.c | 13 +++++-------- src/modules/module-device-restore.c | 12 ++++-------- src/modules/module-esound-sink.c | 2 +- src/modules/module-stream-restore.c | 11 ++++------- src/modules/module-suspend-on-idle.c | 19 +++++++++---------- src/modules/module-tunnel.c | 18 ++++++------------ src/modules/module-waveout.c | 4 ++-- src/modules/raop/raop_client.c | 2 +- src/modules/rtp/module-rtp-recv.c | 15 +++++---------- src/modules/rtp/module-rtp-send.c | 14 ++++---------- src/modules/rtp/rtsp_client.c | 2 +- 13 files changed, 50 insertions(+), 89 deletions(-) (limited to 'src/modules') diff --git a/src/modules/module-card-restore.c b/src/modules/module-card-restore.c index 85583b2c..6b057b4c 100644 --- a/src/modules/module-card-restore.c +++ b/src/modules/module-card-restore.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include @@ -53,7 +54,7 @@ PA_MODULE_DESCRIPTION("Automatically restore profile of cards"); PA_MODULE_VERSION(PACKAGE_VERSION); PA_MODULE_LOAD_ONCE(TRUE); -#define SAVE_INTERVAL 10 +#define SAVE_INTERVAL (10 * PA_USEC_PER_SEC) static const char* const valid_modargs[] = { NULL @@ -75,12 +76,11 @@ struct entry { char profile[PA_NAME_MAX]; } PA_GCC_PACKED ; -static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *tv, void *userdata) { +static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; pa_assert(a); pa_assert(e); - pa_assert(tv); pa_assert(u); pa_assert(e == u->save_time_event); @@ -132,14 +132,10 @@ fail: } static void trigger_save(struct userdata *u) { - struct timeval tv; - if (u->save_time_event) return; - pa_gettimeofday(&tv); - tv.tv_sec += SAVE_INTERVAL; - u->save_time_event = u->core->mainloop->time_new(u->core->mainloop, &tv, save_time_callback, u); + u->save_time_event = pa_core_rttime_new(u->core, pa_rtclock_now() + SAVE_INTERVAL, save_time_callback, u); } static void subscribe_callback(pa_core *c, pa_subscription_event_type_t t, uint32_t idx, void *userdata) { diff --git a/src/modules/module-combine.c b/src/modules/module-combine.c index 6ca7cd99..757dbda4 100644 --- a/src/modules/module-combine.c +++ b/src/modules/module-combine.c @@ -225,9 +225,8 @@ static void adjust_rates(struct userdata *u) { pa_asyncmsgq_send(u->sink->asyncmsgq, PA_MSGOBJECT(u->sink), SINK_MESSAGE_UPDATE_LATENCY, NULL, (int64_t) avg_total_latency, NULL); } -static void time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *tv, void *userdata) { +static void time_callback(pa_mainloop_api *a, pa_time_event *e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; - struct timeval n; pa_assert(u); pa_assert(a); @@ -235,9 +234,7 @@ static void time_callback(pa_mainloop_api*a, pa_time_event* e, const struct time adjust_rates(u); - pa_gettimeofday(&n); - n.tv_sec += (time_t) u->adjust_time; - u->sink->core->mainloop->time_restart(e, &n); + pa_core_rttime_restart(u->core, e, pa_rtclock_now() + u->adjust_time * PA_USEC_PER_SEC); } static void process_render_null(struct userdata *u, pa_usec_t now) { @@ -1171,12 +1168,8 @@ int pa__init(pa_module*m) { if (o->sink_input) pa_sink_input_put(o->sink_input); - if (u->adjust_time > 0) { - struct timeval tv; - pa_gettimeofday(&tv); - tv.tv_sec += (time_t) u->adjust_time; - u->time_event = m->core->mainloop->time_new(m->core->mainloop, &tv, time_callback, u); - } + if (u->adjust_time > 0) + u->time_event = pa_core_rttime_new(m->core, pa_rtclock_now() + u->adjust_time * PA_USEC_PER_SEC, time_callback, u); pa_modargs_free(ma); diff --git a/src/modules/module-default-device-restore.c b/src/modules/module-default-device-restore.c index 0092d1c7..27ae60e5 100644 --- a/src/modules/module-default-device-restore.c +++ b/src/modules/module-default-device-restore.c @@ -26,6 +26,7 @@ #include #include +#include #include #include @@ -42,7 +43,7 @@ PA_MODULE_DESCRIPTION("Automatically restore the default sink and source"); PA_MODULE_VERSION(PACKAGE_VERSION); PA_MODULE_LOAD_ONCE(TRUE); -#define DEFAULT_SAVE_INTERVAL 5 +#define SAVE_INTERVAL (5 * PA_USEC_PER_SEC) struct userdata { pa_core *core; @@ -127,7 +128,7 @@ static void save(struct userdata *u) { u->modified = FALSE; } -static void time_cb(pa_mainloop_api *a, pa_time_event *e, const struct timeval *tv, void *userdata) { +static void time_cb(pa_mainloop_api *a, pa_time_event *e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; pa_assert(u); @@ -146,12 +147,8 @@ static void subscribe_cb(pa_core *c, pa_subscription_event_type_t t, uint32_t id u->modified = TRUE; - if (!u->time_event) { - struct timeval tv; - pa_gettimeofday(&tv); - pa_timeval_add(&tv, DEFAULT_SAVE_INTERVAL*PA_USEC_PER_SEC); - u->time_event = u->core->mainloop->time_new(u->core->mainloop, &tv, time_cb, u); - } + if (!u->time_event) + u->time_event = pa_core_rttime_new(u->core, pa_rtclock_now() + SAVE_INTERVAL, time_cb, u); } int pa__init(pa_module *m) { diff --git a/src/modules/module-device-restore.c b/src/modules/module-device-restore.c index a2745b88..8c15d454 100644 --- a/src/modules/module-device-restore.c +++ b/src/modules/module-device-restore.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include @@ -58,7 +59,7 @@ PA_MODULE_USAGE( "restore_volume= " "restore_muted="); -#define SAVE_INTERVAL 10 +#define SAVE_INTERVAL (10 * PA_USEC_PER_SEC) static const char* const valid_modargs[] = { "restore_volume", @@ -95,12 +96,11 @@ struct entry { char port[PA_NAME_MAX]; } PA_GCC_PACKED; -static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *tv, void *userdata) { +static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; pa_assert(a); pa_assert(e); - pa_assert(tv); pa_assert(u); pa_assert(e == u->save_time_event); @@ -162,14 +162,10 @@ fail: } static void trigger_save(struct userdata *u) { - struct timeval tv; - if (u->save_time_event) return; - pa_gettimeofday(&tv); - tv.tv_sec += SAVE_INTERVAL; - u->save_time_event = u->core->mainloop->time_new(u->core->mainloop, &tv, save_time_callback, u); + u->save_time_event = pa_core_rttime_new(u->core, pa_rtclock_now() + SAVE_INTERVAL, save_time_callback, u); } static pa_bool_t entries_equal(const struct entry *a, const struct entry *b) { diff --git a/src/modules/module-esound-sink.c b/src/modules/module-esound-sink.c index 2df8a0e8..b26b465d 100644 --- a/src/modules/module-esound-sink.c +++ b/src/modules/module-esound-sink.c @@ -609,7 +609,7 @@ int pa__init(pa_module*m) { pa_sink_set_asyncmsgq(u->sink, u->thread_mq.inq); pa_sink_set_rtpoll(u->sink, u->rtpoll); - if (!(u->client = pa_socket_client_new_string(u->core->mainloop, espeaker, ESD_DEFAULT_PORT))) { + if (!(u->client = pa_socket_client_new_string(u->core->mainloop, TRUE, espeaker, ESD_DEFAULT_PORT))) { pa_log("Failed to connect to server."); goto fail; } diff --git a/src/modules/module-stream-restore.c b/src/modules/module-stream-restore.c index f2aea27b..99c69f66 100644 --- a/src/modules/module-stream-restore.c +++ b/src/modules/module-stream-restore.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include @@ -61,7 +62,7 @@ PA_MODULE_USAGE( "restore_volume= " "restore_muted="); -#define SAVE_INTERVAL 10 +#define SAVE_INTERVAL (10 * PA_USEC_PER_SEC) #define IDENTIFICATION_PROPERTY "module-stream-restore.id" static const char* const valid_modargs[] = { @@ -111,12 +112,11 @@ enum { SUBCOMMAND_EVENT }; -static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *tv, void *userdata) { +static void save_time_callback(pa_mainloop_api*a, pa_time_event* e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; pa_assert(a); pa_assert(e); - pa_assert(tv); pa_assert(u); pa_assert(e == u->save_time_event); @@ -210,7 +210,6 @@ fail: } static void trigger_save(struct userdata *u) { - struct timeval tv; pa_native_connection *c; uint32_t idx; @@ -230,9 +229,7 @@ static void trigger_save(struct userdata *u) { if (u->save_time_event) return; - pa_gettimeofday(&tv); - tv.tv_sec += SAVE_INTERVAL; - u->save_time_event = u->core->mainloop->time_new(u->core->mainloop, &tv, save_time_callback, u); + u->save_time_event = pa_core_rttime_new(u->core, pa_rtclock_now() + SAVE_INTERVAL, save_time_callback, u); } static pa_bool_t entries_equal(const struct entry *a, const struct entry *b) { diff --git a/src/modules/module-suspend-on-idle.c b/src/modules/module-suspend-on-idle.c index c5b78911..70a7b049 100644 --- a/src/modules/module-suspend-on-idle.c +++ b/src/modules/module-suspend-on-idle.c @@ -25,6 +25,7 @@ #include #include +#include #include #include @@ -75,11 +76,11 @@ struct device_info { struct userdata *userdata; pa_sink *sink; pa_source *source; - struct timeval last_use; + pa_usec_t last_use; pa_time_event *time_event; }; -static void timeout_cb(pa_mainloop_api*a, pa_time_event* e, const struct timeval *tv, void *userdata) { +static void timeout_cb(pa_mainloop_api*a, pa_time_event* e, const struct timeval *t, void *userdata) { struct device_info *d = userdata; pa_assert(d); @@ -98,22 +99,20 @@ static void timeout_cb(pa_mainloop_api*a, pa_time_event* e, const struct timeval } static void restart(struct device_info *d) { - struct timeval tv; + pa_usec_t now; const char *s; uint32_t timeout; + pa_assert(d); pa_assert(d->sink || d->source); - pa_gettimeofday(&tv); - d->last_use = tv; + d->last_use = now = pa_rtclock_now(); s = pa_proplist_gets(d->sink ? d->sink->proplist : d->source->proplist, "module-suspend-on-idle.timeout"); if (!s || pa_atou(s, &timeout) < 0) - timeout = d->userdata->timeout; - - pa_timeval_add(&tv, timeout * PA_USEC_PER_SEC); + timeout = d->userdata->timeout; - d->userdata->core->mainloop->time_restart(d->time_event, &tv); + pa_core_rttime_restart(d->userdata->core, d->time_event, now + timeout * PA_USEC_PER_SEC); if (d->sink) pa_log_debug("Sink %s becomes idle, timeout in %u seconds.", d->sink->name, timeout); @@ -338,7 +337,7 @@ static pa_hook_result_t device_new_hook_cb(pa_core *c, pa_object *o, struct user d->userdata = u; d->source = source ? pa_source_ref(source) : NULL; d->sink = sink ? pa_sink_ref(sink) : NULL; - d->time_event = c->mainloop->time_new(c->mainloop, NULL, timeout_cb, d); + d->time_event = pa_core_rttime_new(c, PA_USEC_INVALID, timeout_cb, d); pa_hashmap_put(u->device_infos, o, d); if ((d->sink && pa_sink_check_suspend(d->sink) <= 0) || diff --git a/src/modules/module-tunnel.c b/src/modules/module-tunnel.c index ec4808f0..ce37bf47 100644 --- a/src/modules/module-tunnel.c +++ b/src/modules/module-tunnel.c @@ -113,7 +113,7 @@ static const char* const valid_modargs[] = { #define DEFAULT_TIMEOUT 5 -#define LATENCY_INTERVAL 10 +#define LATENCY_INTERVAL (10*PA_USEC_PER_SEC) #define MIN_NETWORK_LATENCY_USEC (8*PA_USEC_PER_MSEC) @@ -879,9 +879,8 @@ static void request_latency(struct userdata *u) { } /* Called from main context */ -static void timeout_callback(pa_mainloop_api *m, pa_time_event*e, const struct timeval *tv, void *userdata) { +static void timeout_callback(pa_mainloop_api *m, pa_time_event *e, const struct timeval *t, void *userdata) { struct userdata *u = userdata; - struct timeval ntv; pa_assert(m); pa_assert(e); @@ -889,9 +888,7 @@ static void timeout_callback(pa_mainloop_api *m, pa_time_event*e, const struct request_latency(u); - pa_gettimeofday(&ntv); - ntv.tv_sec += LATENCY_INTERVAL; - m->time_restart(e, &ntv); + pa_core_rttime_restart(u->core, e, pa_rtclock_now() + LATENCY_INTERVAL); } /* Called from main context */ @@ -1358,7 +1355,6 @@ static void start_subscribe(struct userdata *u) { /* Called from main context */ static void create_stream_callback(pa_pdispatch *pd, uint32_t command, uint32_t tag, pa_tagstruct *t, void *userdata) { struct userdata *u = userdata; - struct timeval ntv; #ifdef TUNNEL_SINK uint32_t bytes; #endif @@ -1440,9 +1436,7 @@ static void create_stream_callback(pa_pdispatch *pd, uint32_t command, uint32_t request_info(u); pa_assert(!u->time_event); - pa_gettimeofday(&ntv); - ntv.tv_sec += LATENCY_INTERVAL; - u->time_event = u->core->mainloop->time_new(u->core->mainloop, &ntv, timeout_callback, u); + u->time_event = pa_core_rttime_new(u->core, pa_rtclock_now() + LATENCY_INTERVAL, timeout_callback, u); request_latency(u); @@ -1707,7 +1701,7 @@ static void on_connection(pa_socket_client *sc, pa_iochannel *io, void *userdata } u->pstream = pa_pstream_new(u->core->mainloop, io, u->core->mempool); - u->pdispatch = pa_pdispatch_new(u->core->mainloop, command_table, PA_COMMAND_MAX); + u->pdispatch = pa_pdispatch_new(u->core->mainloop, TRUE, command_table, PA_COMMAND_MAX); pa_pstream_set_die_callback(u->pstream, pstream_die_callback, u); pa_pstream_set_recieve_packet_callback(u->pstream, pstream_packet_callback, u); @@ -1854,7 +1848,7 @@ int pa__init(pa_module*m) { goto fail; } - if (!(u->client = pa_socket_client_new_string(m->core->mainloop, u->server_name, PA_NATIVE_DEFAULT_PORT))) { + if (!(u->client = pa_socket_client_new_string(m->core->mainloop, TRUE, u->server_name, PA_NATIVE_DEFAULT_PORT))) { pa_log("Failed to connect to server '%s'", u->server_name); goto fail; } diff --git a/src/modules/module-waveout.c b/src/modules/module-waveout.c index 2d35828d..d1b9f2ff 100644 --- a/src/modules/module-waveout.c +++ b/src/modules/module-waveout.c @@ -256,7 +256,7 @@ static void poll_cb(pa_mainloop_api*a, pa_time_event *e, const struct timeval *t pa_gettimeofday(&ntv); pa_timeval_add(&ntv, u->poll_timeout); - a->time_restart(e, &ntv); + a->rtclock_time_restart(e, &ntv); } static void defer_cb(pa_mainloop_api*a, pa_defer_event *e, void *userdata) { @@ -549,7 +549,7 @@ int pa__init(pa_core *c, pa_module*m) { pa_gettimeofday(&tv); pa_timeval_add(&tv, u->poll_timeout); - u->event = c->mainloop->time_new(c->mainloop, &tv, poll_cb, u); + u->event = c->mainloop->rtclock_time_new(c->mainloop, &tv, poll_cb, u); assert(u->event); u->defer = c->mainloop->defer_new(c->mainloop, defer_cb, u); diff --git a/src/modules/raop/raop_client.c b/src/modules/raop/raop_client.c index b3f243c3..c4b02371 100644 --- a/src/modules/raop/raop_client.c +++ b/src/modules/raop/raop_client.c @@ -331,7 +331,7 @@ static void rtsp_cb(pa_rtsp_client *rtsp, pa_rtsp_state state, pa_headerlist* he uint32_t port = pa_rtsp_serverport(c->rtsp); pa_log_debug("RAOP: RECORDED"); - if (!(c->sc = pa_socket_client_new_string(c->core->mainloop, c->host, port))) { + if (!(c->sc = pa_socket_client_new_string(c->core->mainloop, TRUE, c->host, port))) { pa_log("failed to connect to server '%s:%d'", c->host, port); return; } diff --git a/src/modules/rtp/module-rtp-recv.c b/src/modules/rtp/module-rtp-recv.c index 84cf07de..5caf8272 100644 --- a/src/modules/rtp/module-rtp-recv.c +++ b/src/modules/rtp/module-rtp-recv.c @@ -113,6 +113,7 @@ struct session { struct userdata { pa_module *module; + pa_core *core; pa_sap_context sap_context; pa_io_event* sap_event; @@ -622,15 +623,13 @@ static void sap_event_cb(pa_mainloop_api *m, pa_io_event *e, int fd, pa_io_event } } -static void check_death_event_cb(pa_mainloop_api *m, pa_time_event *t, const struct timeval *ptv, void *userdata) { +static void check_death_event_cb(pa_mainloop_api *m, pa_time_event *t, const struct timeval *tv, void *userdata) { struct session *s, *n; struct userdata *u = userdata; struct timeval now; - struct timeval tv; pa_assert(m); pa_assert(t); - pa_assert(ptv); pa_assert(u); pa_rtclock_get(&now); @@ -648,9 +647,7 @@ static void check_death_event_cb(pa_mainloop_api *m, pa_time_event *t, const str } /* Restart timer */ - pa_gettimeofday(&tv); - pa_timeval_add(&tv, DEATH_TIMEOUT*PA_USEC_PER_SEC); - m->time_restart(t, &tv); + pa_core_rttime_restart(u->module->core, t, pa_rtclock_now() + DEATH_TIMEOUT * PA_USEC_PER_SEC); } int pa__init(pa_module*m) { @@ -664,7 +661,6 @@ int pa__init(pa_module*m) { socklen_t salen; const char *sap_address; int fd = -1; - struct timeval tv; pa_assert(m); @@ -697,6 +693,7 @@ int pa__init(pa_module*m) { m->userdata = u = pa_xnew(struct userdata, 1); u->module = m; + u->core = m->core; u->sink_name = pa_xstrdup(pa_modargs_get_value(ma, "sink", NULL)); u->sap_event = m->core->mainloop->io_new(m->core->mainloop, fd, PA_IO_EVENT_INPUT, sap_event_cb, u); @@ -706,9 +703,7 @@ int pa__init(pa_module*m) { u->n_sessions = 0; u->by_origin = pa_hashmap_new(pa_idxset_string_hash_func, pa_idxset_string_compare_func); - pa_gettimeofday(&tv); - pa_timeval_add(&tv, DEATH_TIMEOUT * PA_USEC_PER_SEC); - u->check_death_event = m->core->mainloop->time_new(m->core->mainloop, &tv, check_death_event_cb, u); + u->check_death_event = pa_core_rttime_new(m->core, pa_rtclock_now() + DEATH_TIMEOUT * PA_USEC_PER_SEC, check_death_event_cb, u); pa_modargs_free(ma); diff --git a/src/modules/rtp/module-rtp-send.c b/src/modules/rtp/module-rtp-send.c index 39ee4d75..f147364d 100644 --- a/src/modules/rtp/module-rtp-send.c +++ b/src/modules/rtp/module-rtp-send.c @@ -31,6 +31,7 @@ #include #include +#include #include #include #include @@ -77,7 +78,7 @@ PA_MODULE_USAGE( #define DEFAULT_DESTINATION "224.0.0.56" #define MEMBLOCKQ_MAXLENGTH (1024*170) #define DEFAULT_MTU 1280 -#define SAP_INTERVAL 5 +#define SAP_INTERVAL (5*PA_USEC_PER_SEC) static const char* const valid_modargs[] = { "source", @@ -151,18 +152,14 @@ static void source_output_kill(pa_source_output* o) { static void sap_event_cb(pa_mainloop_api *m, pa_time_event *t, const struct timeval *tv, void *userdata) { struct userdata *u = userdata; - struct timeval next; pa_assert(m); pa_assert(t); - pa_assert(tv); pa_assert(u); pa_sap_send(&u->sap_context, 0); - pa_gettimeofday(&next); - pa_timeval_add(&next, SAP_INTERVAL * PA_USEC_PER_SEC); - m->time_restart(t, &next); + pa_core_rttime_restart(u->module->core, t, pa_rtclock_now() + SAP_INTERVAL); } int pa__init(pa_module*m) { @@ -186,7 +183,6 @@ int pa__init(pa_module*m) { char *p; int r, j; socklen_t k; - struct timeval tv; char hn[128], *n; pa_bool_t loop = FALSE; pa_source_output_new_data data; @@ -395,9 +391,7 @@ int pa__init(pa_module*m) { pa_sap_send(&u->sap_context, 0); - pa_gettimeofday(&tv); - pa_timeval_add(&tv, SAP_INTERVAL * PA_USEC_PER_SEC); - u->sap_event = m->core->mainloop->time_new(m->core->mainloop, &tv, sap_event_cb, u); + u->sap_event = pa_core_rttime_new(m->core, pa_rtclock_now() + SAP_INTERVAL, sap_event_cb, u); pa_source_output_put(u->source_output); diff --git a/src/modules/rtp/rtsp_client.c b/src/modules/rtp/rtsp_client.c index cb037de6..72d304e8 100644 --- a/src/modules/rtp/rtsp_client.c +++ b/src/modules/rtp/rtsp_client.c @@ -333,7 +333,7 @@ int pa_rtsp_connect(pa_rtsp_client *c) { pa_xfree(c->session); c->session = NULL; - if (!(c->sc = pa_socket_client_new_string(c->mainloop, c->hostname, c->port))) { + if (!(c->sc = pa_socket_client_new_string(c->mainloop, TRUE, c->hostname, c->port))) { pa_log("failed to connect to server '%s:%d'", c->hostname, c->port); return -1; } -- cgit