Commit 978d4ddb authored by Mark Brown's avatar Mark Brown

Merge remote-tracking branches 'asoc/topic/suspend', 'asoc/topic/tas2552',...

Merge remote-tracking branches 'asoc/topic/suspend', 'asoc/topic/tas2552', 'asoc/topic/tegra', 'asoc/topic/tlv320aic31xx' and 'asoc/topic/tlv320aic3x' into asoc-next
......@@ -25,6 +25,7 @@ Required properties:
Optional properties:
- nvidia,hp-det-gpios : The GPIO that detect headphones are plugged in
- nvidia,mic-det-gpios : The GPIO that detect microphones are plugged in
Example:
......
......@@ -1337,8 +1337,6 @@ static int pm860x_probe(struct snd_soc_codec *codec)
}
}
pm860x_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
out:
......@@ -1354,7 +1352,6 @@ static int pm860x_remove(struct snd_soc_codec *codec)
for (i = 3; i >= 0; i--)
free_irq(pm860x->irq[i], pm860x);
pm860x_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
......
......@@ -946,20 +946,6 @@ static struct snd_soc_dai_driver cs42l52_dai = {
.ops = &cs42l52_ops,
};
static int cs42l52_suspend(struct snd_soc_codec *codec)
{
cs42l52_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static int cs42l52_resume(struct snd_soc_codec *codec)
{
cs42l52_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int beep_rates[] = {
261, 522, 585, 667, 706, 774, 889, 1000,
1043, 1200, 1333, 1412, 1600, 1714, 2000, 2182
......@@ -1104,8 +1090,6 @@ static int cs42l52_probe(struct snd_soc_codec *codec)
cs42l52_init_beep(codec);
cs42l52_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
cs42l52->sysclk = CS42L52_DEFAULT_CLK;
cs42l52->config.format = CS42L52_DEFAULT_FORMAT;
......@@ -1115,7 +1099,6 @@ static int cs42l52_probe(struct snd_soc_codec *codec)
static int cs42l52_remove(struct snd_soc_codec *codec)
{
cs42l52_free_beep(codec);
cs42l52_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
......@@ -1123,9 +1106,8 @@ static int cs42l52_remove(struct snd_soc_codec *codec)
static struct snd_soc_codec_driver soc_codec_dev_cs42l52 = {
.probe = cs42l52_probe,
.remove = cs42l52_remove,
.suspend = cs42l52_suspend,
.resume = cs42l52_resume,
.set_bias_level = cs42l52_set_bias_level,
.suspend_bias_off = true,
.dapm_widgets = cs42l52_dapm_widgets,
.num_dapm_widgets = ARRAY_SIZE(cs42l52_dapm_widgets),
......
......@@ -1016,20 +1016,6 @@ static struct snd_soc_dai_driver cs42l56_dai = {
.ops = &cs42l56_ops,
};
static int cs42l56_suspend(struct snd_soc_codec *codec)
{
cs42l56_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static int cs42l56_resume(struct snd_soc_codec *codec)
{
cs42l56_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int beep_freq[] = {
261, 522, 585, 667, 706, 774, 889, 1000,
1043, 1200, 1333, 1412, 1600, 1714, 2000, 2182
......@@ -1168,15 +1154,12 @@ static int cs42l56_probe(struct snd_soc_codec *codec)
{
cs42l56_init_beep(codec);
cs42l56_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int cs42l56_remove(struct snd_soc_codec *codec)
{
cs42l56_free_beep(codec);
cs42l56_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
......@@ -1184,9 +1167,8 @@ static int cs42l56_remove(struct snd_soc_codec *codec)
static struct snd_soc_codec_driver soc_codec_dev_cs42l56 = {
.probe = cs42l56_probe,
.remove = cs42l56_remove,
.suspend = cs42l56_suspend,
.resume = cs42l56_resume,
.set_bias_level = cs42l56_set_bias_level,
.suspend_bias_off = true,
.dapm_widgets = cs42l56_dapm_widgets,
.num_dapm_widgets = ARRAY_SIZE(cs42l56_dapm_widgets),
......
......@@ -1330,25 +1330,10 @@ static struct snd_soc_dai_driver cs42l73_dai[] = {
}
};
static int cs42l73_suspend(struct snd_soc_codec *codec)
{
cs42l73_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static int cs42l73_resume(struct snd_soc_codec *codec)
{
cs42l73_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int cs42l73_probe(struct snd_soc_codec *codec)
{
struct cs42l73_private *cs42l73 = snd_soc_codec_get_drvdata(codec);
cs42l73_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
/* Set Charge Pump Frequency */
if (cs42l73->pdata.chgfreq)
snd_soc_update_bits(codec, CS42L73_CPFCHC,
......@@ -1362,18 +1347,10 @@ static int cs42l73_probe(struct snd_soc_codec *codec)
return 0;
}
static int cs42l73_remove(struct snd_soc_codec *codec)
{
cs42l73_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static struct snd_soc_codec_driver soc_codec_dev_cs42l73 = {
.probe = cs42l73_probe,
.remove = cs42l73_remove,
.suspend = cs42l73_suspend,
.resume = cs42l73_resume,
.set_bias_level = cs42l73_set_bias_level,
.suspend_bias_off = true,
.dapm_widgets = cs42l73_dapm_widgets,
.num_dapm_widgets = ARRAY_SIZE(cs42l73_dapm_widgets),
......
......@@ -35,7 +35,6 @@
struct da732x_priv {
struct regmap *regmap;
struct snd_soc_codec *codec;
unsigned int sysclk;
bool pll_en;
......@@ -1508,31 +1507,7 @@ static int da732x_set_bias_level(struct snd_soc_codec *codec,
return 0;
}
static int da732x_probe(struct snd_soc_codec *codec)
{
struct da732x_priv *da732x = snd_soc_codec_get_drvdata(codec);
struct snd_soc_dapm_context *dapm = &codec->dapm;
da732x->codec = codec;
dapm->idle_bias_off = false;
da732x_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int da732x_remove(struct snd_soc_codec *codec)
{
da732x_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static struct snd_soc_codec_driver soc_codec_dev_da732x = {
.probe = da732x_probe,
.remove = da732x_remove,
.set_bias_level = da732x_set_bias_level,
.controls = da732x_snd_controls,
.num_controls = ARRAY_SIZE(da732x_snd_controls),
......
......@@ -293,41 +293,13 @@ static int jz4740_codec_dev_probe(struct snd_soc_codec *codec)
regmap_update_bits(jz4740_codec->regmap, JZ4740_REG_CODEC_1,
JZ4740_CODEC_1_SW2_ENABLE, JZ4740_CODEC_1_SW2_ENABLE);
jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static int jz4740_codec_dev_remove(struct snd_soc_codec *codec)
{
jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
#ifdef CONFIG_PM_SLEEP
static int jz4740_codec_suspend(struct snd_soc_codec *codec)
{
return jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_OFF);
}
static int jz4740_codec_resume(struct snd_soc_codec *codec)
{
return jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
}
#else
#define jz4740_codec_suspend NULL
#define jz4740_codec_resume NULL
#endif
static struct snd_soc_codec_driver soc_codec_dev_jz4740_codec = {
.probe = jz4740_codec_dev_probe,
.remove = jz4740_codec_dev_remove,
.suspend = jz4740_codec_suspend,
.resume = jz4740_codec_resume,
.set_bias_level = jz4740_codec_set_bias_level,
.suspend_bias_off = true,
.controls = jz4740_codec_controls,
.num_controls = ARRAY_SIZE(jz4740_codec_controls),
......
......@@ -565,41 +565,19 @@ static struct snd_soc_dai_driver ml26124_dai = {
.symmetric_rates = 1,
};
#ifdef CONFIG_PM
static int ml26124_suspend(struct snd_soc_codec *codec)
{
ml26124_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static int ml26124_resume(struct snd_soc_codec *codec)
{
ml26124_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
#else
#define ml26124_suspend NULL
#define ml26124_resume NULL
#endif
static int ml26124_probe(struct snd_soc_codec *codec)
{
/* Software Reset */
snd_soc_update_bits(codec, ML26124_SW_RST, 0x01, 1);
snd_soc_update_bits(codec, ML26124_SW_RST, 0x01, 0);
ml26124_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
static struct snd_soc_codec_driver soc_codec_dev_ml26124 = {
.probe = ml26124_probe,
.suspend = ml26124_suspend,
.resume = ml26124_resume,
.set_bias_level = ml26124_set_bias_level,
.suspend_bias_off = true,
.dapm_widgets = ml26124_dapm_widgets,
.num_dapm_widgets = ARRAY_SIZE(ml26124_dapm_widgets),
.dapm_routes = ml26124_intercon,
......
......@@ -1076,26 +1076,6 @@ static bool sgtl5000_readable(struct device *dev, unsigned int reg)
}
}
#ifdef CONFIG_SUSPEND
static int sgtl5000_suspend(struct snd_soc_codec *codec)
{
sgtl5000_set_bias_level(codec, SND_SOC_BIAS_OFF);
return 0;
}
static int sgtl5000_resume(struct snd_soc_codec *codec)
{
/* Bring the codec back up to standby to enable regulators */
sgtl5000_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
#else
#define sgtl5000_suspend NULL
#define sgtl5000_resume NULL
#endif /* CONFIG_SUSPEND */
/*
* sgtl5000 has 3 internal power supplies:
* 1. VAG, normally set to vdda/2
......@@ -1355,11 +1335,6 @@ static int sgtl5000_probe(struct snd_soc_codec *codec)
*/
snd_soc_write(codec, SGTL5000_DAP_CTRL, 0);
/* leading to standby state */
ret = sgtl5000_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
if (ret)
goto err;
return 0;
err:
......@@ -1376,8 +1351,6 @@ static int sgtl5000_remove(struct snd_soc_codec *codec)
{
struct sgtl5000_priv *sgtl5000 = snd_soc_codec_get_drvdata(codec);
sgtl5000_set_bias_level(codec, SND_SOC_BIAS_OFF);
regulator_bulk_disable(ARRAY_SIZE(sgtl5000->supplies),
sgtl5000->supplies);
regulator_bulk_free(ARRAY_SIZE(sgtl5000->supplies),
......@@ -1390,9 +1363,8 @@ static int sgtl5000_remove(struct snd_soc_codec *codec)
static struct snd_soc_codec_driver sgtl5000_driver = {
.probe = sgtl5000_probe,
.remove = sgtl5000_remove,
.suspend = sgtl5000_suspend,
.resume = sgtl5000_resume,
.set_bias_level = sgtl5000_set_bias_level,
.suspend_bias_off = true,
.controls = sgtl5000_snd_controls,
.num_controls = ARRAY_SIZE(sgtl5000_snd_controls),
.dapm_widgets = sgtl5000_dapm_widgets,
......
......@@ -78,6 +78,44 @@ struct tas2552_data {
unsigned int mclk;
};
/* Input mux controls */
static const char *tas2552_input_texts[] = {
"Digital", "Analog"
};
static SOC_ENUM_SINGLE_DECL(tas2552_input_mux_enum, TAS2552_CFG_3, 7,
tas2552_input_texts);
static const struct snd_kcontrol_new tas2552_input_mux_control[] = {
SOC_DAPM_ENUM("Input selection", tas2552_input_mux_enum)
};
static const struct snd_soc_dapm_widget tas2552_dapm_widgets[] =
{
SND_SOC_DAPM_INPUT("IN"),
/* MUX Controls */
SND_SOC_DAPM_MUX("Input selection", SND_SOC_NOPM, 0, 0,
tas2552_input_mux_control),
SND_SOC_DAPM_AIF_IN("DAC IN", "DAC Playback", 0, SND_SOC_NOPM, 0, 0),
SND_SOC_DAPM_DAC("DAC", NULL, SND_SOC_NOPM, 0, 0),
SND_SOC_DAPM_OUT_DRV("ClassD", TAS2552_CFG_2, 7, 0, NULL, 0),
SND_SOC_DAPM_SUPPLY("PLL", TAS2552_CFG_2, 3, 0, NULL, 0),
SND_SOC_DAPM_OUTPUT("OUT")
};
static const struct snd_soc_dapm_route tas2552_audio_map[] = {
{"DAC", NULL, "DAC IN"},
{"Input selection", "Digital", "DAC"},
{"Input selection", "Analog", "IN"},
{"ClassD", NULL, "Input selection"},
{"OUT", NULL, "ClassD"},
{"ClassD", NULL, "PLL"},
};
#ifdef CONFIG_PM_RUNTIME
static void tas2552_sw_shutdown(struct tas2552_data *tas_data, int sw_shutdown)
{
u8 cfg1_reg;
......@@ -90,6 +128,7 @@ static void tas2552_sw_shutdown(struct tas2552_data *tas_data, int sw_shutdown)
snd_soc_update_bits(tas_data->codec, TAS2552_CFG_1,
TAS2552_SWS_MASK, cfg1_reg);
}
#endif
static int tas2552_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
......@@ -101,10 +140,6 @@ static int tas2552_hw_params(struct snd_pcm_substream *substream,
int d;
u8 p, j;
/* Turn on Class D amplifier */
snd_soc_update_bits(codec, TAS2552_CFG_2, TAS2552_CLASSD_EN_MASK,
TAS2552_CLASSD_EN);
if (!tas2552->mclk)
return -EINVAL;
......@@ -147,9 +182,6 @@ static int tas2552_hw_params(struct snd_pcm_substream *substream,
}
snd_soc_update_bits(codec, TAS2552_CFG_2, TAS2552_PLL_ENABLE,
TAS2552_PLL_ENABLE);
return 0;
}
......@@ -269,19 +301,10 @@ static const struct dev_pm_ops tas2552_pm = {
NULL)
};
static void tas2552_shutdown(struct snd_pcm_substream *substream,
struct snd_soc_dai *dai)
{
struct snd_soc_codec *codec = dai->codec;
snd_soc_update_bits(codec, TAS2552_CFG_2, TAS2552_PLL_ENABLE, 0);
}
static struct snd_soc_dai_ops tas2552_speaker_dai_ops = {
.hw_params = tas2552_hw_params,
.set_sysclk = tas2552_set_dai_sysclk,
.set_fmt = tas2552_set_dai_fmt,
.shutdown = tas2552_shutdown,
.digital_mute = tas2552_mute,
};
......@@ -294,7 +317,7 @@ static struct snd_soc_dai_driver tas2552_dai[] = {
{
.name = "tas2552-amplifier",
.playback = {
.stream_name = "Speaker",
.stream_name = "Playback",
.channels_min = 2,
.channels_max = 2,
.rates = SNDRV_PCM_RATE_8000_192000,
......@@ -312,6 +335,7 @@ static DECLARE_TLV_DB_SCALE(dac_tlv, -7, 100, 24);
static const struct snd_kcontrol_new tas2552_snd_controls[] = {
SOC_SINGLE_TLV("Speaker Driver Playback Volume",
TAS2552_PGA_GAIN, 0, 0x1f, 1, dac_tlv),
SOC_DAPM_SINGLE("Playback AMP", SND_SOC_NOPM, 0, 1, 0),
};
static const struct reg_default tas2552_init_regs[] = {
......@@ -321,6 +345,7 @@ static const struct reg_default tas2552_init_regs[] = {
static int tas2552_codec_probe(struct snd_soc_codec *codec)
{
struct tas2552_data *tas2552 = snd_soc_codec_get_drvdata(codec);
struct snd_soc_dapm_context *dapm = &codec->dapm;
int ret;
tas2552->codec = codec;
......@@ -362,9 +387,14 @@ static int tas2552_codec_probe(struct snd_soc_codec *codec)
goto patch_fail;
}
snd_soc_write(codec, TAS2552_CFG_2, TAS2552_CLASSD_EN |
TAS2552_BOOST_EN | TAS2552_APT_EN |
TAS2552_LIM_EN);
snd_soc_write(codec, TAS2552_CFG_2, TAS2552_BOOST_EN |
TAS2552_APT_EN | TAS2552_LIM_EN);
snd_soc_dapm_new_controls(dapm, tas2552_dapm_widgets,
ARRAY_SIZE(tas2552_dapm_widgets));
snd_soc_dapm_add_routes(dapm, tas2552_audio_map,
ARRAY_SIZE(tas2552_audio_map));
return 0;
patch_fail:
......
......@@ -167,13 +167,13 @@ struct aic31xx_priv {
struct regulator_bulk_data supplies[AIC31XX_NUM_SUPPLIES];
struct aic31xx_disable_nb disable_nb[AIC31XX_NUM_SUPPLIES];
unsigned int sysclk;
u8 p_div;
int rate_div_line;
};
struct aic31xx_rate_divs {
u32 mclk;
u32 mclk_p;
u32 rate;
u8 p_val;
u8 pll_j;
u16 pll_d;
u16 dosr;
......@@ -186,62 +186,51 @@ struct aic31xx_rate_divs {
/* ADC dividers can be disabled by cofiguring them to 0 */
static const struct aic31xx_rate_divs aic31xx_divs[] = {
/* mclk rate pll: p j d dosr ndac mdac aors nadc madc */
/* mclk/p rate pll: j d dosr ndac mdac aors nadc madc */
/* 8k rate */
{12000000, 8000, 1, 8, 1920, 128, 48, 2, 128, 48, 2},
{12000000, 8000, 1, 8, 1920, 128, 32, 3, 128, 32, 3},
{24000000, 8000, 2, 8, 1920, 128, 48, 2, 128, 48, 2},
{25000000, 8000, 2, 7, 8643, 128, 48, 2, 128, 48, 2},
{12000000, 8000, 8, 1920, 128, 48, 2, 128, 48, 2},
{12000000, 8000, 8, 1920, 128, 32, 3, 128, 32, 3},
{12500000, 8000, 7, 8643, 128, 48, 2, 128, 48, 2},
/* 11.025k rate */
{12000000, 11025, 1, 7, 5264, 128, 32, 2, 128, 32, 2},
{12000000, 11025, 1, 8, 4672, 128, 24, 3, 128, 24, 3},
{24000000, 11025, 2, 7, 5264, 128, 32, 2, 128, 32, 2},
{25000000, 11025, 2, 7, 2253, 128, 32, 2, 128, 32, 2},
{12000000, 11025, 7, 5264, 128, 32, 2, 128, 32, 2},
{12000000, 11025, 8, 4672, 128, 24, 3, 128, 24, 3},
{12500000, 11025, 7, 2253, 128, 32, 2, 128, 32, 2},
/* 16k rate */
{12000000, 16000, 1, 8, 1920, 128, 24, 2, 128, 24, 2},
{12000000, 16000, 1, 8, 1920, 128, 16, 3, 128, 16, 3},
{24000000, 16000, 2, 8, 1920, 128, 24, 2, 128, 24, 2},
{25000000, 16000, 2, 7, 8643, 128, 24, 2, 128, 24, 2},
{12000000, 16000, 8, 1920, 128, 24, 2, 128, 24, 2},
{12000000, 16000, 8, 1920, 128, 16, 3, 128, 16, 3},
{12500000, 16000, 7, 8643, 128, 24, 2, 128, 24, 2},
/* 22.05k rate */
{12000000, 22050, 1, 7, 5264, 128, 16, 2, 128, 16, 2},
{12000000, 22050, 1, 8, 4672, 128, 12, 3, 128, 12, 3},
{24000000, 22050, 2, 7, 5264, 128, 16, 2, 128, 16, 2},
{25000000, 22050, 2, 7, 2253, 128, 16, 2, 128, 16, 2},
{12000000, 22050, 7, 5264, 128, 16, 2, 128, 16, 2},
{12000000, 22050, 8, 4672, 128, 12, 3, 128, 12, 3},
{12500000, 22050, 7, 2253, 128, 16, 2, 128, 16, 2},
/* 32k rate */
{12000000, 32000, 1, 8, 1920, 128, 12, 2, 128, 12, 2},
{12000000, 32000, 1, 8, 1920, 128, 8, 3, 128, 8, 3},
{24000000, 32000, 2, 8, 1920, 128, 12, 2, 128, 12, 2},
{25000000, 32000, 2, 7, 8643, 128, 12, 2, 128, 12, 2},
{12000000, 32000, 8, 1920, 128, 12, 2, 128, 12, 2},
{12000000, 32000, 8, 1920, 128, 8, 3, 128, 8, 3},
{12500000, 32000, 7, 8643, 128, 12, 2, 128, 12, 2},
/* 44.1k rate */
{12000000, 44100, 1, 7, 5264, 128, 8, 2, 128, 8, 2},
{12000000, 44100, 1, 8, 4672, 128, 6, 3, 128, 6, 3},
{24000000, 44100, 2, 7, 5264, 128, 8, 2, 128, 8, 2},
{25000000, 44100, 2, 7, 2253, 128, 8, 2, 128, 8, 2},
{12000000, 44100, 7, 5264, 128, 8, 2, 128, 8, 2},
{12000000, 44100, 8, 4672, 128, 6, 3, 128, 6, 3},
{12500000, 44100, 7, 2253, 128, 8, 2, 128, 8, 2},
/* 48k rate */
{12000000, 48000, 1, 8, 1920, 128, 8, 2, 128, 8, 2},
{12000000, 48000, 1, 7, 6800, 96, 5, 4, 96, 5, 4},
{24000000, 48000, 2, 8, 1920, 128, 8, 2, 128, 8, 2},
{25000000, 48000, 2, 7, 8643, 128, 8, 2, 128, 8, 2},
{12000000, 48000, 8, 1920, 128, 8, 2, 128, 8, 2},
{12000000, 48000, 7, 6800, 96, 5, 4, 96, 5, 4},
{12500000, 48000, 7, 8643, 128, 8, 2, 128, 8, 2},
/* 88.2k rate */
{12000000, 88200, 1, 7, 5264, 64, 8, 2, 64, 8, 2},
{12000000, 88200, 1, 8, 4672, 64, 6, 3, 64, 6, 3},
{24000000, 88200, 2, 7, 5264, 64, 8, 2, 64, 8, 2},
{25000000, 88200, 2, 7, 2253, 64, 8, 2, 64, 8, 2},
{12000000, 88200, 7, 5264, 64, 8, 2, 64, 8, 2},
{12000000, 88200, 8, 4672, 64, 6, 3, 64, 6, 3},
{12500000, 88200, 7, 2253, 64, 8, 2, 64, 8, 2},
/* 96k rate */
{12000000, 96000, 1, 8, 1920, 64, 8, 2, 64, 8, 2},
{12000000, 96000, 1, 7, 6800, 48, 5, 4, 48, 5, 4},
{24000000, 96000, 2, 8, 1920, 64, 8, 2, 64, 8, 2},
{25000000, 96000, 2, 7, 8643, 64, 8, 2, 64, 8, 2},
{12000000, 96000, 8, 1920, 64, 8, 2, 64, 8, 2},
{12000000, 96000, 7, 6800, 48, 5, 4, 48, 5, 4},
{12500000, 96000, 7, 8643, 64, 8, 2, 64, 8, 2},
/* 176.4k rate */
{12000000, 176400, 1, 7, 5264, 32, 8, 2, 32, 8, 2},
{12000000, 176400, 1, 8, 4672, 32, 6, 3, 32, 6, 3},
{24000000, 176400, 2, 7, 5264, 32, 8, 2, 32, 8, 2},
{25000000, 176400, 2, 7, 2253, 32, 8, 2, 32, 8, 2},
{12000000, 176400, 7, 5264, 32, 8, 2, 32, 8, 2},
{12000000, 176400, 8, 4672, 32, 6, 3, 32, 6, 3},
{12500000, 176400, 7, 2253, 32, 8, 2, 32, 8, 2},
/* 192k rate */
{12000000, 192000, 1, 8, 1920, 32, 8, 2, 32, 8, 2},
{12000000, 192000, 1, 7, 6800, 24, 5, 4, 24, 5, 4},
{24000000, 192000, 2, 8, 1920, 32, 8, 2, 32, 8, 2},
{25000000, 192000, 2, 7, 8643, 32, 8, 2, 32, 8, 2},
{12000000, 192000, 8, 1920, 32, 8, 2, 32, 8, 2},
{12000000, 192000, 7, 6800, 24, 5, 4, 24, 5, 4},
{12500000, 192000, 7, 8643, 32, 8, 2, 32, 8, 2},
};
static const char * const ldac_in_text[] = {
......@@ -692,6 +681,7 @@ static int aic31xx_setup_pll(struct snd_soc_codec *codec,
{
struct aic31xx_priv *aic31xx = snd_soc_codec_get_drvdata(codec);
int bclk_score = snd_soc_params_to_frame_size(params);
int mclk_p = aic31xx->sysclk / aic31xx->p_div;
int bclk_n = 0;
int match = -1;
int i;
......@@ -704,7 +694,7 @@ static int aic31xx_setup_pll(struct snd_soc_codec *codec,
for (i = 0; i < ARRAY_SIZE(aic31xx_divs); i++) {
if (aic31xx_divs[i].rate == params_rate(params) &&
aic31xx_divs[i].mclk == aic31xx->sysclk) {
aic31xx_divs[i].mclk_p == mclk_p) {
int s = (aic31xx_divs[i].dosr * aic31xx_divs[i].mdac) %
snd_soc_params_to_frame_size(params);
int bn = (aic31xx_divs[i].dosr * aic31xx_divs[i].mdac) /
......@@ -738,7 +728,7 @@ static int aic31xx_setup_pll(struct snd_soc_codec *codec,
/* PLL configuration */
snd_soc_update_bits(codec, AIC31XX_PLLPR, AIC31XX_PLL_MASK,
(aic31xx_divs[i].p_val << 4) | 0x01);
(aic31xx->p_div << 4) | 0x01);
snd_soc_write(codec, AIC31XX_PLLJ, aic31xx_divs[i].pll_j);
snd_soc_write(codec, AIC31XX_PLLDMSB,
......@@ -772,7 +762,7 @@ static int aic31xx_setup_pll(struct snd_soc_codec *codec,
dev_dbg(codec->dev,
"pll %d.%04d/%d dosr %d n %d m %d aosr %d n %d m %d bclk_n %d\n",
aic31xx_divs[i].pll_j, aic31xx_divs[i].pll_d,
aic31xx_divs[i].p_val, aic31xx_divs[i].dosr,
aic31xx->p_div, aic31xx_divs[i].dosr,
aic31xx_divs[i].ndac, aic31xx_divs[i].mdac,
aic31xx_divs[i].aosr, aic31xx_divs[i].nadc,
aic31xx_divs[i].madc, bclk_n);
......@@ -840,7 +830,7 @@ static int aic31xx_set_dai_fmt(struct snd_soc_dai *codec_dai,
{
struct snd_soc_codec *codec = codec_dai->codec;
u8 iface_reg1 = 0;
u8 iface_reg3 = 0;
u8 iface_reg2 = 0;
u8 dsp_a_val = 0;
dev_dbg(codec->dev, "## %s: fmt = 0x%x\n", __func__, fmt);
......@@ -865,7 +855,7 @@ static int aic31xx_set_dai_fmt(struct snd_soc_dai *codec_dai,
/* NOTE: BCLKINV bit value 1 equas NB and 0 equals IB */
switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
case SND_SOC_DAIFMT_NB_NF:
iface_reg3 |= AIC31XX_BCLKINV_MASK;
iface_reg2 |= AIC31XX_BCLKINV_MASK;
break;
case SND_SOC_DAIFMT_IB_NF:
break;
......@@ -897,7 +887,7 @@ static int aic31xx_set_dai_fmt(struct snd_soc_dai *codec_dai,
dsp_a_val);
snd_soc_update_bits(codec, AIC31XX_IFACE2,
AIC31XX_BCLKINV_MASK,
iface_reg3);
iface_reg2);
return 0;
}
......@@ -912,7 +902,16 @@ static int aic31xx_set_dai_sysclk(struct snd_soc_dai *codec_dai,
dev_dbg(codec->dev, "## %s: clk_id = %d, freq = %d, dir = %d\n",
__func__, clk_id, freq, dir);
for (i = 0; aic31xx_divs[i].mclk != freq; i++) {
for (i = 1; freq/i > 20000000 && i < 8; i++)
;
if (freq/i > 20000000) {
dev_err(aic31xx->dev, "%s: Too high mclk frequency %u\n",
__func__, freq);
return -EINVAL;
}
aic31xx->p_div = i;
for (i = 0; aic31xx_divs[i].mclk_p != freq/aic31xx->p_div; i++) {
if (i == ARRAY_SIZE(aic31xx_divs)) {
dev_err(aic31xx->dev, "%s: Unsupported frequency %d\n",
__func__, freq);
......
......@@ -18,7 +18,8 @@
#define AIC31XX_RATES SNDRV_PCM_RATE_8000_192000
#define AIC31XX_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE \
| SNDRV_PCM_FMTBIT_S24_3LE | SNDRV_PCM_FMTBIT_S32_LE)
| SNDRV_PCM_FMTBIT_S24_3LE | SNDRV_PCM_FMTBIT_S24_LE \
| SNDRV_PCM_FMTBIT_S32_LE)
#define AIC31XX_STEREO_CLASS_D_BIT 0x1
......
......@@ -1121,6 +1121,7 @@ static int aic3x_regulator_event(struct notifier_block *nb,
static int aic3x_set_power(struct snd_soc_codec *codec, int power)
{
struct aic3x_priv *aic3x = snd_soc_codec_get_drvdata(codec);
unsigned int pll_c, pll_d;
int ret;
if (power) {
......@@ -1138,6 +1139,18 @@ static int aic3x_set_power(struct snd_soc_codec *codec, int power)
/* Sync reg_cache with the hardware */
regcache_cache_only(aic3x->regmap, false);
regcache_sync(aic3x->regmap);
/* Rewrite paired PLL D registers in case cached sync skipped
* writing one of them and thus caused other one also not
* being written
*/
pll_c = snd_soc_read(codec, AIC3X_PLL_PROGC_REG);
pll_d = snd_soc_read(codec, AIC3X_PLL_PROGD_REG);
if (pll_c == aic3x_reg[AIC3X_PLL_PROGC_REG].def ||
pll_d == aic3x_reg[AIC3X_PLL_PROGD_REG].def) {
snd_soc_write(codec, AIC3X_PLL_PROGC_REG, pll_c);
snd_soc_write(codec, AIC3X_PLL_PROGD_REG, pll_d);
}
} else {
/*
* Do soft reset to this codec instance in order to clear
......
......@@ -413,7 +413,6 @@ static int wm8741_resume(struct snd_soc_codec *codec)
return 0;
}
#else
#define wm8741_suspend NULL
#define wm8741_resume NULL
#endif
......
......@@ -42,6 +42,7 @@
struct tegra_max98090 {
struct tegra_asoc_utils_data util_data;
int gpio_hp_det;
int gpio_mic_det;
};
static int tegra_max98090_asoc_hw_params(struct snd_pcm_substream *substream,
......@@ -112,6 +113,22 @@ static struct snd_soc_jack_gpio tegra_max98090_hp_jack_gpio = {
.invert = 1,
};
static struct snd_soc_jack tegra_max98090_mic_jack;
static struct snd_soc_jack_pin tegra_max98090_mic_jack_pins[] = {
{
.pin = "Mic Jack",
.mask = SND_JACK_MICROPHONE,
},
};
static struct snd_soc_jack_gpio tegra_max98090_mic_jack_gpio = {
.name = "Mic detection",
.report = SND_JACK_MICROPHONE,
.debounce_time = 150,
.invert = 1,
};
static const struct snd_soc_dapm_widget tegra_max98090_dapm_widgets[] = {
SND_SOC_DAPM_HP("Headphones", NULL),
SND_SOC_DAPM_SPK("Speakers", NULL),
......@@ -141,6 +158,19 @@ static int tegra_max98090_asoc_init(struct snd_soc_pcm_runtime *rtd)
&tegra_max98090_hp_jack_gpio);
}
if (gpio_is_valid(machine->gpio_mic_det)) {
snd_soc_jack_new(codec, "Mic Jack", SND_JACK_MICROPHONE,
&tegra_max98090_mic_jack);
snd_soc_jack_add_pins(&tegra_max98090_mic_jack,
ARRAY_SIZE(tegra_max98090_mic_jack_pins),
tegra_max98090_mic_jack_pins);
tegra_max98090_mic_jack_gpio.gpio = machine->gpio_mic_det;
snd_soc_jack_add_gpios(&tegra_max98090_mic_jack,
1,
&tegra_max98090_mic_jack_gpio);
}
return 0;
}
......@@ -153,6 +183,11 @@ static int tegra_max98090_card_remove(struct snd_soc_card *card)
&tegra_max98090_hp_jack_gpio);
}
if (gpio_is_valid(machine->gpio_mic_det)) {
snd_soc_jack_free_gpios(&tegra_max98090_mic_jack, 1,
&tegra_max98090_mic_jack_gpio);
}
return 0;
}
......@@ -201,6 +236,11 @@ static int tegra_max98090_probe(struct platform_device *pdev)
if (machine->gpio_hp_det == -EPROBE_DEFER)
return -EPROBE_DEFER;
machine->gpio_mic_det =
of_get_named_gpio(np, "nvidia,mic-det-gpios", 0);
if (machine->gpio_mic_det == -EPROBE_DEFER)
return -EPROBE_DEFER;
ret = snd_soc_of_parse_card_name(card, "nvidia,model");
if (ret)
goto err;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment