Improve async handling

Don't use special callback in node to receive the results. Instead,
use a generic result callback to receive the result. This makes things
a bit more symetric and generic again because then you can choose how
to match the result to the request and you have a generic way to handle
both the sync and async case. We can then also remove the wait method.
This also makes the remote interface and spa interface to objects very
similar.

Make a helper object to receive and dispatch results. Use this in the
helper for enum_params.

Make device use the same result callbacks.
This commit is contained in:
Wim Taymans 2019-02-25 12:29:57 +01:00
parent 98463b689b
commit d2c18c7b1a
64 changed files with 1298 additions and 1141 deletions

View file

@ -180,23 +180,24 @@ static int impl_port_set_io(struct spa_node *node,
return 0;
}
static int impl_port_enum_params(struct spa_node *node,
static int impl_port_enum_params(struct spa_node *node, int seq,
enum spa_direction direction, uint32_t port_id,
uint32_t id, uint32_t start, uint32_t num,
const struct spa_pod *filter,
spa_result_func_t func, void *data)
const struct spa_pod *filter)
{
struct data *d = SPA_CONTAINER_OF(node, struct data, impl_node);
struct spa_pod *param;
struct spa_pod_builder b = { 0 };
uint8_t buffer[1024];
struct spa_result_node_enum_params result;
struct spa_result_node_params result;
uint32_t count = 0;
int res;
result.id = id;
result.next = start;
next:
result.index = result.next++;
spa_pod_builder_init(&b, buffer, sizeof(buffer));
switch (id) {
@ -208,10 +209,10 @@ static int impl_port_enum_params(struct spa_node *node,
SPA_PARAM_Meta,
SPA_PARAM_IO };
if (result.next < SPA_N_ELEMENTS(list))
if (result.index < SPA_N_ELEMENTS(list))
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamList, id,
SPA_PARAM_LIST_id, SPA_POD_Id(list[result.next]));
SPA_PARAM_LIST_id, SPA_POD_Id(list[result.index]));
else
return 0;
break;
@ -220,7 +221,7 @@ static int impl_port_enum_params(struct spa_node *node,
{
SDL_RendererInfo info;
if (result.next != 0)
if (result.index != 0)
return 0;
SDL_GetRendererInfo(d->renderer, &info);
@ -228,13 +229,13 @@ static int impl_port_enum_params(struct spa_node *node,
break;
}
case SPA_PARAM_Format:
if (result.next != 0 || d->format.format == 0)
if (result.index != 0 || d->format.format == 0)
return 0;
param = spa_format_video_raw_build(&b, id, &d->format);
break;
case SPA_PARAM_Buffers:
if (result.next != 0)
if (result.index != 0)
return 0;
param = spa_pod_builder_add_object(&b,
@ -247,7 +248,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_Meta:
switch (result.next) {
switch (result.index) {
case 0:
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamMeta, id,
@ -266,7 +267,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_IO:
switch (result.next) {
switch (result.index) {
case 0:
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamIO, id,
@ -286,12 +287,11 @@ static int impl_port_enum_params(struct spa_node *node,
default:
return -ENOENT;
}
result.next++;
if (spa_pod_filter(&b, &result.param, param, filter) < 0)
goto next;
if ((res = func(data, count, &result)) != 0)
if ((res = d->callbacks->result(d->callbacks_data, seq, 0, &result)) != 0)
return res;
if (++count != num)

View file

@ -148,23 +148,24 @@ static int impl_port_set_io(struct spa_node *node, enum spa_direction direction,
return 0;
}
static int impl_port_enum_params(struct spa_node *node,
static int impl_port_enum_params(struct spa_node *node, int seq,
enum spa_direction direction, uint32_t port_id,
uint32_t id, uint32_t start, uint32_t num,
const struct spa_pod *filter,
spa_result_func_t func, void *data)
const struct spa_pod *filter)
{
struct data *d = SPA_CONTAINER_OF(node, struct data, impl_node);
struct spa_pod *param;
struct spa_pod_builder b = { 0 };
uint8_t buffer[1024];
struct spa_result_node_enum_params result;
struct spa_result_node_params result;
uint32_t count = 0;
int res;
result.id = id;
result.next = start;
next:
result.index = result.next++;
spa_pod_builder_init(&b, buffer, sizeof(buffer));
switch (id) {
@ -176,16 +177,16 @@ static int impl_port_enum_params(struct spa_node *node,
SPA_PARAM_Meta,
SPA_PARAM_IO };
if (result.next < SPA_N_ELEMENTS(list))
if (result.index < SPA_N_ELEMENTS(list))
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamList, id,
SPA_PARAM_LIST_id, SPA_POD_Id(list[result.next]));
SPA_PARAM_LIST_id, SPA_POD_Id(list[result.index]));
else
return 0;
break;
}
case SPA_PARAM_EnumFormat:
if (result.next != 0)
if (result.index != 0)
return 0;
param = spa_pod_builder_add_object(&b,
@ -203,7 +204,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_Format:
if (result.next != 0)
if (result.index != 0)
return 0;
if (d->format.format == 0)
return 0;
@ -211,7 +212,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_Buffers:
if (result.next > 0)
if (result.index > 0)
return 0;
param = spa_pod_builder_add_object(&b,
@ -224,7 +225,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_Meta:
switch (result.next) {
switch (result.index) {
case 0:
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamMeta, id,
@ -236,7 +237,7 @@ static int impl_port_enum_params(struct spa_node *node,
}
break;
case SPA_PARAM_IO:
switch (result.next) {
switch (result.index) {
case 0:
param = spa_pod_builder_add_object(&b,
SPA_TYPE_OBJECT_ParamIO, id,
@ -257,12 +258,10 @@ static int impl_port_enum_params(struct spa_node *node,
return -ENOENT;
}
result.next++;
if (spa_pod_filter(&b, &result.param, param, filter) < 0)
goto next;
if ((res = func(data, count, &result)) != 0)
if ((res = d->callbacks->result(d->callbacks_data, seq, 0, &result)) != 0)
return res;
if (++count != num)

View file

@ -122,23 +122,24 @@ static int impl_port_set_io(struct spa_node *node, enum spa_direction direction,
return 0;
}
static int impl_port_enum_params(struct spa_node *node,
static int impl_port_enum_params(struct spa_node *node, int seq,
enum spa_direction direction, uint32_t port_id,
uint32_t id, uint32_t start, uint32_t num,
const struct spa_pod *filter,
spa_result_func_t func, void *data)
const struct spa_pod *filter)
{
struct data *d = SPA_CONTAINER_OF(node, struct data, impl_node);
struct spa_pod *param;
struct spa_pod_builder b = { 0 };
uint8_t buffer[1024];
struct spa_result_node_enum_params result;
struct spa_result_node_params result;
uint32_t count = 0;
int res;
result.id = id;
result.next = start;
next:
result.index = result.next++;
spa_pod_builder_init(&b, buffer, sizeof(buffer));
switch (id) {
@ -146,7 +147,7 @@ static int impl_port_enum_params(struct spa_node *node,
{
SDL_RendererInfo info;
if (result.next > 0)
if (result.index > 0)
return 0;
SDL_GetRendererInfo(d->renderer, &info);
@ -154,7 +155,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
}
case SPA_PARAM_Buffers:
if (result.next > 0)
if (result.index > 0)
return 0;
param = spa_pod_builder_add_object(&b,
@ -167,7 +168,7 @@ static int impl_port_enum_params(struct spa_node *node,
break;
case SPA_PARAM_Meta:
if (result.next > 0)
if (result.index > 0)
return 0;
param = spa_pod_builder_add_object(&b,
@ -180,12 +181,10 @@ static int impl_port_enum_params(struct spa_node *node,
return -ENOENT;
}
result.next++;
if (spa_pod_filter(&b, &result.param, param, filter) < 0)
goto next;
if ((res = func(data, count, &result)) != 0)
if ((res = d->callbacks->result(d->callbacks_data, seq, 0, &result)) != 0)
return res;
if (++count != num)

View file

@ -193,7 +193,7 @@ static void *find_object(struct impl *impl, uint32_t id)
static void schedule_rescan(struct impl *impl)
{
if (impl->core_proxy)
impl->seq = pw_core_proxy_sync(impl->core_proxy, 0);
impl->seq = pw_core_proxy_sync(impl->core_proxy, 0, impl->seq);
}
static void remove_idle_timeout(struct session *sess)
@ -367,7 +367,7 @@ static int node_event_info(void *object, const struct pw_node_info *info)
return 0;
}
static int node_event_param(void *object,
static int node_event_param(void *object, uint32_t seq,
uint32_t id, uint32_t index, uint32_t next,
const struct spa_pod *param)
{
@ -588,7 +588,7 @@ static int port_event_info(void *object, const struct pw_port_info *info)
return 0;
}
static int port_event_param(void *object,
static int port_event_param(void *object, uint32_t seq,
uint32_t id, uint32_t index, uint32_t next,
const struct spa_pod *param)
{
@ -1171,11 +1171,16 @@ static int rescan_node(struct impl *impl, struct node *node)
if (!exclusive && session->dsp) {
do_link_profile:
audio_info = peer->profile_format;
if (direction == PW_DIRECTION_INPUT)
audio_info.channels = SPA_MIN(peer->format.channels, node->format.channels);
else
audio_info.channels = SPA_MAX(peer->format.channels, node->format.channels);
pw_log_debug(NAME" %p: channels: %d %d -> %d", impl,
peer->format.channels, node->format.channels,
audio_info.channels);
node->profile_format = audio_info;
spa_pod_builder_init(&b, buf, sizeof(buf));