summaryrefslogtreecommitdiff
path: root/sound/soc/codecs/max98090.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/soc/codecs/max98090.c')
-rw-r--r--sound/soc/codecs/max98090.c202
1 files changed, 108 insertions, 94 deletions
diff --git a/sound/soc/codecs/max98090.c b/sound/soc/codecs/max98090.c
index 51f9b3d16b41..98c6e104357c 100644
--- a/sound/soc/codecs/max98090.c
+++ b/sound/soc/codecs/max98090.c
@@ -336,6 +336,7 @@ static bool max98090_readable_register(struct device *dev, unsigned int reg)
case M98090_REG_RECORD_TDM_SLOT:
case M98090_REG_SAMPLE_RATE:
case M98090_REG_DMIC34_BIQUAD_BASE ... M98090_REG_DMIC34_BIQUAD_BASE + 0x0E:
+ case M98090_REG_REVISION_ID:
return true;
default:
return false;
@@ -512,65 +513,75 @@ static const char *max98090_perf_pwr_text[] =
static const char *max98090_pwr_perf_text[] =
{ "Low Power", "High Performance" };
-static const struct soc_enum max98090_vcmbandgap_enum =
- SOC_ENUM_SINGLE(M98090_REG_BIAS_CONTROL, M98090_VCM_MODE_SHIFT,
- ARRAY_SIZE(max98090_pwr_perf_text), max98090_pwr_perf_text);
+static SOC_ENUM_SINGLE_DECL(max98090_vcmbandgap_enum,
+ M98090_REG_BIAS_CONTROL,
+ M98090_VCM_MODE_SHIFT,
+ max98090_pwr_perf_text);
static const char *max98090_osr128_text[] = { "64*fs", "128*fs" };
-static const struct soc_enum max98090_osr128_enum =
- SOC_ENUM_SINGLE(M98090_REG_ADC_CONTROL, M98090_OSR128_SHIFT,
- ARRAY_SIZE(max98090_osr128_text), max98090_osr128_text);
+static SOC_ENUM_SINGLE_DECL(max98090_osr128_enum,
+ M98090_REG_ADC_CONTROL,
+ M98090_OSR128_SHIFT,
+ max98090_osr128_text);
static const char *max98090_mode_text[] = { "Voice", "Music" };
-static const struct soc_enum max98090_mode_enum =
- SOC_ENUM_SINGLE(M98090_REG_FILTER_CONFIG, M98090_MODE_SHIFT,
- ARRAY_SIZE(max98090_mode_text), max98090_mode_text);
+static SOC_ENUM_SINGLE_DECL(max98090_mode_enum,
+ M98090_REG_FILTER_CONFIG,
+ M98090_MODE_SHIFT,
+ max98090_mode_text);
-static const struct soc_enum max98090_filter_dmic34mode_enum =
- SOC_ENUM_SINGLE(M98090_REG_FILTER_CONFIG,
- M98090_FLT_DMIC34MODE_SHIFT,
- ARRAY_SIZE(max98090_mode_text), max98090_mode_text);
+static SOC_ENUM_SINGLE_DECL(max98090_filter_dmic34mode_enum,
+ M98090_REG_FILTER_CONFIG,
+ M98090_FLT_DMIC34MODE_SHIFT,
+ max98090_mode_text);
static const char *max98090_drcatk_text[] =
{ "0.5ms", "1ms", "5ms", "10ms", "25ms", "50ms", "100ms", "200ms" };
-static const struct soc_enum max98090_drcatk_enum =
- SOC_ENUM_SINGLE(M98090_REG_DRC_TIMING, M98090_DRCATK_SHIFT,
- ARRAY_SIZE(max98090_drcatk_text), max98090_drcatk_text);
+static SOC_ENUM_SINGLE_DECL(max98090_drcatk_enum,
+ M98090_REG_DRC_TIMING,
+ M98090_DRCATK_SHIFT,
+ max98090_drcatk_text);
static const char *max98090_drcrls_text[] =
{ "8s", "4s", "2s", "1s", "0.5s", "0.25s", "0.125s", "0.0625s" };
-static const struct soc_enum max98090_drcrls_enum =
- SOC_ENUM_SINGLE(M98090_REG_DRC_TIMING, M98090_DRCRLS_SHIFT,
- ARRAY_SIZE(max98090_drcrls_text), max98090_drcrls_text);
+static SOC_ENUM_SINGLE_DECL(max98090_drcrls_enum,
+ M98090_REG_DRC_TIMING,
+ M98090_DRCRLS_SHIFT,
+ max98090_drcrls_text);
static const char *max98090_alccmp_text[] =
{ "1:1", "1:1.5", "1:2", "1:4", "1:INF" };
-static const struct soc_enum max98090_alccmp_enum =
- SOC_ENUM_SINGLE(M98090_REG_DRC_COMPRESSOR, M98090_DRCCMP_SHIFT,
- ARRAY_SIZE(max98090_alccmp_text), max98090_alccmp_text);
+static SOC_ENUM_SINGLE_DECL(max98090_alccmp_enum,
+ M98090_REG_DRC_COMPRESSOR,
+ M98090_DRCCMP_SHIFT,
+ max98090_alccmp_text);
static const char *max98090_drcexp_text[] = { "1:1", "2:1", "3:1" };
-static const struct soc_enum max98090_drcexp_enum =
- SOC_ENUM_SINGLE(M98090_REG_DRC_EXPANDER, M98090_DRCEXP_SHIFT,
- ARRAY_SIZE(max98090_drcexp_text), max98090_drcexp_text);
+static SOC_ENUM_SINGLE_DECL(max98090_drcexp_enum,
+ M98090_REG_DRC_EXPANDER,
+ M98090_DRCEXP_SHIFT,
+ max98090_drcexp_text);
-static const struct soc_enum max98090_dac_perfmode_enum =
- SOC_ENUM_SINGLE(M98090_REG_DAC_CONTROL, M98090_PERFMODE_SHIFT,
- ARRAY_SIZE(max98090_perf_pwr_text), max98090_perf_pwr_text);
+static SOC_ENUM_SINGLE_DECL(max98090_dac_perfmode_enum,
+ M98090_REG_DAC_CONTROL,
+ M98090_PERFMODE_SHIFT,
+ max98090_perf_pwr_text);
-static const struct soc_enum max98090_dachp_enum =
- SOC_ENUM_SINGLE(M98090_REG_DAC_CONTROL, M98090_DACHP_SHIFT,
- ARRAY_SIZE(max98090_pwr_perf_text), max98090_pwr_perf_text);
+static SOC_ENUM_SINGLE_DECL(max98090_dachp_enum,
+ M98090_REG_DAC_CONTROL,
+ M98090_DACHP_SHIFT,
+ max98090_pwr_perf_text);
-static const struct soc_enum max98090_adchp_enum =
- SOC_ENUM_SINGLE(M98090_REG_ADC_CONTROL, M98090_ADCHP_SHIFT,
- ARRAY_SIZE(max98090_pwr_perf_text), max98090_pwr_perf_text);
+static SOC_ENUM_SINGLE_DECL(max98090_adchp_enum,
+ M98090_REG_ADC_CONTROL,
+ M98090_ADCHP_SHIFT,
+ max98090_pwr_perf_text);
static const struct snd_kcontrol_new max98090_snd_controls[] = {
SOC_ENUM("MIC Bias VCM Bandgap", max98090_vcmbandgap_enum),
@@ -841,39 +852,42 @@ static int max98090_micinput_event(struct snd_soc_dapm_widget *w,
static const char *mic1_mux_text[] = { "IN12", "IN56" };
-static const struct soc_enum mic1_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_INPUT_MODE, M98090_EXTMIC1_SHIFT,
- ARRAY_SIZE(mic1_mux_text), mic1_mux_text);
+static SOC_ENUM_SINGLE_DECL(mic1_mux_enum,
+ M98090_REG_INPUT_MODE,
+ M98090_EXTMIC1_SHIFT,
+ mic1_mux_text);
static const struct snd_kcontrol_new max98090_mic1_mux =
SOC_DAPM_ENUM("MIC1 Mux", mic1_mux_enum);
static const char *mic2_mux_text[] = { "IN34", "IN56" };
-static const struct soc_enum mic2_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_INPUT_MODE, M98090_EXTMIC2_SHIFT,
- ARRAY_SIZE(mic2_mux_text), mic2_mux_text);
+static SOC_ENUM_SINGLE_DECL(mic2_mux_enum,
+ M98090_REG_INPUT_MODE,
+ M98090_EXTMIC2_SHIFT,
+ mic2_mux_text);
static const struct snd_kcontrol_new max98090_mic2_mux =
SOC_DAPM_ENUM("MIC2 Mux", mic2_mux_enum);
static const char *dmic_mux_text[] = { "ADC", "DMIC" };
-static const struct soc_enum dmic_mux_enum =
- SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(dmic_mux_text), dmic_mux_text);
+static SOC_ENUM_SINGLE_VIRT_DECL(dmic_mux_enum, dmic_mux_text);
static const struct snd_kcontrol_new max98090_dmic_mux =
SOC_DAPM_ENUM_VIRT("DMIC Mux", dmic_mux_enum);
static const char *max98090_micpre_text[] = { "Off", "On" };
-static const struct soc_enum max98090_pa1en_enum =
- SOC_ENUM_SINGLE(M98090_REG_MIC1_INPUT_LEVEL, M98090_MIC_PA1EN_SHIFT,
- ARRAY_SIZE(max98090_micpre_text), max98090_micpre_text);
+static SOC_ENUM_SINGLE_DECL(max98090_pa1en_enum,
+ M98090_REG_MIC1_INPUT_LEVEL,
+ M98090_MIC_PA1EN_SHIFT,
+ max98090_micpre_text);
-static const struct soc_enum max98090_pa2en_enum =
- SOC_ENUM_SINGLE(M98090_REG_MIC2_INPUT_LEVEL, M98090_MIC_PA2EN_SHIFT,
- ARRAY_SIZE(max98090_micpre_text), max98090_micpre_text);
+static SOC_ENUM_SINGLE_DECL(max98090_pa2en_enum,
+ M98090_REG_MIC2_INPUT_LEVEL,
+ M98090_MIC_PA2EN_SHIFT,
+ max98090_micpre_text);
/* LINEA mixer switch */
static const struct snd_kcontrol_new max98090_linea_mixer_controls[] = {
@@ -937,13 +951,15 @@ static const struct snd_kcontrol_new max98090_right_adc_mixer_controls[] = {
static const char *lten_mux_text[] = { "Normal", "Loopthrough" };
-static const struct soc_enum ltenl_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_IO_CONFIGURATION, M98090_LTEN_SHIFT,
- ARRAY_SIZE(lten_mux_text), lten_mux_text);
+static SOC_ENUM_SINGLE_DECL(ltenl_mux_enum,
+ M98090_REG_IO_CONFIGURATION,
+ M98090_LTEN_SHIFT,
+ lten_mux_text);
-static const struct soc_enum ltenr_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_IO_CONFIGURATION, M98090_LTEN_SHIFT,
- ARRAY_SIZE(lten_mux_text), lten_mux_text);
+static SOC_ENUM_SINGLE_DECL(ltenr_mux_enum,
+ M98090_REG_IO_CONFIGURATION,
+ M98090_LTEN_SHIFT,
+ lten_mux_text);
static const struct snd_kcontrol_new max98090_ltenl_mux =
SOC_DAPM_ENUM("LTENL Mux", ltenl_mux_enum);
@@ -953,13 +969,15 @@ static const struct snd_kcontrol_new max98090_ltenr_mux =
static const char *lben_mux_text[] = { "Normal", "Loopback" };
-static const struct soc_enum lbenl_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_IO_CONFIGURATION, M98090_LBEN_SHIFT,
- ARRAY_SIZE(lben_mux_text), lben_mux_text);
+static SOC_ENUM_SINGLE_DECL(lbenl_mux_enum,
+ M98090_REG_IO_CONFIGURATION,
+ M98090_LBEN_SHIFT,
+ lben_mux_text);
-static const struct soc_enum lbenr_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_IO_CONFIGURATION, M98090_LBEN_SHIFT,
- ARRAY_SIZE(lben_mux_text), lben_mux_text);
+static SOC_ENUM_SINGLE_DECL(lbenr_mux_enum,
+ M98090_REG_IO_CONFIGURATION,
+ M98090_LBEN_SHIFT,
+ lben_mux_text);
static const struct snd_kcontrol_new max98090_lbenl_mux =
SOC_DAPM_ENUM("LBENL Mux", lbenl_mux_enum);
@@ -971,13 +989,15 @@ static const char *stenl_mux_text[] = { "Normal", "Sidetone Left" };
static const char *stenr_mux_text[] = { "Normal", "Sidetone Right" };
-static const struct soc_enum stenl_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_ADC_SIDETONE, M98090_DSTSL_SHIFT,
- ARRAY_SIZE(stenl_mux_text), stenl_mux_text);
+static SOC_ENUM_SINGLE_DECL(stenl_mux_enum,
+ M98090_REG_ADC_SIDETONE,
+ M98090_DSTSL_SHIFT,
+ stenl_mux_text);
-static const struct soc_enum stenr_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_ADC_SIDETONE, M98090_DSTSR_SHIFT,
- ARRAY_SIZE(stenr_mux_text), stenr_mux_text);
+static SOC_ENUM_SINGLE_DECL(stenr_mux_enum,
+ M98090_REG_ADC_SIDETONE,
+ M98090_DSTSR_SHIFT,
+ stenr_mux_text);
static const struct snd_kcontrol_new max98090_stenl_mux =
SOC_DAPM_ENUM("STENL Mux", stenl_mux_enum);
@@ -1085,9 +1105,10 @@ static const struct snd_kcontrol_new max98090_right_rcv_mixer_controls[] = {
static const char *linmod_mux_text[] = { "Left Only", "Left and Right" };
-static const struct soc_enum linmod_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_LOUTR_MIXER, M98090_LINMOD_SHIFT,
- ARRAY_SIZE(linmod_mux_text), linmod_mux_text);
+static SOC_ENUM_SINGLE_DECL(linmod_mux_enum,
+ M98090_REG_LOUTR_MIXER,
+ M98090_LINMOD_SHIFT,
+ linmod_mux_text);
static const struct snd_kcontrol_new max98090_linmod_mux =
SOC_DAPM_ENUM("LINMOD Mux", linmod_mux_enum);
@@ -1097,16 +1118,18 @@ static const char *mixhpsel_mux_text[] = { "DAC Only", "HP Mixer" };
/*
* This is a mux as it selects the HP output, but to DAPM it is a Mixer enable
*/
-static const struct soc_enum mixhplsel_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_HP_CONTROL, M98090_MIXHPLSEL_SHIFT,
- ARRAY_SIZE(mixhpsel_mux_text), mixhpsel_mux_text);
+static SOC_ENUM_SINGLE_DECL(mixhplsel_mux_enum,
+ M98090_REG_HP_CONTROL,
+ M98090_MIXHPLSEL_SHIFT,
+ mixhpsel_mux_text);
static const struct snd_kcontrol_new max98090_mixhplsel_mux =
SOC_DAPM_ENUM("MIXHPLSEL Mux", mixhplsel_mux_enum);
-static const struct soc_enum mixhprsel_mux_enum =
- SOC_ENUM_SINGLE(M98090_REG_HP_CONTROL, M98090_MIXHPRSEL_SHIFT,
- ARRAY_SIZE(mixhpsel_mux_text), mixhpsel_mux_text);
+static SOC_ENUM_SINGLE_DECL(mixhprsel_mux_enum,
+ M98090_REG_HP_CONTROL,
+ M98090_MIXHPRSEL_SHIFT,
+ mixhpsel_mux_text);
static const struct snd_kcontrol_new max98090_mixhprsel_mux =
SOC_DAPM_ENUM("MIXHPRSEL Mux", mixhprsel_mux_enum);
@@ -1769,16 +1792,6 @@ static int max98090_set_bias_level(struct snd_soc_codec *codec,
switch (level) {
case SND_SOC_BIAS_ON:
- if (codec->dapm.bias_level == SND_SOC_BIAS_OFF) {
- ret = regcache_sync(max98090->regmap);
-
- if (ret != 0) {
- dev_err(codec->dev,
- "Failed to sync cache: %d\n", ret);
- return ret;
- }
- }
-
if (max98090->jack_state == M98090_JACK_STATE_HEADSET) {
/*
* Set to normal bias level.
@@ -1792,6 +1805,16 @@ static int max98090_set_bias_level(struct snd_soc_codec *codec,
break;
case SND_SOC_BIAS_STANDBY:
+ if (codec->dapm.bias_level == SND_SOC_BIAS_OFF) {
+ ret = regcache_sync(max98090->regmap);
+ if (ret != 0) {
+ dev_err(codec->dev,
+ "Failed to sync cache: %d\n", ret);
+ return ret;
+ }
+ }
+ break;
+
case SND_SOC_BIAS_OFF:
/* Set internal pull-up to lowest power mode */
snd_soc_update_bits(codec, M98090_REG_JACK_DETECT,
@@ -2195,14 +2218,6 @@ static int max98090_probe(struct snd_soc_codec *codec)
max98090->codec = codec;
- codec->control_data = max98090->regmap;
-
- ret = snd_soc_codec_set_cache_io(codec, 8, 8, SND_SOC_REGMAP);
- if (ret != 0) {
- dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret);
- return ret;
- }
-
/* Reset the codec, the DSP core, and disable all interrupts */
max98090_reset(max98090);
@@ -2328,7 +2343,6 @@ static int max98090_i2c_probe(struct i2c_client *i2c,
max98090->devtype = id->driver_data;
i2c_set_clientdata(i2c, max98090);
- max98090->control_data = i2c;
max98090->pdata = i2c->dev.platform_data;
max98090->irq = i2c->irq;