Hi guys,

Finally the circumstances (e.g. customer priorities :D) allowed me to
port the audio glitch work-around to 3.10.53. Feel welcome to take a
look at it and give it a try, and I'll be more than happy if it fixes
the issue for you.

Note: the patch is just RFC to illustrate the issue and one possible
solution.

Kind regards,
Nikolay
>From f3f5259c959b561e53feef72524d587fccac1edd Mon Sep 17 00:00:00 2001
From: Nikolay Dimitrov <[email protected]>
Date: Wed, 24 Jun 2015 20:11:28 +0300
Subject: [PATCH] sound: sgtl5000: Fix audio glitch after audio stream is
 stopped

When an audio stream is stopped, ALSA DAPM subsystem shutdowns the
audio codec after several seconds of inactivity to conserve power. This
shutdown sequence causes an audible glitch on SGTL5000 codec's line-out.
This patch disables the DAPM for SGTL5000 and keeps the codec's internal
modules powered-on all the time to prevent the audio glitch.

Upstream-status: Inappropriate [design]
 - ALSA DAPM is mandatory by design, and the patch violates this
   requirement

Signed-off-by: Nikolay Dimitrov <[email protected]>
---
 sound/soc/codecs/sgtl5000.c |   68 +++++++------------------------------------
 1 file changed, 10 insertions(+), 58 deletions(-)

diff --git a/sound/soc/codecs/sgtl5000.c b/sound/soc/codecs/sgtl5000.c
index ddf66d9..3750ec8 100644
--- a/sound/soc/codecs/sgtl5000.c
+++ b/sound/soc/codecs/sgtl5000.c
@@ -142,32 +142,6 @@ static int mic_bias_event(struct snd_soc_dapm_widget *w,
 	return 0;
 }
 
-/*
- * As manual described, ADC/DAC only works when VAG powerup,
- * So enabled VAG before ADC/DAC up.
- * In power down case, we need wait 400ms when vag fully ramped down.
- */
-static int power_vag_event(struct snd_soc_dapm_widget *w,
-	struct snd_kcontrol *kcontrol, int event)
-{
-	switch (event) {
-	case SND_SOC_DAPM_POST_PMU:
-		snd_soc_update_bits(w->codec, SGTL5000_CHIP_ANA_POWER,
-			SGTL5000_VAG_POWERUP, SGTL5000_VAG_POWERUP);
-		break;
-
-	case SND_SOC_DAPM_PRE_PMD:
-		snd_soc_update_bits(w->codec, SGTL5000_CHIP_ANA_POWER,
-			SGTL5000_VAG_POWERUP, 0);
-		msleep(400);
-		break;
-	default:
-		break;
-	}
-
-	return 0;
-}
-
 /* input sources for ADC */
 static const char *adc_mux_text[] = {
 	"MIC_IN", "LINE_IN"
@@ -201,27 +175,8 @@ static const struct snd_soc_dapm_widget sgtl5000_dapm_widgets[] = {
 			    mic_bias_event,
 			    SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD),
 
-	SND_SOC_DAPM_PGA("HP", SGTL5000_CHIP_ANA_POWER, 4, 0, NULL, 0),
-	SND_SOC_DAPM_PGA("LO", SGTL5000_CHIP_ANA_POWER, 0, 0, NULL, 0),
-
 	SND_SOC_DAPM_MUX("Capture Mux", SND_SOC_NOPM, 0, 0, &adc_mux),
 	SND_SOC_DAPM_MUX("Headphone Mux", SND_SOC_NOPM, 0, 0, &dac_mux),
-
-	/* aif for i2s input */
-	SND_SOC_DAPM_AIF_IN("AIFIN", "Playback",
-				0, SGTL5000_CHIP_DIG_POWER,
-				0, 0),
-
-	/* aif for i2s output */
-	SND_SOC_DAPM_AIF_OUT("AIFOUT", "Capture",
-				0, SGTL5000_CHIP_DIG_POWER,
-				1, 0),
-
-	SND_SOC_DAPM_ADC("ADC", "Capture", SGTL5000_CHIP_ANA_POWER, 1, 0),
-	SND_SOC_DAPM_DAC("DAC", "Playback", SGTL5000_CHIP_ANA_POWER, 3, 0),
-
-	SND_SOC_DAPM_PRE("VAG_POWER_PRE", power_vag_event),
-	SND_SOC_DAPM_POST("VAG_POWER_POST", power_vag_event),
 };
 
 /* routes for sgtl5000 */
@@ -229,18 +184,7 @@ static const struct snd_soc_dapm_route sgtl5000_dapm_routes[] = {
 	{"Capture Mux", "LINE_IN", "LINE_IN"},	/* line_in --> adc_mux */
 	{"Capture Mux", "MIC_IN", "MIC_IN"},	/* mic_in --> adc_mux */
 
-	{"ADC", NULL, "Capture Mux"},		/* adc_mux --> adc */
-	{"AIFOUT", NULL, "ADC"},		/* adc --> i2s_out */
-
-	{"DAC", NULL, "AIFIN"},			/* i2s-->dac,skip audio mux */
-	{"Headphone Mux", "DAC", "DAC"},	/* dac --> hp_mux */
-	{"LO", NULL, "DAC"},			/* dac --> line_out */
-
 	{"Headphone Mux", "LINE_IN", "LINE_IN"},/* line_in --> hp_mux */
-	{"HP", NULL, "Headphone Mux"},		/* hp_mux --> hp */
-
-	{"LINE_OUT", NULL, "LO"},
-	{"HP_OUT", NULL, "HP"},
 };
 
 /* custom function to fetch info of PCM playback volume */
@@ -1096,7 +1040,12 @@ static int sgtl5000_set_power_regs(struct snd_soc_codec *codec)
 	ana_pwr = snd_soc_read(codec, SGTL5000_CHIP_ANA_POWER);
 	ana_pwr |= SGTL5000_DAC_STEREO |
 			SGTL5000_ADC_STEREO |
-			SGTL5000_REFTOP_POWERUP;
+			SGTL5000_VAG_POWERUP |
+			SGTL5000_REFTOP_POWERUP |
+			SGTL5000_DAC_POWERUP |
+			SGTL5000_CAPLESS_HP_POWERUP |
+			SGTL5000_ADC_POWERUP |
+			SGTL5000_LINE_OUT_POWERUP;
 	lreg_ctrl = snd_soc_read(codec, SGTL5000_CHIP_LINREG_CTRL);
 
 	if (vddio < 3100 && vdda < 3100) {
@@ -1326,7 +1275,10 @@ static int sgtl5000_probe(struct snd_soc_codec *codec)
 	snd_soc_write(codec, SGTL5000_CHIP_SSS_CTRL,
 			SGTL5000_DAC_SEL_I2S_IN << SGTL5000_DAC_SEL_SHIFT);
 	snd_soc_write(codec, SGTL5000_CHIP_DIG_POWER,
-			SGTL5000_ADC_EN | SGTL5000_DAC_EN);
+			SGTL5000_ADC_EN |
+			SGTL5000_DAC_EN |
+			SGTL5000_I2S_OUT_POWERUP |
+			SGTL5000_I2S_IN_POWERUP);
 
 	/* enable dac volume ramp by default */
 	snd_soc_write(codec, SGTL5000_CHIP_ADCDAC_CTRL,
-- 
1.7.10.4

-- 
_______________________________________________
meta-freescale mailing list
[email protected]
https://lists.yoctoproject.org/listinfo/meta-freescale

Reply via email to