diff options
Diffstat (limited to 'sound')
-rw-r--r-- | sound/core/vmaster.c | 1 | ||||
-rw-r--r-- | sound/last.c | 2 | ||||
-rw-r--r-- | sound/pci/hda/patch_conexant.c | 35 | ||||
-rw-r--r-- | sound/pci/hda/patch_realtek.c | 50 | ||||
-rw-r--r-- | sound/pci/hda/patch_sigmatel.c | 5 | ||||
-rw-r--r-- | sound/soc/codecs/Kconfig | 3 | ||||
-rw-r--r-- | sound/soc/codecs/cs42l73.c | 2 | ||||
-rw-r--r-- | sound/soc/codecs/twl6040.c | 3 | ||||
-rw-r--r-- | sound/soc/codecs/wm8994.c | 276 | ||||
-rw-r--r-- | sound/soc/omap/Kconfig | 2 | ||||
-rw-r--r-- | sound/soc/sh/fsi.c | 7 | ||||
-rw-r--r-- | sound/soc/soc-core.c | 1 | ||||
-rw-r--r-- | sound/soc/soc-dapm.c | 2 |
13 files changed, 313 insertions, 76 deletions
diff --git a/sound/core/vmaster.c b/sound/core/vmaster.c index 14a286a7bf2..857586135d1 100644 --- a/sound/core/vmaster.c +++ b/sound/core/vmaster.c @@ -419,6 +419,7 @@ EXPORT_SYMBOL(snd_ctl_make_virtual_master); * snd_ctl_add_vmaster_hook - Add a hook to a vmaster control * @kcontrol: vmaster kctl element * @hook: the hook function + * @private_data: the private_data pointer to be saved * * Adds the given hook to the vmaster control element so that it's called * at each time when the value is changed. diff --git a/sound/last.c b/sound/last.c index bdd0857b887..7ffc182e084 100644 --- a/sound/last.c +++ b/sound/last.c @@ -38,4 +38,4 @@ static int __init alsa_sound_last_init(void) return 0; } -__initcall(alsa_sound_last_init); +late_initcall_sync(alsa_sound_last_init); diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c index a36488d94aa..d906c5b74cf 100644 --- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c @@ -3971,9 +3971,14 @@ static void cx_auto_init_output(struct hda_codec *codec) int i; mute_outputs(codec, spec->multiout.num_dacs, spec->multiout.dac_nids); - for (i = 0; i < cfg->hp_outs; i++) + for (i = 0; i < cfg->hp_outs; i++) { + unsigned int val = PIN_OUT; + if (snd_hda_query_pin_caps(codec, cfg->hp_pins[i]) & + AC_PINCAP_HP_DRV) + val |= AC_PINCTL_HP_EN; snd_hda_codec_write(codec, cfg->hp_pins[i], 0, - AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_HP); + AC_VERB_SET_PIN_WIDGET_CONTROL, val); + } mute_outputs(codec, cfg->hp_outs, cfg->hp_pins); mute_outputs(codec, cfg->line_outs, cfg->line_out_pins); mute_outputs(codec, cfg->speaker_outs, cfg->speaker_pins); @@ -4391,8 +4396,10 @@ static void apply_pin_fixup(struct hda_codec *codec, enum { CXT_PINCFG_LENOVO_X200, + CXT_PINCFG_LENOVO_TP410, }; +/* ThinkPad X200 & co with cxt5051 */ static const struct cxt_pincfg cxt_pincfg_lenovo_x200[] = { { 0x16, 0x042140ff }, /* HP (seq# overridden) */ { 0x17, 0x21a11000 }, /* dock-mic */ @@ -4401,15 +4408,33 @@ static const struct cxt_pincfg cxt_pincfg_lenovo_x200[] = { {} }; +/* ThinkPad 410/420/510/520, X201 & co with cxt5066 */ +static const struct cxt_pincfg cxt_pincfg_lenovo_tp410[] = { + { 0x19, 0x042110ff }, /* HP (seq# overridden) */ + { 0x1a, 0x21a190f0 }, /* dock-mic */ + { 0x1c, 0x212140ff }, /* dock-HP */ + {} +}; + static const struct cxt_pincfg *cxt_pincfg_tbl[] = { [CXT_PINCFG_LENOVO_X200] = cxt_pincfg_lenovo_x200, + [CXT_PINCFG_LENOVO_TP410] = cxt_pincfg_lenovo_tp410, }; -static const struct snd_pci_quirk cxt_fixups[] = { +static const struct snd_pci_quirk cxt5051_fixups[] = { SND_PCI_QUIRK(0x17aa, 0x20f2, "Lenovo X200", CXT_PINCFG_LENOVO_X200), {} }; +static const struct snd_pci_quirk cxt5066_fixups[] = { + SND_PCI_QUIRK(0x17aa, 0x20f2, "Lenovo T400", CXT_PINCFG_LENOVO_TP410), + SND_PCI_QUIRK(0x17aa, 0x215e, "Lenovo T410", CXT_PINCFG_LENOVO_TP410), + SND_PCI_QUIRK(0x17aa, 0x215f, "Lenovo T510", CXT_PINCFG_LENOVO_TP410), + SND_PCI_QUIRK(0x17aa, 0x21ce, "Lenovo T420", CXT_PINCFG_LENOVO_TP410), + SND_PCI_QUIRK(0x17aa, 0x21cf, "Lenovo T520", CXT_PINCFG_LENOVO_TP410), + {} +}; + /* add "fake" mute amp-caps to DACs on cx5051 so that mixer mute switches * can be created (bko#42825) */ @@ -4446,13 +4471,13 @@ static int patch_conexant_auto(struct hda_codec *codec) case 0x14f15051: add_cx5051_fake_mutes(codec); codec->pin_amp_workaround = 1; + apply_pin_fixup(codec, cxt5051_fixups, cxt_pincfg_tbl); break; default: codec->pin_amp_workaround = 1; + apply_pin_fixup(codec, cxt5066_fixups, cxt_pincfg_tbl); } - apply_pin_fixup(codec, cxt_fixups, cxt_pincfg_tbl); - /* Show mute-led control only on HP laptops * This is a sort of white-list: on HP laptops, EAPD corresponds * only to the mute-LED without actualy amp function. Meanwhile, diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 2508f8109f1..818f90bc7d5 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -1445,6 +1445,13 @@ enum { ALC_FIXUP_ACT_BUILD, }; +static void alc_apply_pincfgs(struct hda_codec *codec, + const struct alc_pincfg *cfg) +{ + for (; cfg->nid; cfg++) + snd_hda_codec_set_pincfg(codec, cfg->nid, cfg->val); +} + static void alc_apply_fixup(struct hda_codec *codec, int action) { struct alc_spec *spec = codec->spec; @@ -1478,9 +1485,7 @@ static void alc_apply_fixup(struct hda_codec *codec, int action) snd_printdd(KERN_INFO "hda_codec: %s: " "Apply pincfg for %s\n", codec->chip_name, modelname); - for (; cfg->nid; cfg++) - snd_hda_codec_set_pincfg(codec, cfg->nid, - cfg->val); + alc_apply_pincfgs(codec, cfg); break; case ALC_FIXUP_VERBS: if (action != ALC_FIXUP_ACT_PROBE || !fix->v.verbs) @@ -4861,6 +4866,7 @@ enum { ALC260_FIXUP_GPIO1_TOGGLE, ALC260_FIXUP_REPLACER, ALC260_FIXUP_HP_B1900, + ALC260_FIXUP_KN1, }; static void alc260_gpio1_automute(struct hda_codec *codec) @@ -4888,6 +4894,36 @@ static void alc260_fixup_gpio1_toggle(struct hda_codec *codec, } } +static void alc260_fixup_kn1(struct hda_codec *codec, + const struct alc_fixup *fix, int action) +{ + struct alc_spec *spec = codec->spec; + static const struct alc_pincfg pincfgs[] = { + { 0x0f, 0x02214000 }, /* HP/speaker */ + { 0x12, 0x90a60160 }, /* int mic */ + { 0x13, 0x02a19000 }, /* ext mic */ + { 0x18, 0x01446000 }, /* SPDIF out */ + /* disable bogus I/O pins */ + { 0x10, 0x411111f0 }, + { 0x11, 0x411111f0 }, + { 0x14, 0x411111f0 }, + { 0x15, 0x411111f0 }, + { 0x16, 0x411111f0 }, + { 0x17, 0x411111f0 }, + { 0x19, 0x411111f0 }, + { } + }; + + switch (action) { + case ALC_FIXUP_ACT_PRE_PROBE: + alc_apply_pincfgs(codec, pincfgs); + break; + case ALC_FIXUP_ACT_PROBE: + spec->init_amp = ALC_INIT_NONE; + break; + } +} + static const struct alc_fixup alc260_fixups[] = { [ALC260_FIXUP_HP_DC5750] = { .type = ALC_FIXUP_PINS, @@ -4938,7 +4974,11 @@ static const struct alc_fixup alc260_fixups[] = { .v.func = alc260_fixup_gpio1_toggle, .chained = true, .chain_id = ALC260_FIXUP_COEF, - } + }, + [ALC260_FIXUP_KN1] = { + .type = ALC_FIXUP_FUNC, + .v.func = alc260_fixup_kn1, + }, }; static const struct snd_pci_quirk alc260_fixup_tbl[] = { @@ -4948,6 +4988,7 @@ static const struct snd_pci_quirk alc260_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x280a, "HP dc5750", ALC260_FIXUP_HP_DC5750), SND_PCI_QUIRK(0x103c, 0x30ba, "HP Presario B1900", ALC260_FIXUP_HP_B1900), SND_PCI_QUIRK(0x1509, 0x4540, "Favorit 100XS", ALC260_FIXUP_GPIO1), + SND_PCI_QUIRK(0x152d, 0x0729, "Quanta KN1", ALC260_FIXUP_KN1), SND_PCI_QUIRK(0x161f, 0x2057, "Replacer 672V", ALC260_FIXUP_REPLACER), SND_PCI_QUIRK(0x1631, 0xc017, "PB V7900", ALC260_FIXUP_COEF), {} @@ -6068,6 +6109,7 @@ static const struct alc_fixup alc269_fixups[] = { static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x1586, "HP", ALC269_FIXUP_MIC2_MUTE_LED), + SND_PCI_QUIRK(0x1043, 0x1427, "Asus Zenbook UX31E", ALC269VB_FIXUP_DMIC), SND_PCI_QUIRK(0x1043, 0x1a13, "Asus G73Jw", ALC269_FIXUP_ASUS_G73JW), SND_PCI_QUIRK(0x1043, 0x16e3, "ASUS UX50", ALC269_FIXUP_STEREO_DMIC), SND_PCI_QUIRK(0x1043, 0x831a, "ASUS P901", ALC269_FIXUP_STEREO_DMIC), diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index 33a9946b492..4742cac26aa 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -5063,12 +5063,11 @@ static void stac92xx_update_led_status(struct hda_codec *codec, int enabled) if (spec->gpio_led_polarity) muted = !muted; - /*polarity defines *not* muted state level*/ if (!spec->vref_mute_led_nid) { if (muted) - spec->gpio_data &= ~spec->gpio_led; /* orange */ + spec->gpio_data |= spec->gpio_led; else - spec->gpio_data |= spec->gpio_led; /* white */ + spec->gpio_data &= ~spec->gpio_led; stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir, spec->gpio_data); } else { diff --git a/sound/soc/codecs/Kconfig b/sound/soc/codecs/Kconfig index 6508e8b790b..59d8efaa17e 100644 --- a/sound/soc/codecs/Kconfig +++ b/sound/soc/codecs/Kconfig @@ -57,7 +57,7 @@ config SND_SOC_ALL_CODECS select SND_SOC_TPA6130A2 if I2C select SND_SOC_TLV320DAC33 if I2C select SND_SOC_TWL4030 if TWL4030_CORE - select SND_SOC_TWL6040 if TWL4030_CORE + select SND_SOC_TWL6040 if TWL6040_CORE select SND_SOC_UDA134X select SND_SOC_UDA1380 if I2C select SND_SOC_WL1273 if MFD_WL1273_CORE @@ -276,7 +276,6 @@ config SND_SOC_TWL4030 tristate config SND_SOC_TWL6040 - select TWL6040_CORE tristate config SND_SOC_UDA134X diff --git a/sound/soc/codecs/cs42l73.c b/sound/soc/codecs/cs42l73.c index 78979b3e0e9..07c44b71f09 100644 --- a/sound/soc/codecs/cs42l73.c +++ b/sound/soc/codecs/cs42l73.c @@ -929,6 +929,8 @@ static int cs42l73_set_mclk(struct snd_soc_dai *dai, unsigned int freq) /* MCLKX -> MCLK */ mclkx_coeff = cs42l73_get_mclkx_coeff(freq); + if (mclkx_coeff < 0) + return mclkx_coeff; mclk = cs42l73_mclkx_coeffs[mclkx_coeff].mclkx / cs42l73_mclkx_coeffs[mclkx_coeff].ratio; diff --git a/sound/soc/codecs/twl6040.c b/sound/soc/codecs/twl6040.c index 2d8c6b825e5..dc7509b9d53 100644 --- a/sound/soc/codecs/twl6040.c +++ b/sound/soc/codecs/twl6040.c @@ -26,7 +26,6 @@ #include <linux/pm.h> #include <linux/platform_device.h> #include <linux/slab.h> -#include <linux/i2c/twl.h> #include <linux/mfd/twl6040.h> #include <sound/core.h> @@ -1528,7 +1527,7 @@ static int twl6040_resume(struct snd_soc_codec *codec) static int twl6040_probe(struct snd_soc_codec *codec) { struct twl6040_data *priv; - struct twl4030_codec_data *pdata = dev_get_platdata(codec->dev); + struct twl6040_codec_data *pdata = dev_get_platdata(codec->dev); struct platform_device *pdev = container_of(codec->dev, struct platform_device, dev); int ret = 0; diff --git a/sound/soc/codecs/wm8994.c b/sound/soc/codecs/wm8994.c index 7c49642af05..6c1fe3afd4b 100644 --- a/sound/soc/codecs/wm8994.c +++ b/sound/soc/codecs/wm8994.c @@ -1000,61 +1000,170 @@ static void wm8994_update_class_w(struct snd_soc_codec *codec) } } -static int late_enable_ev(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) +static int aif1clk_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) { struct snd_soc_codec *codec = w->codec; - struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); + struct wm8994 *control = codec->control_data; + int mask = WM8994_AIF1DAC1L_ENA | WM8994_AIF1DAC1R_ENA; + int dac; + int adc; + int val; + + switch (control->type) { + case WM8994: + case WM8958: + mask |= WM8994_AIF1DAC2L_ENA | WM8994_AIF1DAC2R_ENA; + break; + default: + break; + } switch (event) { case SND_SOC_DAPM_PRE_PMU: - if (wm8994->aif1clk_enable) { - snd_soc_update_bits(codec, WM8994_AIF1_CLOCKING_1, - WM8994_AIF1CLK_ENA_MASK, - WM8994_AIF1CLK_ENA); - wm8994->aif1clk_enable = 0; - } - if (wm8994->aif2clk_enable) { - snd_soc_update_bits(codec, WM8994_AIF2_CLOCKING_1, - WM8994_AIF2CLK_ENA_MASK, - WM8994_AIF2CLK_ENA); - wm8994->aif2clk_enable = 0; - } + val = snd_soc_read(codec, WM8994_AIF1_CONTROL_1); + if ((val & WM8994_AIF1ADCL_SRC) && + (val & WM8994_AIF1ADCR_SRC)) + adc = WM8994_AIF1ADC1R_ENA | WM8994_AIF1ADC2R_ENA; + else if (!(val & WM8994_AIF1ADCL_SRC) && + !(val & WM8994_AIF1ADCR_SRC)) + adc = WM8994_AIF1ADC1L_ENA | WM8994_AIF1ADC2L_ENA; + else + adc = WM8994_AIF1ADC1R_ENA | WM8994_AIF1ADC2R_ENA | + WM8994_AIF1ADC1L_ENA | WM8994_AIF1ADC2L_ENA; + + val = snd_soc_read(codec, WM8994_AIF1_CONTROL_2); + if ((val & WM8994_AIF1DACL_SRC) && + (val & WM8994_AIF1DACR_SRC)) + dac = WM8994_AIF1DAC1R_ENA | WM8994_AIF1DAC2R_ENA; + else if (!(val & WM8994_AIF1DACL_SRC) && + !(val & WM8994_AIF1DACR_SRC)) + dac = WM8994_AIF1DAC1L_ENA | WM8994_AIF1DAC2L_ENA; + else + dac = WM8994_AIF1DAC1R_ENA | WM8994_AIF1DAC2R_ENA | + WM8994_AIF1DAC1L_ENA | WM8994_AIF1DAC2L_ENA; + + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_4, + mask, adc); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + mask, dac); + snd_soc_update_bits(codec, WM8994_CLOCKING_1, + WM8994_AIF1DSPCLK_ENA | + WM8994_SYSDSPCLK_ENA, + WM8994_AIF1DSPCLK_ENA | + WM8994_SYSDSPCLK_ENA); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_4, mask, + WM8994_AIF1ADC1R_ENA | + WM8994_AIF1ADC1L_ENA | + WM8994_AIF1ADC2R_ENA | + WM8994_AIF1ADC2L_ENA); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, mask, + WM8994_AIF1DAC1R_ENA | + WM8994_AIF1DAC1L_ENA | + WM8994_AIF1DAC2R_ENA | + WM8994_AIF1DAC2L_ENA); break; - } - /* We may also have postponed startup of DSP, handle that. */ - wm8958_aif_ev(w, kcontrol, event); + case SND_SOC_DAPM_PRE_PMD: + case SND_SOC_DAPM_POST_PMD: + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + mask, 0); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_4, + mask, 0); + + val = snd_soc_read(codec, WM8994_CLOCKING_1); + if (val & WM8994_AIF2DSPCLK_ENA) + val = WM8994_SYSDSPCLK_ENA; + else + val = 0; + snd_soc_update_bits(codec, WM8994_CLOCKING_1, + WM8994_SYSDSPCLK_ENA | + WM8994_AIF1DSPCLK_ENA, val); + break; + } return 0; } -static int late_disable_ev(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) +static int aif2clk_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) { struct snd_soc_codec *codec = w->codec; - struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); + int dac; + int adc; + int val; switch (event) { + case SND_SOC_DAPM_PRE_PMU: + val = snd_soc_read(codec, WM8994_AIF2_CONTROL_1); + if ((val & WM8994_AIF2ADCL_SRC) && + (val & WM8994_AIF2ADCR_SRC)) + adc = WM8994_AIF2ADCR_ENA; + else if (!(val & WM8994_AIF2ADCL_SRC) && + !(val & WM8994_AIF2ADCR_SRC)) + adc = WM8994_AIF2ADCL_ENA; + else + adc = WM8994_AIF2ADCL_ENA | WM8994_AIF2ADCR_ENA; + + + val = snd_soc_read(codec, WM8994_AIF2_CONTROL_2); + if ((val & WM8994_AIF2DACL_SRC) && + (val & WM8994_AIF2DACR_SRC)) + dac = WM8994_AIF2DACR_ENA; + else if (!(val & WM8994_AIF2DACL_SRC) && + !(val & WM8994_AIF2DACR_SRC)) + dac = WM8994_AIF2DACL_ENA; + else + dac = WM8994_AIF2DACL_ENA | WM8994_AIF2DACR_ENA; + + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_4, + WM8994_AIF2ADCL_ENA | + WM8994_AIF2ADCR_ENA, adc); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + WM8994_AIF2DACL_ENA | + WM8994_AIF2DACR_ENA, dac); + snd_soc_update_bits(codec, WM8994_CLOCKING_1, + WM8994_AIF2DSPCLK_ENA | + WM8994_SYSDSPCLK_ENA, + WM8994_AIF2DSPCLK_ENA | + WM8994_SYSDSPCLK_ENA); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_4, + WM8994_AIF2ADCL_ENA | + WM8994_AIF2ADCR_ENA, + WM8994_AIF2ADCL_ENA | + WM8994_AIF2ADCR_ENA); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + WM8994_AIF2DACL_ENA | + WM8994_AIF2DACR_ENA, + WM8994_AIF2DACL_ENA | + WM8994_AIF2DACR_ENA); + break; + + case SND_SOC_DAPM_PRE_PMD: case SND_SOC_DAPM_POST_PMD: - if (wm8994->aif1clk_disable) { - snd_soc_update_bits(codec, WM8994_AIF1_CLOCKING_1, - WM8994_AIF1CLK_ENA_MASK, 0); - wm8994->aif1clk_disable = 0; - } - if (wm8994->aif2clk_disable) { - snd_soc_update_bits(codec, WM8994_AIF2_CLOCKING_1, - WM8994_AIF2CLK_ENA_MASK, 0); - wm8994->aif2clk_disable = 0; - } + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + WM8994_AIF2DACL_ENA | + WM8994_AIF2DACR_ENA, 0); + snd_soc_update_bits(codec, WM8994_POWER_MANAGEMENT_5, + WM8994_AIF2ADCL_ENA | + WM8994_AIF2ADCR_ENA, 0); + + val = snd_soc_read(codec, WM8994_CLOCKING_1); + if (val & WM8994_AIF1DSPCLK_ENA) + val = WM8994_SYSDSPCLK_ENA; + else + val = 0; + snd_soc_update_bits(codec, WM8994_CLOCKING_1, + WM8994_SYSDSPCLK_ENA | + WM8994_AIF2DSPCLK_ENA, val); break; } return 0; } -static int aif1clk_ev(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) +static int aif1clk_late_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) { struct snd_soc_codec *codec = w->codec; struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); @@ -1071,8 +1180,8 @@ static int aif1clk_ev(struct snd_soc_dapm_widget *w, return 0; } -static int aif2clk_ev(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) +static int aif2clk_late_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) { struct snd_soc_codec *codec = w->codec; struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); @@ -1089,6 +1198,63 @@ static int aif2clk_ev(struct snd_soc_dapm_widget *w, return 0; } +static int late_enable_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) +{ + struct snd_soc_codec *codec = w->codec; + struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); + + switch (event) { + case SND_SOC_DAPM_PRE_PMU: + if (wm8994->aif1clk_enable) { + aif1clk_ev(w, kcontrol, event); + snd_soc_update_bits(codec, WM8994_AIF1_CLOCKING_1, + WM8994_AIF1CLK_ENA_MASK, + WM8994_AIF1CLK_ENA); + wm8994->aif1clk_enable = 0; + } + if (wm8994->aif2clk_enable) { + aif2clk_ev(w, kcontrol, event); + snd_soc_update_bits(codec, WM8994_AIF2_CLOCKING_1, + WM8994_AIF2CLK_ENA_MASK, + WM8994_AIF2CLK_ENA); + wm8994->aif2clk_enable = 0; + } + break; + } + + /* We may also have postponed startup of DSP, handle that. */ + wm8958_aif_ev(w, kcontrol, event); + + return 0; +} + +static int late_disable_ev(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) +{ + struct snd_soc_codec *codec = w->codec; + struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); + + switch (event) { + case SND_SOC_DAPM_POST_PMD: + if (wm8994->aif1clk_disable) { + snd_soc_update_bits(codec, WM8994_AIF1_CLOCKING_1, + WM8994_AIF1CLK_ENA_MASK, 0); + aif1clk_ev(w, kcontrol, event); + wm8994->aif1clk_disable = 0; + } + if (wm8994->aif2clk_disable) { + snd_soc_update_bits(codec, WM8994_AIF2_CLOCKING_1, + WM8994_AIF2CLK_ENA_MASK, 0); + aif2clk_ev(w, kcontrol, event); + wm8994->aif2clk_disable = 0; + } + break; + } + + return 0; +} + static int adc_mux_ev(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol, int event) { @@ -1385,9 +1551,9 @@ static const struct snd_kcontrol_new aif2dacr_src_mux = SOC_DAPM_ENUM("AIF2DACR Mux", aif2dacr_src_enum); static const struct snd_soc_dapm_widget wm8994_lateclk_revd_widgets[] = { -SND_SOC_DAPM_SUPPLY("AIF1CLK", SND_SOC_NOPM, 0, 0, aif1clk_ev, +SND_SOC_DAPM_SUPPLY("AIF1CLK", SND_SOC_NOPM, 0, 0, aif1clk_late_ev, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD), -SND_SOC_DAPM_SUPPLY("AIF2CLK", SND_SOC_NOPM, 0, 0, aif2clk_ev, +SND_SOC_DAPM_SUPPLY("AIF2CLK", SND_SOC_NOPM, 0, 0, aif2clk_late_ev, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_PGA_E("Late DAC1L Enable PGA", SND_SOC_NOPM, 0, 0, NULL, 0, @@ -1416,8 +1582,10 @@ SND_SOC_DAPM_POST("Late Disable PGA", late_disable_ev) }; static const struct snd_soc_dapm_widget wm8994_lateclk_widgets[] = { -SND_SOC_DAPM_SUPPLY("AIF1CLK", WM8994_AIF1_CLOCKING_1, 0, 0, NULL, 0), -SND_SOC_DAPM_SUPPLY("AIF2CLK", WM8994_AIF2_CLOCKING_1, 0, 0, NULL, 0), +SND_SOC_DAPM_SUPPLY("AIF1CLK", WM8994_AIF1_CLOCKING_1, 0, 0, aif1clk_ev, + SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_PRE_PMD), +SND_SOC_DAPM_SUPPLY("AIF2CLK", WM8994_AIF2_CLOCKING_1, 0, 0, aif2clk_ev, + SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_PRE_PMD), SND_SOC_DAPM_PGA("Direct Voice", SND_SOC_NOPM, 0, 0, NULL, 0), SND_SOC_DAPM_MIXER("SPKL", WM8994_POWER_MANAGEMENT_3, 8, 0, left_speaker_mixer, ARRAY_SIZE(left_speaker_mixer)), @@ -1470,30 +1638,30 @@ SND_SOC_DAPM_SUPPLY("VMID", SND_SOC_NOPM, 0, 0, vmid_event, SND_SOC_DAPM_SUPPLY("CLK_SYS", SND_SOC_NOPM, 0, 0, clk_sys_event, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), -SND_SOC_DAPM_SUPPLY("DSP1CLK", WM8994_CLOCKING_1, 3, 0, NULL, 0), -SND_SOC_DAPM_SUPPLY("DSP2CLK", WM8994_CLOCKING_1, 2, 0, NULL, 0), -SND_SOC_DAPM_SUPPLY("DSPINTCLK", WM8994_CLOCKING_1, 1, 0, NULL, 0), +SND_SOC_DAPM_SUPPLY("DSP1CLK", SND_SOC_NOPM, 3, 0, NULL, 0), +SND_SOC_DAPM_SUPPLY("DSP2CLK", SND_SOC_NOPM, 2, 0, NULL, 0), +SND_SOC_DAPM_SUPPLY("DSPINTCLK", SND_SOC_NOPM, 1, 0, NULL, 0), SND_SOC_DAPM_AIF_OUT("AIF1ADC1L", NULL, - 0, WM8994_POWER_MANAGEMENT_4, 9, 0), + 0, SND_SOC_NOPM, 9, 0), SND_SOC_DAPM_AIF_OUT("AIF1ADC1R", NULL, - 0, WM8994_POWER_MANAGEMENT_4, 8, 0), + 0, SND_SOC_NOPM, 8, 0), SND_SOC_DAPM_AIF_IN_E("AIF1DAC1L", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 9, 0, wm8958_aif_ev, + SND_SOC_NOPM, 9, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_AIF_IN_E("AIF1DAC1R", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 8, 0, wm8958_aif_ev, + SND_SOC_NOPM, 8, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_AIF_OUT("AIF1ADC2L", NULL, - 0, WM8994_POWER_MANAGEMENT_4, 11, 0), + 0, SND_SOC_NOPM, 11, 0), SND_SOC_DAPM_AIF_OUT("AIF1ADC2R", NULL, - 0, WM8994_POWER_MANAGEMENT_4, 10, 0), + 0, SND_SOC_NOPM, 10, 0), SND_SOC_DAPM_AIF_IN_E("AIF1DAC2L", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 11, 0, wm8958_aif_ev, + SND_SOC_NOPM, 11, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_AIF_IN_E("AIF1DAC2R", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 10, 0, wm8958_aif_ev, + SND_SOC_NOPM, 10, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_MIXER("AIF1ADC1L Mixer", SND_SOC_NOPM, 0, 0, @@ -1520,14 +1688,14 @@ SND_SOC_DAPM_MIXER("DAC1R Mixer", SND_SOC_NOPM, 0, 0, dac1r_mix, ARRAY_SIZE(dac1r_mix)), SND_SOC_DAPM_AIF_OUT("AIF2ADCL", NULL, 0, - WM8994_POWER_MANAGEMENT_4, 13, 0), + SND_SOC_NOPM, 13, 0), SND_SOC_DAPM_AIF_OUT("AIF2ADCR", NULL, 0, - WM8994_POWER_MANAGEMENT_4, 12, 0), + SND_SOC_NOPM, 12, 0), SND_SOC_DAPM_AIF_IN_E("AIF2DACL", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 13, 0, wm8958_aif_ev, + SND_SOC_NOPM, 13, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), SND_SOC_DAPM_AIF_IN_E("AIF2DACR", NULL, 0, - WM8994_POWER_MANAGEMENT_5, 12, 0, wm8958_aif_ev, + SND_SOC_NOPM, 12, 0, wm8958_aif_ev, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), SND_SOC_DAPM_AIF_IN("AIF1DACDAT", NULL, 0, SND_SOC_NOPM, 0, 0), diff --git a/sound/soc/omap/Kconfig b/sound/soc/omap/Kconfig index e00dd0b1139..deafbfaacdb 100644 --- a/sound/soc/omap/Kconfig +++ b/sound/soc/omap/Kconfig @@ -97,7 +97,7 @@ config SND_OMAP_SOC_SDP3430 config SND_OMAP_SOC_OMAP_ABE_TWL6040 tristate "SoC Audio support for OMAP boards using ABE and twl6040 codec" - depends on TWL4030_CORE && SND_OMAP_SOC && ARCH_OMAP4 + depends on TWL6040_CORE && SND_OMAP_SOC && ARCH_OMAP4 select SND_OMAP_SOC_DMIC select SND_OMAP_SOC_MCPDM select SND_SOC_TWL6040 diff --git a/sound/soc/sh/fsi.c b/sound/soc/sh/fsi.c index 378cc5b056d..74ed2dffbff 100644 --- a/sound/soc/sh/fsi.c +++ b/sound/soc/sh/fsi.c @@ -1001,11 +1001,10 @@ static void fsi_dma_do_tasklet(unsigned long data) sg_dma_address(&sg) = buf; sg_dma_len(&sg) = len; - desc = chan->device->device_prep_slave_sg(chan, &sg, 1, dir, - DMA_PREP_INTERRUPT | - DMA_CTRL_ACK); + desc = dmaengine_prep_slave_sg(chan, &sg, 1, dir, + DMA_PREP_INTERRUPT | DMA_CTRL_ACK); if (!desc) { - dev_err(dai->dev, "device_prep_slave_sg() fail\n"); + dev_err(dai->dev, "dmaengine_prep_slave_sg() fail\n"); return; } diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c index accdcb7d4d9..1d6a80c9f4c 100644 --- a/sound/soc/soc-core.c +++ b/sound/soc/soc-core.c @@ -3113,6 +3113,7 @@ int snd_soc_register_card(struct snd_soc_card *card) GFP_KERNEL); if (card->rtd == NULL) return -ENOMEM; + card->num_rtd = 0; card->rtd_aux = &card->rtd[card->num_links]; for (i = 0; i < card->num_links; i++) diff --git a/sound/soc/soc-dapm.c b/sound/soc/soc-dapm.c index 5cbd2d7623b..1bb6d4a63cd 100644 --- a/sound/soc/soc-dapm.c +++ b/sound/soc/soc-dapm.c @@ -67,6 +67,7 @@ static int dapm_up_seq[] = { [snd_soc_dapm_out_drv] = 10, [snd_soc_dapm_hp] = 10, [snd_soc_dapm_spk] = 10, + [snd_soc_dapm_line] = 10, [snd_soc_dapm_post] = 11, }; @@ -75,6 +76,7 @@ static int dapm_down_seq[] = { [snd_soc_dapm_adc] = 1, [snd_soc_dapm_hp] = 2, [snd_soc_dapm_spk] = 2, + [snd_soc_dapm_line] = 2, [snd_soc_dapm_out_drv] = 2, [snd_soc_dapm_pga] = 4, [snd_soc_dapm_mixer_named_ctl] = 5, |