From f37bc7a88d374448a1f4bba9267d308606d78bf2 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Thu, 8 Nov 2012 15:59:23 +0100 Subject: [PATCH] ALSA: hda - Give standard "Bass Speaker" mixer for 2.1 speakers When two built-in speakers are found on the machine, we can suppose it's rather a 2.1 speaker system with a bass output instead of front/surround channels. Signed-off-by: Takashi Iwai --- sound/pci/hda/patch_cirrus.c | 8 +++++++- sound/pci/hda/patch_conexant.c | 28 +++++++++++++++++++++++++--- sound/pci/hda/patch_sigmatel.c | 8 ++++---- sound/pci/hda/patch_via.c | 6 +++--- 4 files changed, 39 insertions(+), 11 deletions(-) diff --git a/sound/pci/hda/patch_cirrus.c b/sound/pci/hda/patch_cirrus.c index b9039dbd704d..794b0da11212 100644 --- a/sound/pci/hda/patch_cirrus.c +++ b/sound/pci/hda/patch_cirrus.c @@ -68,6 +68,7 @@ struct cs_spec { unsigned int hp_detect:1; unsigned int mic_detect:1; + unsigned int speaker_2_1:1; /* CS421x */ unsigned int spdif_detect:1; unsigned int sense_b:1; @@ -443,6 +444,9 @@ static int parse_output(struct hda_codec *codec) spec->multiout.dac_nids = spec->dac_nid; spec->multiout.max_channels = i * 2; + if (cfg->line_out_type == AUTO_PIN_SPEAKER_OUT && i == 2) + spec->speaker_2_1 = 1; /* assume 2.1 speakers */ + /* add HP and speakers */ extra_nids = 0; for (i = 0; i < cfg->hp_outs; i++) { @@ -632,7 +636,9 @@ static int add_output(struct hda_codec *codec, hda_nid_t dac, int idx, index = idx; break; case AUTO_PIN_SPEAKER_OUT: - if (num_ctls > 1) + if (spec->speaker_2_1) + name = idx ? "Bass Speaker" : "Speaker"; + else if (num_ctls > 1) name = speakers[idx]; else name = "Speaker"; diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c index 252d4197f221..f8e9ff493dc7 100644 --- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c @@ -472,7 +472,7 @@ static const struct snd_kcontrol_new cxt_beep_mixer[] = { #endif static const char * const slave_pfxs[] = { - "Headphone", "Speaker", "Front", "Surround", "CLFE", + "Headphone", "Speaker", "Bass Speaker", "Front", "Surround", "CLFE", NULL }; @@ -4116,11 +4116,26 @@ static int try_add_pb_volume(struct hda_codec *codec, hda_nid_t dac, return 0; } +static bool is_2_1_speaker(struct conexant_spec *spec) +{ + int i, type, num_spk = 0; + + for (i = 0; i < spec->dac_info_filled; i++) { + type = spec->dac_info[i].type; + if (type == AUTO_PIN_LINE_OUT) + type = spec->autocfg.line_out_type; + if (type == AUTO_PIN_SPEAKER_OUT) + num_spk++; + } + return (num_spk == 2 && spec->autocfg.line_out_type != AUTO_PIN_LINE_OUT); +} + static int cx_auto_build_output_controls(struct hda_codec *codec) { struct conexant_spec *spec = codec->spec; int i, err; int num_line = 0, num_hp = 0, num_spk = 0; + bool speaker_2_1; static const char * const texts[3] = { "Front", "Surround", "CLFE" }; if (spec->dac_info_filled == 1) @@ -4128,6 +4143,8 @@ static int cx_auto_build_output_controls(struct hda_codec *codec) spec->dac_info[0].pin, "Master", 0); + speaker_2_1 = is_2_1_speaker(spec); + for (i = 0; i < spec->dac_info_filled; i++) { const char *label; int idx, type; @@ -4146,8 +4163,13 @@ static int cx_auto_build_output_controls(struct hda_codec *codec) idx = num_hp++; break; case AUTO_PIN_SPEAKER_OUT: - label = "Speaker"; - idx = num_spk++; + if (speaker_2_1) { + label = num_spk++ ? "Bass Speaker" : "Speaker"; + idx = 0; + } else { + label = "Speaker"; + idx = num_spk++; + } break; } err = try_add_pb_volume(codec, dac, diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index 962a948f4f10..f799406f4404 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -1081,7 +1081,7 @@ static struct snd_kcontrol_new stac_smux_mixer = { static const char * const slave_pfxs[] = { "Front", "Surround", "Center", "LFE", "Side", - "Headphone", "Speaker", "IEC958", "PCM", + "Headphone", "Speaker", "Bass Speaker", "IEC958", "PCM", NULL }; @@ -3269,9 +3269,9 @@ static int create_multi_out_ctls(struct hda_codec *codec, int num_outs, idx = i; break; case AUTO_PIN_SPEAKER_OUT: - if (num_outs <= 1) { - name = "Speaker"; - idx = i; + if (num_outs <= 2) { + name = i ? "Bass Speaker" : "Speaker"; + idx = 0; break; } /* Fall through in case of multi speaker outs */ diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c index 019e1a00414a..0e9b0747adc6 100644 --- a/sound/pci/hda/patch_via.c +++ b/sound/pci/hda/patch_via.c @@ -1454,7 +1454,7 @@ static const struct hda_pcm_stream via_pcm_digital_capture = { */ static const char * const via_slave_pfxs[] = { "Front", "Surround", "Center", "LFE", "Side", - "Headphone", "Speaker", + "Headphone", "Speaker", "Bass Speaker", NULL, }; @@ -1969,8 +1969,8 @@ static int via_auto_create_multi_out_ctls(struct hda_codec *codec) } else { const char *pfx = chname[i]; if (cfg->line_out_type == AUTO_PIN_SPEAKER_OUT && - cfg->line_outs == 1) - pfx = "Speaker"; + cfg->line_outs <= 2) + pfx = i ? "Bass Speaker" : "Speaker"; err = create_ch_ctls(codec, pfx, 3, true, path); if (err < 0) return err; -- 2.30.2