From 4fb17d1c0362f5d792e9df279438dd6059dd5d43 Mon Sep 17 00:00:00 2001 From: Wim Taymans Date: Thu, 30 Mar 2023 11:47:25 +0200 Subject: [PATCH] audioadapter: clear rate matching when not using converter Ensure that we clear the rate matching when we are not using the converter. This will make the follower use the quantum instead of the dummy unused rate matching area. Exit when we can't make an internal converter because then things really are not going to work. Remove some of the pointless NULL checks. --- spa/plugins/audioconvert/audioadapter.c | 64 ++++++++++++++----------- 1 file changed, 37 insertions(+), 27 deletions(-) diff --git a/spa/plugins/audioconvert/audioadapter.c b/spa/plugins/audioconvert/audioadapter.c index 2067820e3..9ecfd192e 100644 --- a/spa/plugins/audioconvert/audioadapter.c +++ b/spa/plugins/audioconvert/audioadapter.c @@ -227,30 +227,40 @@ next: static int link_io(struct impl *this) { int res; - - if (this->convert == NULL) - return 0; + struct spa_io_rate_match *rate_match; + size_t rate_match_size; spa_log_debug(this->log, "%p: controls", this); spa_zero(this->io_rate_match); this->io_rate_match.rate = 1.0; + if (this->follower == this->target) { + rate_match = NULL; + rate_match_size = 0; + } else { + rate_match = &this->io_rate_match; + rate_match_size = sizeof(this->io_rate_match); + } + if ((res = spa_node_port_set_io(this->follower, this->direction, 0, SPA_IO_RateMatch, - &this->io_rate_match, sizeof(this->io_rate_match))) < 0) { + rate_match, rate_match_size)) < 0) { spa_log_debug(this->log, "%p: set RateMatch on follower disabled %d %s", this, res, spa_strerror(res)); } else if ((res = spa_node_port_set_io(this->convert, SPA_DIRECTION_REVERSE(this->direction), 0, SPA_IO_RateMatch, - &this->io_rate_match, sizeof(this->io_rate_match))) < 0) { + rate_match, rate_match_size)) < 0) { spa_log_warn(this->log, "%p: set RateMatch on convert failed %d %s", this, res, spa_strerror(res)); } + if (this->follower == this->target) + return 0; + this->io_buffers = SPA_IO_BUFFERS_INIT; if ((res = spa_node_port_set_io(this->follower, @@ -488,7 +498,7 @@ static int configure_format(struct impl *this, uint32_t flags, const struct spa_ format = fmt; } - if (this->target != this->follower && this->convert) { + if (this->target != this->follower) { if ((res = spa_node_port_set_param(this->convert, SPA_DIRECTION_REVERSE(this->direction), 0, SPA_PARAM_Format, flags, @@ -566,8 +576,8 @@ static int reconfigure_mode(struct impl *this, bool passthrough, } else { /* add converter ports */ configure_convert(this, SPA_PARAM_PORT_CONFIG_MODE_dsp); - link_io(this); } + link_io(this); } this->info.change_mask |= SPA_NODE_CHANGE_MASK_FLAGS | SPA_NODE_CHANGE_MASK_PARAMS; @@ -775,18 +785,16 @@ static int negotiate_format(struct impl *this) goto done; } } - if (this->convert) { - state = 0; - if ((res = spa_node_port_enum_params_sync(this->convert, - SPA_DIRECTION_REVERSE(this->direction), 0, - SPA_PARAM_EnumFormat, &state, - format, &format, &b)) != 1) { - debug_params(this, this->convert, - SPA_DIRECTION_REVERSE(this->direction), 0, - SPA_PARAM_EnumFormat, format, "convert format", res); - res = -ENOTSUP; - goto done; - } + state = 0; + if ((res = spa_node_port_enum_params_sync(this->convert, + SPA_DIRECTION_REVERSE(this->direction), 0, + SPA_PARAM_EnumFormat, &state, + format, &format, &b)) != 1) { + debug_params(this, this->convert, + SPA_DIRECTION_REVERSE(this->direction), 0, + SPA_PARAM_EnumFormat, format, "convert format", res); + res = -ENOTSUP; + goto done; } if (format == NULL) { res = -ENOTSUP; @@ -1230,7 +1238,7 @@ static int follower_reuse_buffer(void *data, uint32_t port_id, uint32_t buffer_i int res; struct impl *this = data; - if (this->target != this->follower && this->convert) + if (this->target != this->follower) res = spa_node_port_reuse_buffer(this->convert, port_id, buffer_id); else res = spa_node_call_reuse_buffer(&this->callbacks, port_id, buffer_id); @@ -1273,11 +1281,10 @@ static int impl_node_add_listener(void *object, spa_node_add_listener(this->follower, &l, &follower_node_events, this); spa_hook_remove(&l); - if (this->convert) { - spa_zero(l); - spa_node_add_listener(this->convert, &l, &convert_node_events, this); - spa_hook_remove(&l); - } + spa_zero(l); + spa_node_add_listener(this->convert, &l, &convert_node_events, this); + spa_hook_remove(&l); + this->add_listener = false; emit_node_info(this, true); @@ -1467,7 +1474,7 @@ static int impl_node_process(void *object) * First we run the converter to process the input for the follower * then if it produced data, we run the follower. */ while (retry--) { - status = this->convert ? spa_node_process(this->convert) : 0; + status = spa_node_process(this->convert); /* schedule the follower when the converter needed * a recycled buffer */ if (status == -EPIPE || status == 0) @@ -1499,7 +1506,7 @@ static int impl_node_process(void *object) /* output node (source). First run the converter to make * sure we push out any queued data. Then when it needs * more data, schedule the follower. */ - status = this->convert ? spa_node_process(this->convert) : 0; + status = spa_node_process(this->convert); if (status == 0) status = SPA_STATUS_NEED_DATA; else if (status < 0) @@ -1661,6 +1668,9 @@ impl_init(const struct spa_handle_factory *factory, info, support, n_support); spa_handle_get_interface(this->hnd_convert, SPA_TYPE_INTERFACE_Node, &iface); + if (iface == NULL) + return -EINVAL; + this->convert = iface; this->target = this->convert;