From 96c119fbe4cfbe52e895e73aca6d654428927850 Mon Sep 17 00:00:00 2001 From: Arun Raghavan Date: Wed, 12 Jan 2022 16:25:59 -0500 Subject: [PATCH] sink, source: Add a channel map validity check for reconfiguration Also move the check to an early assert instead of silently bailing. --- src/pulsecore/sink.c | 16 ++++++++++++---- src/pulsecore/source.c | 17 +++++++++++++---- 2 files changed, 25 insertions(+), 8 deletions(-) diff --git a/src/pulsecore/sink.c b/src/pulsecore/sink.c index cb62d7c81..5081925e1 100644 --- a/src/pulsecore/sink.c +++ b/src/pulsecore/sink.c @@ -1510,11 +1510,22 @@ int pa_sink_reconfigure(pa_sink *s, pa_sample_spec *spec, pa_channel_map *map, b pa_channel_map old_map, *new_map; bool restore = spec == NULL; - pa_assert(spec != NULL || (map == NULL && pa_sample_spec_valid(&s->saved_spec))); + /* if spec is unspecified (i.e. we want to restore), map must not be specified either */ + pa_assert(spec != NULL || map == NULL); + pa_assert(spec == NULL || pa_sample_spec_valid(spec)); + pa_assert(map == NULL || pa_channel_map_valid(map)); if (!restore && pa_sample_spec_equal(spec, &s->sample_spec)) return 0; + if (restore && !pa_sample_spec_valid(&s->saved_spec)) { + /* If we were asked to restore and nothing was saved, this is not an + * error -- it means that no reconfiguration was required in the + * "entry" phase, so none is required in the "exit" phase either. + */ + return 0; + } + if (!s->reconfigure) return -1; @@ -1536,9 +1547,6 @@ int pa_sink_reconfigure(pa_sink *s, pa_sample_spec *spec, pa_channel_map *map, b } } - if (PA_UNLIKELY(!restore && !pa_sample_spec_valid(spec))) - return -1; - if (passthrough) { /* Save the previous sample spec and channel map, we will try to restore it when leaving passthrough */ s->saved_spec = s->sample_spec; diff --git a/src/pulsecore/source.c b/src/pulsecore/source.c index e4d351581..3a96a4954 100644 --- a/src/pulsecore/source.c +++ b/src/pulsecore/source.c @@ -1073,11 +1073,23 @@ int pa_source_reconfigure(pa_source *s, pa_sample_spec *spec, pa_channel_map *ma pa_channel_map old_map, *new_map; bool restore = spec == NULL; - pa_assert(spec != NULL || (map == NULL && pa_sample_spec_valid(&s->saved_spec))); + /* if spec is unspecified (i.e. we want to restore), map must not be specified either */ + pa_assert(spec != NULL || map == NULL); + pa_assert(spec == NULL || pa_sample_spec_valid(spec)); + pa_assert(map == NULL || pa_channel_map_valid(map)); + if (!restore && pa_sample_spec_equal(spec, &s->sample_spec)) return 0; + if (restore && !pa_sample_spec_valid(&s->saved_spec)) { + /* If we were asked to restore and nothing was saved, this is not an + * error -- it means that no reconfiguration was required in the + * "entry" phase, so none is required in the "exit" phase either. + */ + return 0; + } + if (!s->reconfigure && !s->monitor_of) return -1; @@ -1099,9 +1111,6 @@ int pa_source_reconfigure(pa_source *s, pa_sample_spec *spec, pa_channel_map *ma } } - if (PA_UNLIKELY(!restore && !pa_sample_spec_valid(spec))) - return -1; - if (passthrough) { /* Save the previous sample spec and channel map, we will try to restore it when leaving passthrough */ s->saved_spec = s->sample_spec;