aboutsummaryrefslogtreecommitdiffstats
path: root/sound/soc/codecs/wm8994.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/soc/codecs/wm8994.c')
-rw-r--r--sound/soc/codecs/wm8994.c230
1 files changed, 77 insertions, 153 deletions
diff --git a/sound/soc/codecs/wm8994.c b/sound/soc/codecs/wm8994.c
index a87046a96f2a..7823f92413f3 100644
--- a/sound/soc/codecs/wm8994.c
+++ b/sound/soc/codecs/wm8994.c
@@ -36,9 +36,6 @@
36#include "wm8994.h" 36#include "wm8994.h"
37#include "wm_hubs.h" 37#include "wm_hubs.h"
38 38
39static struct snd_soc_codec *wm8994_codec;
40struct snd_soc_codec_device soc_codec_dev_wm8994;
41
42struct fll_config { 39struct fll_config {
43 int src; 40 int src;
44 int in; 41 int in;
@@ -71,7 +68,9 @@ struct wm8994_micdet {
71/* codec private data */ 68/* codec private data */
72struct wm8994_priv { 69struct wm8994_priv {
73 struct wm_hubs_data hubs; 70 struct wm_hubs_data hubs;
74 struct snd_soc_codec codec; 71 enum snd_soc_control_type control_type;
72 void *control_data;
73 struct snd_soc_codec *codec;
75 u16 reg_cache[WM8994_REG_CACHE_SIZE + 1]; 74 u16 reg_cache[WM8994_REG_CACHE_SIZE + 1];
76 int sysclk[2]; 75 int sysclk[2];
77 int sysclk_rate[2]; 76 int sysclk_rate[2];
@@ -1901,8 +1900,6 @@ static int wm8994_put_drc_sw(struct snd_kcontrol *kcontrol,
1901 return snd_soc_put_volsw(kcontrol, ucontrol); 1900 return snd_soc_put_volsw(kcontrol, ucontrol);
1902} 1901}
1903 1902
1904
1905
1906static void wm8994_set_drc(struct snd_soc_codec *codec, int drc) 1903static void wm8994_set_drc(struct snd_soc_codec *codec, int drc)
1907{ 1904{
1908 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 1905 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
@@ -1941,7 +1938,7 @@ static int wm8994_put_drc_enum(struct snd_kcontrol *kcontrol,
1941 struct snd_ctl_elem_value *ucontrol) 1938 struct snd_ctl_elem_value *ucontrol)
1942{ 1939{
1943 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); 1940 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol);
1944 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 1941 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
1945 struct wm8994_pdata *pdata = wm8994->pdata; 1942 struct wm8994_pdata *pdata = wm8994->pdata;
1946 int drc = wm8994_get_drc(kcontrol->id.name); 1943 int drc = wm8994_get_drc(kcontrol->id.name);
1947 int value = ucontrol->value.integer.value[0]; 1944 int value = ucontrol->value.integer.value[0];
@@ -2044,7 +2041,7 @@ static int wm8994_put_retune_mobile_enum(struct snd_kcontrol *kcontrol,
2044 struct snd_ctl_elem_value *ucontrol) 2041 struct snd_ctl_elem_value *ucontrol)
2045{ 2042{
2046 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); 2043 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol);
2047 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 2044 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
2048 struct wm8994_pdata *pdata = wm8994->pdata; 2045 struct wm8994_pdata *pdata = wm8994->pdata;
2049 int block = wm8994_get_retune_mobile_block(kcontrol->id.name); 2046 int block = wm8994_get_retune_mobile_block(kcontrol->id.name);
2050 int value = ucontrol->value.integer.value[0]; 2047 int value = ucontrol->value.integer.value[0];
@@ -2066,7 +2063,7 @@ static int wm8994_get_retune_mobile_enum(struct snd_kcontrol *kcontrol,
2066 struct snd_ctl_elem_value *ucontrol) 2063 struct snd_ctl_elem_value *ucontrol)
2067{ 2064{
2068 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); 2065 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol);
2069 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 2066 struct wm8994_priv *wm8994 =snd_soc_codec_get_drvdata(codec);
2070 int block = wm8994_get_retune_mobile_block(kcontrol->id.name); 2067 int block = wm8994_get_retune_mobile_block(kcontrol->id.name);
2071 2068
2072 ucontrol->value.enumerated.item[0] = wm8994->retune_mobile_cfg[block]; 2069 ucontrol->value.enumerated.item[0] = wm8994->retune_mobile_cfg[block];
@@ -2880,10 +2877,9 @@ static int wm8994_get_fll_config(struct fll_div *fll,
2880 return 0; 2877 return 0;
2881} 2878}
2882 2879
2883static int wm8994_set_fll(struct snd_soc_dai *dai, int id, int src, 2880static int _wm8994_set_fll(struct snd_soc_codec *codec, int id, int src,
2884 unsigned int freq_in, unsigned int freq_out) 2881 unsigned int freq_in, unsigned int freq_out)
2885{ 2882{
2886 struct snd_soc_codec *codec = dai->codec;
2887 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 2883 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
2888 int reg_offset, ret; 2884 int reg_offset, ret;
2889 struct fll_div fll; 2885 struct fll_div fll;
@@ -2994,8 +2990,15 @@ static int wm8994_set_fll(struct snd_soc_dai *dai, int id, int src,
2994 return 0; 2990 return 0;
2995} 2991}
2996 2992
2993
2997static int opclk_divs[] = { 10, 20, 30, 40, 55, 60, 80, 120, 160 }; 2994static int opclk_divs[] = { 10, 20, 30, 40, 55, 60, 80, 120, 160 };
2998 2995
2996static int wm8994_set_fll(struct snd_soc_dai *dai, int id, int src,
2997 unsigned int freq_in, unsigned int freq_out)
2998{
2999 return _wm8994_set_fll(dai->codec, id, src, freq_in, freq_out);
3000}
3001
2999static int wm8994_set_dai_sysclk(struct snd_soc_dai *dai, 3002static int wm8994_set_dai_sysclk(struct snd_soc_dai *dai,
3000 int clk_id, unsigned int freq, int dir) 3003 int clk_id, unsigned int freq, int dir)
3001{ 3004{
@@ -3507,10 +3510,9 @@ static struct snd_soc_dai_ops wm8994_aif3_dai_ops = {
3507 .set_tristate = wm8994_set_tristate, 3510 .set_tristate = wm8994_set_tristate,
3508}; 3511};
3509 3512
3510struct snd_soc_dai wm8994_dai[] = { 3513static struct snd_soc_dai_driver wm8994_dai[] = {
3511 { 3514 {
3512 .name = "WM8994 AIF1", 3515 .name = "wm8994-aif1",
3513 .id = 1,
3514 .playback = { 3516 .playback = {
3515 .stream_name = "AIF1 Playback", 3517 .stream_name = "AIF1 Playback",
3516 .channels_min = 2, 3518 .channels_min = 2,
@@ -3528,8 +3530,7 @@ struct snd_soc_dai wm8994_dai[] = {
3528 .ops = &wm8994_aif1_dai_ops, 3530 .ops = &wm8994_aif1_dai_ops,
3529 }, 3531 },
3530 { 3532 {
3531 .name = "WM8994 AIF2", 3533 .name = "wm8994-aif2",
3532 .id = 2,
3533 .playback = { 3534 .playback = {
3534 .stream_name = "AIF2 Playback", 3535 .stream_name = "AIF2 Playback",
3535 .channels_min = 2, 3536 .channels_min = 2,
@@ -3547,8 +3548,7 @@ struct snd_soc_dai wm8994_dai[] = {
3547 .ops = &wm8994_aif2_dai_ops, 3548 .ops = &wm8994_aif2_dai_ops,
3548 }, 3549 },
3549 { 3550 {
3550 .name = "WM8994 AIF3", 3551 .name = "wm8994-aif3",
3551 .id = 3,
3552 .playback = { 3552 .playback = {
3553 .stream_name = "AIF3 Playback", 3553 .stream_name = "AIF3 Playback",
3554 .channels_min = 2, 3554 .channels_min = 2,
@@ -3566,20 +3566,17 @@ struct snd_soc_dai wm8994_dai[] = {
3566 .ops = &wm8994_aif3_dai_ops, 3566 .ops = &wm8994_aif3_dai_ops,
3567 } 3567 }
3568}; 3568};
3569EXPORT_SYMBOL_GPL(wm8994_dai);
3570 3569
3571#ifdef CONFIG_PM 3570#ifdef CONFIG_PM
3572static int wm8994_suspend(struct platform_device *pdev, pm_message_t state) 3571static int wm8994_suspend(struct snd_soc_codec *codec, pm_message_t state)
3573{ 3572{
3574 struct snd_soc_device *socdev = platform_get_drvdata(pdev);
3575 struct snd_soc_codec *codec = socdev->card->codec;
3576 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 3573 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
3577 int i, ret; 3574 int i, ret;
3578 3575
3579 for (i = 0; i < ARRAY_SIZE(wm8994->fll); i++) { 3576 for (i = 0; i < ARRAY_SIZE(wm8994->fll); i++) {
3580 memcpy(&wm8994->fll_suspend[i], &wm8994->fll[i], 3577 memcpy(&wm8994->fll_suspend[i], &wm8994->fll[i],
3581 sizeof(struct fll_config)); 3578 sizeof(struct fll_config));
3582 ret = wm8994_set_fll(&codec->dai[0], i + 1, 0, 0, 0); 3579 ret = _wm8994_set_fll(codec, i + 1, 0, 0, 0);
3583 if (ret < 0) 3580 if (ret < 0)
3584 dev_warn(codec->dev, "Failed to stop FLL%d: %d\n", 3581 dev_warn(codec->dev, "Failed to stop FLL%d: %d\n",
3585 i + 1, ret); 3582 i + 1, ret);
@@ -3590,10 +3587,8 @@ static int wm8994_suspend(struct platform_device *pdev, pm_message_t state)
3590 return 0; 3587 return 0;
3591} 3588}
3592 3589
3593static int wm8994_resume(struct platform_device *pdev) 3590static int wm8994_resume(struct snd_soc_codec *codec)
3594{ 3591{
3595 struct snd_soc_device *socdev = platform_get_drvdata(pdev);
3596 struct snd_soc_codec *codec = socdev->card->codec;
3597 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec); 3592 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
3598 u16 *reg_cache = codec->reg_cache; 3593 u16 *reg_cache = codec->reg_cache;
3599 int i, ret; 3594 int i, ret;
@@ -3622,7 +3617,7 @@ static int wm8994_resume(struct platform_device *pdev)
3622 if (!wm8994->fll_suspend[i].out) 3617 if (!wm8994->fll_suspend[i].out)
3623 continue; 3618 continue;
3624 3619
3625 ret = wm8994_set_fll(&codec->dai[0], i + 1, 3620 ret = _wm8994_set_fll(codec, i + 1,
3626 wm8994->fll_suspend[i].src, 3621 wm8994->fll_suspend[i].src,
3627 wm8994->fll_suspend[i].in, 3622 wm8994->fll_suspend[i].in,
3628 wm8994->fll_suspend[i].out); 3623 wm8994->fll_suspend[i].out);
@@ -3640,7 +3635,7 @@ static int wm8994_resume(struct platform_device *pdev)
3640 3635
3641static void wm8994_handle_retune_mobile_pdata(struct wm8994_priv *wm8994) 3636static void wm8994_handle_retune_mobile_pdata(struct wm8994_priv *wm8994)
3642{ 3637{
3643 struct snd_soc_codec *codec = &wm8994->codec; 3638 struct snd_soc_codec *codec = wm8994->codec;
3644 struct wm8994_pdata *pdata = wm8994->pdata; 3639 struct wm8994_pdata *pdata = wm8994->pdata;
3645 struct snd_kcontrol_new controls[] = { 3640 struct snd_kcontrol_new controls[] = {
3646 SOC_ENUM_EXT("AIF1.1 EQ Mode", 3641 SOC_ENUM_EXT("AIF1.1 EQ Mode",
@@ -3698,16 +3693,16 @@ static void wm8994_handle_retune_mobile_pdata(struct wm8994_priv *wm8994)
3698 wm8994->retune_mobile_enum.max = wm8994->num_retune_mobile_texts; 3693 wm8994->retune_mobile_enum.max = wm8994->num_retune_mobile_texts;
3699 wm8994->retune_mobile_enum.texts = wm8994->retune_mobile_texts; 3694 wm8994->retune_mobile_enum.texts = wm8994->retune_mobile_texts;
3700 3695
3701 ret = snd_soc_add_controls(&wm8994->codec, controls, 3696 ret = snd_soc_add_controls(wm8994->codec, controls,
3702 ARRAY_SIZE(controls)); 3697 ARRAY_SIZE(controls));
3703 if (ret != 0) 3698 if (ret != 0)
3704 dev_err(wm8994->codec.dev, 3699 dev_err(wm8994->codec->dev,
3705 "Failed to add ReTune Mobile controls: %d\n", ret); 3700 "Failed to add ReTune Mobile controls: %d\n", ret);
3706} 3701}
3707 3702
3708static void wm8994_handle_pdata(struct wm8994_priv *wm8994) 3703static void wm8994_handle_pdata(struct wm8994_priv *wm8994)
3709{ 3704{
3710 struct snd_soc_codec *codec = &wm8994->codec; 3705 struct snd_soc_codec *codec = wm8994->codec;
3711 struct wm8994_pdata *pdata = wm8994->pdata; 3706 struct wm8994_pdata *pdata = wm8994->pdata;
3712 int ret, i; 3707 int ret, i;
3713 3708
@@ -3739,7 +3734,7 @@ static void wm8994_handle_pdata(struct wm8994_priv *wm8994)
3739 wm8994->drc_texts = kmalloc(sizeof(char *) 3734 wm8994->drc_texts = kmalloc(sizeof(char *)
3740 * pdata->num_drc_cfgs, GFP_KERNEL); 3735 * pdata->num_drc_cfgs, GFP_KERNEL);
3741 if (!wm8994->drc_texts) { 3736 if (!wm8994->drc_texts) {
3742 dev_err(wm8994->codec.dev, 3737 dev_err(wm8994->codec->dev,
3743 "Failed to allocate %d DRC config texts\n", 3738 "Failed to allocate %d DRC config texts\n",
3744 pdata->num_drc_cfgs); 3739 pdata->num_drc_cfgs);
3745 return; 3740 return;
@@ -3751,10 +3746,10 @@ static void wm8994_handle_pdata(struct wm8994_priv *wm8994)
3751 wm8994->drc_enum.max = pdata->num_drc_cfgs; 3746 wm8994->drc_enum.max = pdata->num_drc_cfgs;
3752 wm8994->drc_enum.texts = wm8994->drc_texts; 3747 wm8994->drc_enum.texts = wm8994->drc_texts;
3753 3748
3754 ret = snd_soc_add_controls(&wm8994->codec, controls, 3749 ret = snd_soc_add_controls(wm8994->codec, controls,
3755 ARRAY_SIZE(controls)); 3750 ARRAY_SIZE(controls));
3756 if (ret != 0) 3751 if (ret != 0)
3757 dev_err(wm8994->codec.dev, 3752 dev_err(wm8994->codec->dev,
3758 "Failed to add DRC mode controls: %d\n", ret); 3753 "Failed to add DRC mode controls: %d\n", ret);
3759 3754
3760 for (i = 0; i < WM8994_NUM_DRC; i++) 3755 for (i = 0; i < WM8994_NUM_DRC; i++)
@@ -3767,62 +3762,10 @@ static void wm8994_handle_pdata(struct wm8994_priv *wm8994)
3767 if (pdata->num_retune_mobile_cfgs) 3762 if (pdata->num_retune_mobile_cfgs)
3768 wm8994_handle_retune_mobile_pdata(wm8994); 3763 wm8994_handle_retune_mobile_pdata(wm8994);
3769 else 3764 else
3770 snd_soc_add_controls(&wm8994->codec, wm8994_eq_controls, 3765 snd_soc_add_controls(wm8994->codec, wm8994_eq_controls,
3771 ARRAY_SIZE(wm8994_eq_controls)); 3766 ARRAY_SIZE(wm8994_eq_controls));
3772} 3767}
3773 3768
3774static int wm8994_probe(struct platform_device *pdev)
3775{
3776 struct snd_soc_device *socdev = platform_get_drvdata(pdev);
3777 struct snd_soc_codec *codec;
3778 int ret = 0;
3779
3780 if (wm8994_codec == NULL) {
3781 dev_err(&pdev->dev, "Codec device not registered\n");
3782 return -ENODEV;
3783 }
3784
3785 socdev->card->codec = wm8994_codec;
3786 codec = wm8994_codec;
3787
3788 /* register pcms */
3789 ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
3790 if (ret < 0) {
3791 dev_err(codec->dev, "failed to create pcms: %d\n", ret);
3792 return ret;
3793 }
3794
3795 wm8994_handle_pdata(snd_soc_codec_get_drvdata(codec));
3796
3797 wm_hubs_add_analogue_controls(codec);
3798 snd_soc_add_controls(codec, wm8994_snd_controls,
3799 ARRAY_SIZE(wm8994_snd_controls));
3800 snd_soc_dapm_new_controls(codec, wm8994_dapm_widgets,
3801 ARRAY_SIZE(wm8994_dapm_widgets));
3802 wm_hubs_add_analogue_routes(codec, 0, 0);
3803 snd_soc_dapm_add_routes(codec, intercon, ARRAY_SIZE(intercon));
3804
3805 return 0;
3806}
3807
3808static int wm8994_remove(struct platform_device *pdev)
3809{
3810 struct snd_soc_device *socdev = platform_get_drvdata(pdev);
3811
3812 snd_soc_free_pcms(socdev);
3813 snd_soc_dapm_free(socdev);
3814
3815 return 0;
3816}
3817
3818struct snd_soc_codec_device soc_codec_dev_wm8994 = {
3819 .probe = wm8994_probe,
3820 .remove = wm8994_remove,
3821 .suspend = wm8994_suspend,
3822 .resume = wm8994_resume,
3823};
3824EXPORT_SYMBOL_GPL(soc_codec_dev_wm8994);
3825
3826/** 3769/**
3827 * wm8994_mic_detect - Enable microphone detection via the WM8994 IRQ 3770 * wm8994_mic_detect - Enable microphone detection via the WM8994 IRQ
3828 * 3771 *
@@ -3881,7 +3824,7 @@ EXPORT_SYMBOL_GPL(wm8994_mic_detect);
3881static irqreturn_t wm8994_mic_irq(int irq, void *data) 3824static irqreturn_t wm8994_mic_irq(int irq, void *data)
3882{ 3825{
3883 struct wm8994_priv *priv = data; 3826 struct wm8994_priv *priv = data;
3884 struct snd_soc_codec *codec = &priv->codec; 3827 struct snd_soc_codec *codec = priv->codec;
3885 int reg; 3828 int reg;
3886 int report; 3829 int report;
3887 3830
@@ -3913,47 +3856,20 @@ static irqreturn_t wm8994_mic_irq(int irq, void *data)
3913 return IRQ_HANDLED; 3856 return IRQ_HANDLED;
3914} 3857}
3915 3858
3916static int wm8994_codec_probe(struct platform_device *pdev) 3859static int wm8994_codec_probe(struct snd_soc_codec *codec)
3917{ 3860{
3918 int ret;
3919 struct wm8994_priv *wm8994; 3861 struct wm8994_priv *wm8994;
3920 struct snd_soc_codec *codec; 3862 int ret, i, rev;
3921 int i;
3922 u16 rev;
3923 3863
3924 if (wm8994_codec) { 3864 codec->control_data = dev_get_drvdata(codec->dev->parent);
3925 dev_err(&pdev->dev, "Another WM8994 is registered\n");
3926 return -EINVAL;
3927 }
3928 3865
3929 wm8994 = kzalloc(sizeof(struct wm8994_priv), GFP_KERNEL); 3866 wm8994 = kzalloc(sizeof(struct wm8994_priv), GFP_KERNEL);
3930 if (!wm8994) { 3867 if (wm8994 == NULL)
3931 dev_err(&pdev->dev, "Failed to allocate private data\n");
3932 return -ENOMEM; 3868 return -ENOMEM;
3933 }
3934
3935 codec = &wm8994->codec;
3936
3937 mutex_init(&codec->mutex);
3938 INIT_LIST_HEAD(&codec->dapm_widgets);
3939 INIT_LIST_HEAD(&codec->dapm_paths);
3940
3941 snd_soc_codec_set_drvdata(codec, wm8994); 3869 snd_soc_codec_set_drvdata(codec, wm8994);
3942 codec->control_data = dev_get_drvdata(pdev->dev.parent); 3870
3943 codec->name = "WM8994"; 3871 wm8994->pdata = dev_get_platdata(codec->dev->parent);
3944 codec->owner = THIS_MODULE; 3872 wm8994->codec = codec;
3945 codec->read = wm8994_read;
3946 codec->write = wm8994_write;
3947 codec->readable_register = wm8994_readable;
3948 codec->bias_level = SND_SOC_BIAS_OFF;
3949 codec->set_bias_level = wm8994_set_bias_level;
3950 codec->dai = &wm8994_dai[0];
3951 codec->num_dai = 3;
3952 codec->reg_cache_size = WM8994_MAX_REGISTER;
3953 codec->reg_cache = &wm8994->reg_cache;
3954 codec->dev = &pdev->dev;
3955
3956 wm8994->pdata = pdev->dev.parent->platform_data;
3957 3873
3958 /* Fill the cache with physical values we inherited; don't reset */ 3874 /* Fill the cache with physical values we inherited; don't reset */
3959 ret = wm8994_bulk_read(codec->control_data, 0, 3875 ret = wm8994_bulk_read(codec->control_data, 0,
@@ -3989,25 +3905,25 @@ static int wm8994_codec_probe(struct platform_device *pdev)
3989 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC1_DET, 3905 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC1_DET,
3990 wm8994_mic_irq, "Mic 1 detect", wm8994); 3906 wm8994_mic_irq, "Mic 1 detect", wm8994);
3991 if (ret != 0) 3907 if (ret != 0)
3992 dev_warn(&pdev->dev, 3908 dev_warn(codec->dev,
3993 "Failed to request Mic1 detect IRQ: %d\n", ret); 3909 "Failed to request Mic1 detect IRQ: %d\n", ret);
3994 3910
3995 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC1_SHRT, 3911 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC1_SHRT,
3996 wm8994_mic_irq, "Mic 1 short", wm8994); 3912 wm8994_mic_irq, "Mic 1 short", wm8994);
3997 if (ret != 0) 3913 if (ret != 0)
3998 dev_warn(&pdev->dev, 3914 dev_warn(codec->dev,
3999 "Failed to request Mic1 short IRQ: %d\n", ret); 3915 "Failed to request Mic1 short IRQ: %d\n", ret);
4000 3916
4001 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC2_DET, 3917 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC2_DET,
4002 wm8994_mic_irq, "Mic 2 detect", wm8994); 3918 wm8994_mic_irq, "Mic 2 detect", wm8994);
4003 if (ret != 0) 3919 if (ret != 0)
4004 dev_warn(&pdev->dev, 3920 dev_warn(codec->dev,
4005 "Failed to request Mic2 detect IRQ: %d\n", ret); 3921 "Failed to request Mic2 detect IRQ: %d\n", ret);
4006 3922
4007 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT, 3923 ret = wm8994_request_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT,
4008 wm8994_mic_irq, "Mic 2 short", wm8994); 3924 wm8994_mic_irq, "Mic 2 short", wm8994);
4009 if (ret != 0) 3925 if (ret != 0)
4010 dev_warn(&pdev->dev, 3926 dev_warn(codec->dev,
4011 "Failed to request Mic2 short IRQ: %d\n", ret); 3927 "Failed to request Mic2 short IRQ: %d\n", ret);
4012 3928
4013 /* Remember if AIFnLRCLK is configured as a GPIO. This should be 3929 /* Remember if AIFnLRCLK is configured as a GPIO. This should be
@@ -4038,13 +3954,8 @@ static int wm8994_codec_probe(struct platform_device *pdev)
4038 wm8994->lrclk_shared[1] = 0; 3954 wm8994->lrclk_shared[1] = 0;
4039 } 3955 }
4040 3956
4041 for (i = 0; i < ARRAY_SIZE(wm8994_dai); i++)
4042 wm8994_dai[i].dev = codec->dev;
4043
4044 wm8994_set_bias_level(codec, SND_SOC_BIAS_STANDBY); 3957 wm8994_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
4045 3958
4046 wm8994_codec = codec;
4047
4048 /* Latch volume updates (right only; we always do left then right). */ 3959 /* Latch volume updates (right only; we always do left then right). */
4049 snd_soc_update_bits(codec, WM8994_AIF1_DAC1_RIGHT_VOLUME, 3960 snd_soc_update_bits(codec, WM8994_AIF1_DAC1_RIGHT_VOLUME,
4050 WM8994_AIF1DAC1_VU, WM8994_AIF1DAC1_VU); 3961 WM8994_AIF1DAC1_VU, WM8994_AIF1DAC1_VU);
@@ -4081,24 +3992,18 @@ static int wm8994_codec_probe(struct platform_device *pdev)
4081 3992
4082 wm8994_update_class_w(codec); 3993 wm8994_update_class_w(codec);
4083 3994
4084 ret = snd_soc_register_codec(codec); 3995 wm8994_handle_pdata(wm8994);
4085 if (ret != 0) {
4086 dev_err(codec->dev, "Failed to register codec: %d\n", ret);
4087 goto err_irq;
4088 }
4089
4090 ret = snd_soc_register_dais(wm8994_dai, ARRAY_SIZE(wm8994_dai));
4091 if (ret != 0) {
4092 dev_err(codec->dev, "Failed to register DAIs: %d\n", ret);
4093 goto err_codec;
4094 }
4095 3996
4096 platform_set_drvdata(pdev, wm8994); 3997 wm_hubs_add_analogue_controls(codec);
3998 snd_soc_add_controls(codec, wm8994_snd_controls,
3999 ARRAY_SIZE(wm8994_snd_controls));
4000 snd_soc_dapm_new_controls(codec, wm8994_dapm_widgets,
4001 ARRAY_SIZE(wm8994_dapm_widgets));
4002 wm_hubs_add_analogue_routes(codec, 0, 0);
4003 snd_soc_dapm_add_routes(codec, intercon, ARRAY_SIZE(intercon));
4097 4004
4098 return 0; 4005 return 0;
4099 4006
4100err_codec:
4101 snd_soc_unregister_codec(codec);
4102err_irq: 4007err_irq:
4103 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT, wm8994); 4008 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT, wm8994);
4104 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_DET, wm8994); 4009 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_DET, wm8994);
@@ -4109,31 +4014,50 @@ err:
4109 return ret; 4014 return ret;
4110} 4015}
4111 4016
4112static int __devexit wm8994_codec_remove(struct platform_device *pdev) 4017static int wm8994_codec_remove(struct snd_soc_codec *codec)
4113{ 4018{
4114 struct wm8994_priv *wm8994 = platform_get_drvdata(pdev); 4019 struct wm8994_priv *wm8994 = snd_soc_codec_get_drvdata(codec);
4115 struct snd_soc_codec *codec = &wm8994->codec;
4116 4020
4117 wm8994_set_bias_level(codec, SND_SOC_BIAS_OFF); 4021 wm8994_set_bias_level(codec, SND_SOC_BIAS_OFF);
4118 snd_soc_unregister_dais(wm8994_dai, ARRAY_SIZE(wm8994_dai)); 4022
4119 snd_soc_unregister_codec(&wm8994->codec);
4120 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT, wm8994); 4023 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_SHRT, wm8994);
4121 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_DET, wm8994); 4024 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC2_DET, wm8994);
4122 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC1_SHRT, wm8994); 4025 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC1_SHRT, wm8994);
4123 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC1_DET, wm8994); 4026 wm8994_free_irq(codec->control_data, WM8994_IRQ_MIC1_DET, wm8994);
4124 kfree(wm8994); 4027 kfree(wm8994);
4125 wm8994_codec = NULL;
4126 4028
4127 return 0; 4029 return 0;
4128} 4030}
4129 4031
4032static struct snd_soc_codec_driver soc_codec_dev_wm8994 = {
4033 .probe = wm8994_codec_probe,
4034 .remove = wm8994_codec_remove,
4035 .suspend = wm8994_suspend,
4036 .resume = wm8994_resume,
4037 .read = wm8994_read,
4038 .write = wm8994_write,
4039 .set_bias_level = wm8994_set_bias_level,
4040};
4041
4042static int __devinit wm8994_probe(struct platform_device *pdev)
4043{
4044 return snd_soc_register_codec(&pdev->dev, &soc_codec_dev_wm8994,
4045 wm8994_dai, ARRAY_SIZE(wm8994_dai));
4046}
4047
4048static int __devexit wm8994_remove(struct platform_device *pdev)
4049{
4050 snd_soc_unregister_codec(&pdev->dev);
4051 return 0;
4052}
4053
4130static struct platform_driver wm8994_codec_driver = { 4054static struct platform_driver wm8994_codec_driver = {
4131 .driver = { 4055 .driver = {
4132 .name = "wm8994-codec", 4056 .name = "wm8994-codec",
4133 .owner = THIS_MODULE, 4057 .owner = THIS_MODULE,
4134 }, 4058 },
4135 .probe = wm8994_codec_probe, 4059 .probe = wm8994_probe,
4136 .remove = __devexit_p(wm8994_codec_remove), 4060 .remove = __devexit_p(wm8994_remove),
4137}; 4061};
4138 4062
4139static __init int wm8994_init(void) 4063static __init int wm8994_init(void)