[pulseaudio-discuss] [PATCH 3/3] alsa-mixer: autodetect the HDMI jack PCM device
Tanu Kaskinen
tanuk at iki.fi
Mon Jun 12 15:45:16 UTC 2017
This removes the need to hardcode the PCM device index in the HDMI jack
names. The hardcoded values don't work with the Intel HDMI LPE driver.
BugLink: https://bugs.freedesktop.org/show_bug.cgi?id=100488
---
src/modules/alsa/alsa-mixer.c | 50 ++++++++++++++++++++--
src/modules/alsa/alsa-mixer.h | 4 +-
src/modules/alsa/alsa-sink.c | 2 +-
src/modules/alsa/alsa-source.c | 2 +-
.../alsa/mixer/paths/analog-output.conf.common | 5 +++
src/modules/alsa/mixer/paths/hdmi-output-0.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-1.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-2.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-3.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-4.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-5.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-6.conf | 3 +-
src/modules/alsa/mixer/paths/hdmi-output-7.conf | 3 +-
13 files changed, 73 insertions(+), 14 deletions(-)
diff --git a/src/modules/alsa/alsa-mixer.c b/src/modules/alsa/alsa-mixer.c
index 71b393e49..49ce39e6b 100644
--- a/src/modules/alsa/alsa-mixer.c
+++ b/src/modules/alsa/alsa-mixer.c
@@ -1812,12 +1812,31 @@ static int element_probe(pa_alsa_element *e, snd_mixer_t *m) {
return 0;
}
-static int jack_probe(pa_alsa_jack *j, snd_mixer_t *m) {
+static int jack_probe(pa_alsa_jack *j, pa_alsa_mapping *mapping, snd_mixer_t *m) {
bool has_control;
pa_assert(j);
pa_assert(j->path);
+ if (j->append_pcm_to_name) {
+ char *new_name;
+
+ if (!mapping) {
+ /* This could also be an assertion, because this should never
+ * happen. At the time of writing, mapping can only be NULL when
+ * module-alsa-sink/source synthesizes a path, and those
+ * synthesized paths never have any jacks, so jack_probe() should
+ * never be called with a NULL mapping. */
+ pa_log("Jack %s: append_pcm_to_name is set, but mapping is NULL. Can't use this jack.", j->name);
+ return -1;
+ }
+
+ new_name = pa_sprintf_malloc("%s,pcm=%i Jack", j->name, mapping->hw_device_index);
+ pa_xfree(j->alsa_name);
+ j->alsa_name = new_name;
+ j->append_pcm_to_name = false;
+ }
+
has_control = pa_alsa_mixer_find(m, j->alsa_name, 0) != NULL;
pa_alsa_jack_set_has_control(j, has_control);
@@ -2348,6 +2367,30 @@ static int jack_parse_state(pa_config_parser_state *state) {
return 0;
}
+static int jack_parse_append_pcm_to_name(pa_config_parser_state *state) {
+ pa_alsa_path *path;
+ pa_alsa_jack *jack;
+ int b;
+
+ pa_assert(state);
+
+ path = state->userdata;
+ if (!(jack = jack_get(path, state->section))) {
+ pa_log("[%s:%u] Option 'append_pcm_to_name' not expected in section '%s'",
+ state->filename, state->lineno, state->section);
+ return -1;
+ }
+
+ b = pa_parse_boolean(state->rvalue);
+ if (b < 0) {
+ pa_log("[%s:%u] Invalid value for 'append_pcm_to_name': %s", state->filename, state->lineno, state->rvalue);
+ return -1;
+ }
+
+ jack->append_pcm_to_name = b;
+ return 0;
+}
+
static int element_set_option(pa_alsa_element *e, snd_mixer_t *m, int alsa_idx) {
snd_mixer_selem_id_t *sid;
snd_mixer_elem_t *me;
@@ -2555,6 +2598,7 @@ pa_alsa_path* pa_alsa_path_new(const char *paths_dir, const char *fname, pa_alsa
/* [Jack ...] */
{ "state.plugged", jack_parse_state, NULL, NULL },
{ "state.unplugged", jack_parse_state, NULL, NULL },
+ { "append-pcm-to-name", jack_parse_append_pcm_to_name, NULL, NULL },
/* [Element ...] */
{ "switch", element_parse_switch, NULL, NULL },
@@ -2766,7 +2810,7 @@ static void path_create_settings(pa_alsa_path *p) {
element_create_settings(p->elements, NULL);
}
-int pa_alsa_path_probe(pa_alsa_path *p, snd_mixer_t *m, bool ignore_dB) {
+int pa_alsa_path_probe(pa_alsa_path *p, pa_alsa_mapping *mapping, snd_mixer_t *m, bool ignore_dB) {
pa_alsa_element *e;
pa_alsa_jack *j;
double min_dB[PA_CHANNEL_POSITION_MAX], max_dB[PA_CHANNEL_POSITION_MAX];
@@ -2786,7 +2830,7 @@ int pa_alsa_path_probe(pa_alsa_path *p, snd_mixer_t *m, bool ignore_dB) {
pa_log_debug("Probing path '%s'", p->name);
PA_LLIST_FOREACH(j, p->jacks) {
- if (jack_probe(j, m) < 0) {
+ if (jack_probe(j, mapping, m) < 0) {
p->supported = false;
pa_log_debug("Probe of jack '%s' failed.", j->alsa_name);
return -1;
diff --git a/src/modules/alsa/alsa-mixer.h b/src/modules/alsa/alsa-mixer.h
index d85cc38d3..7400064fa 100644
--- a/src/modules/alsa/alsa-mixer.h
+++ b/src/modules/alsa/alsa-mixer.h
@@ -171,6 +171,8 @@ struct pa_alsa_jack {
pa_dynarray *ucm_devices; /* pa_alsa_ucm_device */
pa_dynarray *ucm_hw_mute_devices; /* pa_alsa_ucm_device */
+
+ bool append_pcm_to_name;
};
pa_alsa_jack *pa_alsa_jack_new(pa_alsa_path *path, const char *name);
@@ -235,7 +237,7 @@ void pa_alsa_element_dump(pa_alsa_element *e);
pa_alsa_path *pa_alsa_path_new(const char *paths_dir, const char *fname, pa_alsa_direction_t direction);
pa_alsa_path *pa_alsa_path_synthesize(const char *element, pa_alsa_direction_t direction);
-int pa_alsa_path_probe(pa_alsa_path *p, snd_mixer_t *m, bool ignore_dB);
+int pa_alsa_path_probe(pa_alsa_path *p, pa_alsa_mapping *mapping, snd_mixer_t *m, bool ignore_dB);
void pa_alsa_path_dump(pa_alsa_path *p);
int pa_alsa_path_get_volume(pa_alsa_path *p, snd_mixer_t *m, const pa_channel_map *cm, pa_cvolume *v);
int pa_alsa_path_get_mute(pa_alsa_path *path, snd_mixer_t *m, bool *muted);
diff --git a/src/modules/alsa/alsa-sink.c b/src/modules/alsa/alsa-sink.c
index 827a65081..99ca5061b 100644
--- a/src/modules/alsa/alsa-sink.c
+++ b/src/modules/alsa/alsa-sink.c
@@ -1912,7 +1912,7 @@ static void find_mixer(struct userdata *u, pa_alsa_mapping *mapping, const char
if (!(u->mixer_path = pa_alsa_path_synthesize(element, PA_ALSA_DIRECTION_OUTPUT)))
goto fail;
- if (pa_alsa_path_probe(u->mixer_path, u->mixer_handle, ignore_dB) < 0)
+ if (pa_alsa_path_probe(u->mixer_path, NULL, u->mixer_handle, ignore_dB) < 0)
goto fail;
pa_log_debug("Probed mixer path %s:", u->mixer_path->name);
diff --git a/src/modules/alsa/alsa-source.c b/src/modules/alsa/alsa-source.c
index 6bec188ea..84abbf1d9 100644
--- a/src/modules/alsa/alsa-source.c
+++ b/src/modules/alsa/alsa-source.c
@@ -1615,7 +1615,7 @@ static void find_mixer(struct userdata *u, pa_alsa_mapping *mapping, const char
if (!(u->mixer_path = pa_alsa_path_synthesize(element, PA_ALSA_DIRECTION_INPUT)))
goto fail;
- if (pa_alsa_path_probe(u->mixer_path, u->mixer_handle, ignore_dB) < 0)
+ if (pa_alsa_path_probe(u->mixer_path, NULL, u->mixer_handle, ignore_dB) < 0)
goto fail;
pa_log_debug("Probed mixer path %s:", u->mixer_path->name);
diff --git a/src/modules/alsa/mixer/paths/analog-output.conf.common b/src/modules/alsa/mixer/paths/analog-output.conf.common
index a113a2e3a..13d4f7c3b 100644
--- a/src/modules/alsa/mixer/paths/analog-output.conf.common
+++ b/src/modules/alsa/mixer/paths/analog-output.conf.common
@@ -124,6 +124,11 @@
; # the required-any are present.
; state.plugged = yes | no | unknown # Normally a plugged jack would mean the port becomes available, and an unplugged means it's
; state.unplugged = yes | no | unknown # unavailable, but the port status can be overridden by specifying state.plugged and/or state.unplugged.
+; append-pcm-to-name = no | yes # Add ",pcm=N" to the jack name? N is the hw PCM device index. HDMI jacks have
+; # the PCM device index in their name, but different drivers use different
+; # numbering schemes, so we can't hardcode the full jack name in our configuration
+; # files. If this is set to "yes", then also "query-hw-device" in the mapping
+; # configuration needs to be set to "yes".
[Element PCM]
switch = mute
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-0.conf b/src/modules/alsa/mixer/paths/hdmi-output-0.conf
index ce96a4989..95b1342e9 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-0.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-0.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=3]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-1.conf b/src/modules/alsa/mixer/paths/hdmi-output-1.conf
index d35f6cb93..37b945204 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-1.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-1.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=7]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-2.conf b/src/modules/alsa/mixer/paths/hdmi-output-2.conf
index b54da82f4..19c38f2e8 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-2.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-2.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=8]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-3.conf b/src/modules/alsa/mixer/paths/hdmi-output-3.conf
index 27f786fc7..8551570ac 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-3.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-3.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=9]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-4.conf b/src/modules/alsa/mixer/paths/hdmi-output-4.conf
index 8e7f82f40..e36128921 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-4.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-4.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=10]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-5.conf b/src/modules/alsa/mixer/paths/hdmi-output-5.conf
index 708e83876..82dc3be79 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-5.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-5.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=11]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-6.conf b/src/modules/alsa/mixer/paths/hdmi-output-6.conf
index 340d5e495..92e8fd1e2 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-6.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-6.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=12]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
diff --git a/src/modules/alsa/mixer/paths/hdmi-output-7.conf b/src/modules/alsa/mixer/paths/hdmi-output-7.conf
index 9946eda2c..abe2b60e6 100644
--- a/src/modules/alsa/mixer/paths/hdmi-output-7.conf
+++ b/src/modules/alsa/mixer/paths/hdmi-output-7.conf
@@ -6,5 +6,6 @@ eld-device = auto
[Properties]
device.icon_name = video-display
-[Jack HDMI/DP,pcm=13]
+[Jack HDMI/DP]
+append-pcm-to-name = yes
required = ignore
--
2.11.0
More information about the pulseaudio-discuss
mailing list