aboutsummaryrefslogtreecommitdiffstats
path: root/sound/soc/sh
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2010-10-25 11:32:05 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2010-10-25 11:32:05 -0400
commit33081adf8b89d5a716d7e1c60171768d39795b39 (patch)
tree275de58bbbb5f7ddffcdc087844cfc7fbe4315be /sound/soc/sh
parentc55960499f810357a29659b32d6ea594abee9237 (diff)
parent506ecbca71d07fa327dd986be1682e90885678ee (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound-2.6
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound-2.6: (365 commits) ALSA: hda - Disable sticky PCM stream assignment for AD codecs ALSA: usb - Creative USB X-Fi volume knob support ALSA: ca0106: Use card specific dac id for mute controls. ALSA: ca0106: Allow different sound cards to use different SPI channel mappings. ALSA: ca0106: Create a nice spot for mapping channels to dacs. ALSA: ca0106: Move enabling of front dac out of hardcoded setup sequence. ALSA: ca0106: Pull out dac powering routine into separate function. ALSA: ca0106 - add Sound Blaster 5.1vx info. ASoC: tlv320dac33: Use usleep_range for delays ALSA: usb-audio: add Novation Launchpad support ALSA: hda - Add workarounds for CT-IBG controllers ALSA: hda - Fix wrong TLV mute bit for STAC/IDT codecs ASoC: tpa6130a2: Error handling for broken chip ASoC: max98088: Staticise m98088_eq_band ASoC: soc-core: Fix codec->name memory leak ALSA: hda - Apply ideapad quirk to Acer laptops with Cxt5066 ALSA: hda - Add some workarounds for Creative IBG ALSA: hda - Fix wrong SPDIF NID assignment for CA0110 ALSA: hda - Fix codec rename rules for ALC662-compatible codecs ALSA: hda - Add alc_init_jacks() call to other codecs ...
Diffstat (limited to 'sound/soc/sh')
-rw-r--r--sound/soc/sh/Kconfig11
-rw-r--r--sound/soc/sh/Makefile2
-rw-r--r--sound/soc/sh/dma-sh7760.c53
-rw-r--r--sound/soc/sh/fsi-ak4642.c31
-rw-r--r--sound/soc/sh/fsi-da7210.c24
-rw-r--r--sound/soc/sh/fsi-hdmi.c60
-rw-r--r--sound/soc/sh/fsi.c606
-rw-r--r--sound/soc/sh/hac.c46
-rw-r--r--sound/soc/sh/migor.c29
-rw-r--r--sound/soc/sh/sh7760-ac97.c25
-rw-r--r--sound/soc/sh/siu.h6
-rw-r--r--sound/soc/sh/siu_dai.c97
-rw-r--r--sound/soc/sh/siu_pcm.c32
-rw-r--r--sound/soc/sh/ssi.c55
14 files changed, 619 insertions, 458 deletions
diff --git a/sound/soc/sh/Kconfig b/sound/soc/sh/Kconfig
index 52d7e8ed9c1f..7f0a496e07ce 100644
--- a/sound/soc/sh/Kconfig
+++ b/sound/soc/sh/Kconfig
@@ -47,7 +47,7 @@ config SND_SH7760_AC97
47 AC97 unit of the SH7760. 47 AC97 unit of the SH7760.
48 48
49config SND_FSI_AK4642 49config SND_FSI_AK4642
50 bool "FSI-AK4642 sound support" 50 tristate "FSI-AK4642 sound support"
51 depends on SND_SOC_SH4_FSI && I2C_SH_MOBILE 51 depends on SND_SOC_SH4_FSI && I2C_SH_MOBILE
52 select SND_SOC_AK4642 52 select SND_SOC_AK4642
53 help 53 help
@@ -55,13 +55,20 @@ config SND_FSI_AK4642
55 FSI - AK4642 unit 55 FSI - AK4642 unit
56 56
57config SND_FSI_DA7210 57config SND_FSI_DA7210
58 bool "FSI-DA7210 sound support" 58 tristate "FSI-DA7210 sound support"
59 depends on SND_SOC_SH4_FSI && I2C_SH_MOBILE 59 depends on SND_SOC_SH4_FSI && I2C_SH_MOBILE
60 select SND_SOC_DA7210 60 select SND_SOC_DA7210
61 help 61 help
62 This option enables generic sound support for the 62 This option enables generic sound support for the
63 FSI - DA7210 unit 63 FSI - DA7210 unit
64 64
65config SND_FSI_HDMI
66 tristate "FSI-HDMI sound support"
67 depends on SND_SOC_SH4_FSI && FB_SH_MOBILE_HDMI
68 help
69 This option enables generic sound support for the
70 FSI - HDMI unit
71
65config SND_SIU_MIGOR 72config SND_SIU_MIGOR
66 tristate "SIU sound support on Migo-R" 73 tristate "SIU sound support on Migo-R"
67 depends on SH_MIGOR 74 depends on SH_MIGOR
diff --git a/sound/soc/sh/Makefile b/sound/soc/sh/Makefile
index 8a5a19293bda..94476d4c0fd5 100644
--- a/sound/soc/sh/Makefile
+++ b/sound/soc/sh/Makefile
@@ -16,9 +16,11 @@ obj-$(CONFIG_SND_SOC_SH4_SIU) += snd-soc-siu.o
16snd-soc-sh7760-ac97-objs := sh7760-ac97.o 16snd-soc-sh7760-ac97-objs := sh7760-ac97.o
17snd-soc-fsi-ak4642-objs := fsi-ak4642.o 17snd-soc-fsi-ak4642-objs := fsi-ak4642.o
18snd-soc-fsi-da7210-objs := fsi-da7210.o 18snd-soc-fsi-da7210-objs := fsi-da7210.o
19snd-soc-fsi-hdmi-objs := fsi-hdmi.o
19snd-soc-migor-objs := migor.o 20snd-soc-migor-objs := migor.o
20 21
21obj-$(CONFIG_SND_SH7760_AC97) += snd-soc-sh7760-ac97.o 22obj-$(CONFIG_SND_SH7760_AC97) += snd-soc-sh7760-ac97.o
22obj-$(CONFIG_SND_FSI_AK4642) += snd-soc-fsi-ak4642.o 23obj-$(CONFIG_SND_FSI_AK4642) += snd-soc-fsi-ak4642.o
23obj-$(CONFIG_SND_FSI_DA7210) += snd-soc-fsi-da7210.o 24obj-$(CONFIG_SND_FSI_DA7210) += snd-soc-fsi-da7210.o
25obj-$(CONFIG_SND_FSI_HDMI) += snd-soc-fsi-hdmi.o
24obj-$(CONFIG_SND_SIU_MIGOR) += snd-soc-migor.o 26obj-$(CONFIG_SND_SIU_MIGOR) += snd-soc-migor.o
diff --git a/sound/soc/sh/dma-sh7760.c b/sound/soc/sh/dma-sh7760.c
index 0d8bdf07729c..c326d29992fe 100644
--- a/sound/soc/sh/dma-sh7760.c
+++ b/sound/soc/sh/dma-sh7760.c
@@ -137,7 +137,7 @@ static void camelot_rxdma(void *data)
137static int camelot_pcm_open(struct snd_pcm_substream *substream) 137static int camelot_pcm_open(struct snd_pcm_substream *substream)
138{ 138{
139 struct snd_soc_pcm_runtime *rtd = substream->private_data; 139 struct snd_soc_pcm_runtime *rtd = substream->private_data;
140 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 140 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
141 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1; 141 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1;
142 int ret, dmairq; 142 int ret, dmairq;
143 143
@@ -150,7 +150,7 @@ static int camelot_pcm_open(struct snd_pcm_substream *substream)
150 ret = dmabrg_request_irq(dmairq, camelot_rxdma, cam); 150 ret = dmabrg_request_irq(dmairq, camelot_rxdma, cam);
151 if (unlikely(ret)) { 151 if (unlikely(ret)) {
152 pr_debug("audio unit %d irqs already taken!\n", 152 pr_debug("audio unit %d irqs already taken!\n",
153 rtd->dai->cpu_dai->id); 153 rtd->cpu_dai->id);
154 return -EBUSY; 154 return -EBUSY;
155 } 155 }
156 (void)dmabrg_request_irq(dmairq + 1,camelot_rxdma, cam); 156 (void)dmabrg_request_irq(dmairq + 1,camelot_rxdma, cam);
@@ -159,7 +159,7 @@ static int camelot_pcm_open(struct snd_pcm_substream *substream)
159 ret = dmabrg_request_irq(dmairq, camelot_txdma, cam); 159 ret = dmabrg_request_irq(dmairq, camelot_txdma, cam);
160 if (unlikely(ret)) { 160 if (unlikely(ret)) {
161 pr_debug("audio unit %d irqs already taken!\n", 161 pr_debug("audio unit %d irqs already taken!\n",
162 rtd->dai->cpu_dai->id); 162 rtd->cpu_dai->id);
163 return -EBUSY; 163 return -EBUSY;
164 } 164 }
165 (void)dmabrg_request_irq(dmairq + 1, camelot_txdma, cam); 165 (void)dmabrg_request_irq(dmairq + 1, camelot_txdma, cam);
@@ -170,7 +170,7 @@ static int camelot_pcm_open(struct snd_pcm_substream *substream)
170static int camelot_pcm_close(struct snd_pcm_substream *substream) 170static int camelot_pcm_close(struct snd_pcm_substream *substream)
171{ 171{
172 struct snd_soc_pcm_runtime *rtd = substream->private_data; 172 struct snd_soc_pcm_runtime *rtd = substream->private_data;
173 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 173 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
174 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1; 174 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1;
175 int dmairq; 175 int dmairq;
176 176
@@ -191,7 +191,7 @@ static int camelot_hw_params(struct snd_pcm_substream *substream,
191 struct snd_pcm_hw_params *hw_params) 191 struct snd_pcm_hw_params *hw_params)
192{ 192{
193 struct snd_soc_pcm_runtime *rtd = substream->private_data; 193 struct snd_soc_pcm_runtime *rtd = substream->private_data;
194 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 194 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
195 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1; 195 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1;
196 int ret; 196 int ret;
197 197
@@ -219,7 +219,7 @@ static int camelot_prepare(struct snd_pcm_substream *substream)
219{ 219{
220 struct snd_pcm_runtime *runtime = substream->runtime; 220 struct snd_pcm_runtime *runtime = substream->runtime;
221 struct snd_soc_pcm_runtime *rtd = substream->private_data; 221 struct snd_soc_pcm_runtime *rtd = substream->private_data;
222 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 222 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
223 223
224 pr_debug("PCM data: addr 0x%08ulx len %d\n", 224 pr_debug("PCM data: addr 0x%08ulx len %d\n",
225 (u32)runtime->dma_addr, runtime->dma_bytes); 225 (u32)runtime->dma_addr, runtime->dma_bytes);
@@ -266,7 +266,7 @@ static inline void dmabrg_rec_dma_stop(struct camelot_pcm *cam)
266static int camelot_trigger(struct snd_pcm_substream *substream, int cmd) 266static int camelot_trigger(struct snd_pcm_substream *substream, int cmd)
267{ 267{
268 struct snd_soc_pcm_runtime *rtd = substream->private_data; 268 struct snd_soc_pcm_runtime *rtd = substream->private_data;
269 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 269 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
270 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1; 270 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1;
271 271
272 switch (cmd) { 272 switch (cmd) {
@@ -293,7 +293,7 @@ static snd_pcm_uframes_t camelot_pos(struct snd_pcm_substream *substream)
293{ 293{
294 struct snd_pcm_runtime *runtime = substream->runtime; 294 struct snd_pcm_runtime *runtime = substream->runtime;
295 struct snd_soc_pcm_runtime *rtd = substream->private_data; 295 struct snd_soc_pcm_runtime *rtd = substream->private_data;
296 struct camelot_pcm *cam = &cam_pcm_data[rtd->dai->cpu_dai->id]; 296 struct camelot_pcm *cam = &cam_pcm_data[rtd->cpu_dai->id];
297 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1; 297 int recv = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0:1;
298 unsigned long pos; 298 unsigned long pos;
299 299
@@ -342,25 +342,44 @@ static int camelot_pcm_new(struct snd_card *card,
342 return 0; 342 return 0;
343} 343}
344 344
345struct snd_soc_platform sh7760_soc_platform = { 345static struct snd_soc_platform sh7760_soc_platform = {
346 .name = "sh7760-pcm",
347 .pcm_ops = &camelot_pcm_ops, 346 .pcm_ops = &camelot_pcm_ops,
348 .pcm_new = camelot_pcm_new, 347 .pcm_new = camelot_pcm_new,
349 .pcm_free = camelot_pcm_free, 348 .pcm_free = camelot_pcm_free,
350}; 349};
351EXPORT_SYMBOL_GPL(sh7760_soc_platform);
352 350
353static int __init sh7760_soc_platform_init(void) 351static int __devinit sh7760_soc_platform_probe(struct platform_device *pdev)
354{ 352{
355 return snd_soc_register_platform(&sh7760_soc_platform); 353 return snd_soc_register_platform(&pdev->dev, &sh7760_soc_platform);
356} 354}
357module_init(sh7760_soc_platform_init);
358 355
359static void __exit sh7760_soc_platform_exit(void) 356static int __devexit sh7760_soc_platform_remove(struct platform_device *pdev)
360{ 357{
361 snd_soc_unregister_platform(&sh7760_soc_platform); 358 snd_soc_unregister_platform(&pdev->dev);
359 return 0;
360}
361
362static struct platform_driver sh7760_pcm_driver = {
363 .driver = {
364 .name = "sh7760-pcm-audio",
365 .owner = THIS_MODULE,
366 },
367
368 .probe = sh7760_soc_platform_probe,
369 .remove = __devexit_p(sh7760_soc_platform_remove),
370};
371
372static int __init snd_sh7760_pcm_init(void)
373{
374 return platform_driver_register(&sh7760_pcm_driver);
375}
376module_init(snd_sh7760_pcm_init);
377
378static void __exit snd_sh7760_pcm_exit(void)
379{
380 platform_driver_unregister(&sh7760_pcm_driver);
362} 381}
363module_exit(sh7760_soc_platform_exit); 382module_exit(snd_sh7760_pcm_exit);
364 383
365MODULE_LICENSE("GPL"); 384MODULE_LICENSE("GPL");
366MODULE_DESCRIPTION("SH7760 Audio DMA (DMABRG) driver"); 385MODULE_DESCRIPTION("SH7760 Audio DMA (DMABRG) driver");
diff --git a/sound/soc/sh/fsi-ak4642.c b/sound/soc/sh/fsi-ak4642.c
index dad575a22622..d96602de71de 100644
--- a/sound/soc/sh/fsi-ak4642.c
+++ b/sound/soc/sh/fsi-ak4642.c
@@ -11,17 +11,17 @@
11 11
12#include <linux/platform_device.h> 12#include <linux/platform_device.h>
13#include <sound/sh_fsi.h> 13#include <sound/sh_fsi.h>
14#include <../sound/soc/codecs/ak4642.h>
15 14
16static int fsi_ak4642_dai_init(struct snd_soc_codec *codec) 15static int fsi_ak4642_dai_init(struct snd_soc_pcm_runtime *rtd)
17{ 16{
17 struct snd_soc_dai *dai = rtd->codec_dai;
18 int ret; 18 int ret;
19 19
20 ret = snd_soc_dai_set_fmt(&ak4642_dai, SND_SOC_DAIFMT_CBM_CFM); 20 ret = snd_soc_dai_set_fmt(dai, SND_SOC_DAIFMT_CBM_CFM);
21 if (ret < 0) 21 if (ret < 0)
22 return ret; 22 return ret;
23 23
24 ret = snd_soc_dai_set_sysclk(&ak4642_dai, 0, 11289600, 0); 24 ret = snd_soc_dai_set_sysclk(dai, 0, 11289600, 0);
25 25
26 return ret; 26 return ret;
27} 27}
@@ -29,24 +29,25 @@ static int fsi_ak4642_dai_init(struct snd_soc_codec *codec)
29static struct snd_soc_dai_link fsi_dai_link = { 29static struct snd_soc_dai_link fsi_dai_link = {
30 .name = "AK4642", 30 .name = "AK4642",
31 .stream_name = "AK4642", 31 .stream_name = "AK4642",
32 .cpu_dai = &fsi_soc_dai[FSI_PORT_A], 32 .cpu_dai_name = "fsia-dai", /* fsi A */
33 .codec_dai = &ak4642_dai, 33 .codec_dai_name = "ak4642-hifi",
34#ifdef CONFIG_MACH_AP4EVB
35 .platform_name = "sh_fsi2",
36 .codec_name = "ak4642-codec.0-0013",
37#else
38 .platform_name = "sh_fsi.0",
39 .codec_name = "ak4642-codec.0-0012",
40#endif
34 .init = fsi_ak4642_dai_init, 41 .init = fsi_ak4642_dai_init,
35 .ops = NULL, 42 .ops = NULL,
36}; 43};
37 44
38static struct snd_soc_card fsi_soc_card = { 45static struct snd_soc_card fsi_soc_card = {
39 .name = "FSI", 46 .name = "FSI (AK4642)",
40 .platform = &fsi_soc_platform,
41 .dai_link = &fsi_dai_link, 47 .dai_link = &fsi_dai_link,
42 .num_links = 1, 48 .num_links = 1,
43}; 49};
44 50
45static struct snd_soc_device fsi_snd_devdata = {
46 .card = &fsi_soc_card,
47 .codec_dev = &soc_codec_dev_ak4642,
48};
49
50static struct platform_device *fsi_snd_device; 51static struct platform_device *fsi_snd_device;
51 52
52static int __init fsi_ak4642_init(void) 53static int __init fsi_ak4642_init(void)
@@ -57,9 +58,7 @@ static int __init fsi_ak4642_init(void)
57 if (!fsi_snd_device) 58 if (!fsi_snd_device)
58 goto out; 59 goto out;
59 60
60 platform_set_drvdata(fsi_snd_device, 61 platform_set_drvdata(fsi_snd_device, &fsi_soc_card);
61 &fsi_snd_devdata);
62 fsi_snd_devdata.dev = &fsi_snd_device->dev;
63 ret = platform_device_add(fsi_snd_device); 62 ret = platform_device_add(fsi_snd_device);
64 63
65 if (ret) 64 if (ret)
diff --git a/sound/soc/sh/fsi-da7210.c b/sound/soc/sh/fsi-da7210.c
index 121bbb07bb03..a6adb6e43250 100644
--- a/sound/soc/sh/fsi-da7210.c
+++ b/sound/soc/sh/fsi-da7210.c
@@ -12,11 +12,12 @@
12 12
13#include <linux/platform_device.h> 13#include <linux/platform_device.h>
14#include <sound/sh_fsi.h> 14#include <sound/sh_fsi.h>
15#include "../codecs/da7210.h"
16 15
17static int fsi_da7210_init(struct snd_soc_codec *codec) 16static int fsi_da7210_init(struct snd_soc_pcm_runtime *rtd)
18{ 17{
19 return snd_soc_dai_set_fmt(&da7210_dai, 18 struct snd_soc_dai *dai = rtd->codec_dai;
19
20 return snd_soc_dai_set_fmt(dai,
20 SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | 21 SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF |
21 SND_SOC_DAIFMT_CBM_CFM); 22 SND_SOC_DAIFMT_CBM_CFM);
22} 23}
@@ -24,23 +25,19 @@ static int fsi_da7210_init(struct snd_soc_codec *codec)
24static struct snd_soc_dai_link fsi_da7210_dai = { 25static struct snd_soc_dai_link fsi_da7210_dai = {
25 .name = "DA7210", 26 .name = "DA7210",
26 .stream_name = "DA7210", 27 .stream_name = "DA7210",
27 .cpu_dai = &fsi_soc_dai[FSI_PORT_B], 28 .cpu_dai_name = "fsib-dai", /* FSI B */
28 .codec_dai = &da7210_dai, 29 .codec_dai_name = "da7210-hifi",
30 .platform_name = "sh_fsi.0",
31 .codec_name = "da7210-codec.0-001a",
29 .init = fsi_da7210_init, 32 .init = fsi_da7210_init,
30}; 33};
31 34
32static struct snd_soc_card fsi_soc_card = { 35static struct snd_soc_card fsi_soc_card = {
33 .name = "FSI", 36 .name = "FSI (DA7210)",
34 .platform = &fsi_soc_platform,
35 .dai_link = &fsi_da7210_dai, 37 .dai_link = &fsi_da7210_dai,
36 .num_links = 1, 38 .num_links = 1,
37}; 39};
38 40
39static struct snd_soc_device fsi_da7210_snd_devdata = {
40 .card = &fsi_soc_card,
41 .codec_dev = &soc_codec_dev_da7210,
42};
43
44static struct platform_device *fsi_da7210_snd_device; 41static struct platform_device *fsi_da7210_snd_device;
45 42
46static int __init fsi_da7210_sound_init(void) 43static int __init fsi_da7210_sound_init(void)
@@ -51,8 +48,7 @@ static int __init fsi_da7210_sound_init(void)
51 if (!fsi_da7210_snd_device) 48 if (!fsi_da7210_snd_device)
52 return -ENOMEM; 49 return -ENOMEM;
53 50
54 platform_set_drvdata(fsi_da7210_snd_device, &fsi_da7210_snd_devdata); 51 platform_set_drvdata(fsi_da7210_snd_device, &fsi_soc_card);
55 fsi_da7210_snd_devdata.dev = &fsi_da7210_snd_device->dev;
56 ret = platform_device_add(fsi_da7210_snd_device); 52 ret = platform_device_add(fsi_da7210_snd_device);
57 if (ret) 53 if (ret)
58 platform_device_put(fsi_da7210_snd_device); 54 platform_device_put(fsi_da7210_snd_device);
diff --git a/sound/soc/sh/fsi-hdmi.c b/sound/soc/sh/fsi-hdmi.c
new file mode 100644
index 000000000000..a52dd8ec71d3
--- /dev/null
+++ b/sound/soc/sh/fsi-hdmi.c
@@ -0,0 +1,60 @@
1/*
2 * FSI - HDMI sound support
3 *
4 * Copyright (C) 2010 Renesas Solutions Corp.
5 * Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
6 *
7 * This file is subject to the terms and conditions of the GNU General Public
8 * License. See the file "COPYING" in the main directory of this archive
9 * for more details.
10 */
11
12#include <linux/platform_device.h>
13#include <sound/sh_fsi.h>
14
15static struct snd_soc_dai_link fsi_dai_link = {
16 .name = "HDMI",
17 .stream_name = "HDMI",
18 .cpu_dai_name = "fsib-dai", /* fsi B */
19 .codec_dai_name = "sh_mobile_hdmi-hifi",
20 .platform_name = "sh_fsi2",
21 .codec_name = "sh-mobile-hdmi",
22};
23
24static struct snd_soc_card fsi_soc_card = {
25 .name = "FSI (SH MOBILE HDMI)",
26 .dai_link = &fsi_dai_link,
27 .num_links = 1,
28};
29
30static struct platform_device *fsi_snd_device;
31
32static int __init fsi_hdmi_init(void)
33{
34 int ret = -ENOMEM;
35
36 fsi_snd_device = platform_device_alloc("soc-audio", FSI_PORT_B);
37 if (!fsi_snd_device)
38 goto out;
39
40 platform_set_drvdata(fsi_snd_device, &fsi_soc_card);
41 ret = platform_device_add(fsi_snd_device);
42
43 if (ret)
44 platform_device_put(fsi_snd_device);
45
46out:
47 return ret;
48}
49
50static void __exit fsi_hdmi_exit(void)
51{
52 platform_device_unregister(fsi_snd_device);
53}
54
55module_init(fsi_hdmi_init);
56module_exit(fsi_hdmi_exit);
57
58MODULE_LICENSE("GPL");
59MODULE_DESCRIPTION("Generic SH4 FSI-HDMI sound card");
60MODULE_AUTHOR("Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>");
diff --git a/sound/soc/sh/fsi.c b/sound/soc/sh/fsi.c
index 58c6bec642de..507e709f2807 100644
--- a/sound/soc/sh/fsi.c
+++ b/sound/soc/sh/fsi.c
@@ -80,11 +80,12 @@
80#define B_CLK 0x00000010 80#define B_CLK 0x00000010
81#define A_CLK 0x00000001 81#define A_CLK 0x00000001
82 82
83/* INT_ST */ 83/* IO SHIFT / MACRO */
84#define INT_B_IN (1 << 12) 84#define BI_SHIFT 12
85#define INT_B_OUT (1 << 8) 85#define BO_SHIFT 8
86#define INT_A_IN (1 << 4) 86#define AI_SHIFT 4
87#define INT_A_OUT (1 << 0) 87#define AO_SHIFT 0
88#define AB_IO(param, shift) (param << shift)
88 89
89/* SOFT_RST */ 90/* SOFT_RST */
90#define PBSR (1 << 12) /* Port B Software Reset */ 91#define PBSR (1 << 12) /* Port B Software Reset */
@@ -93,33 +94,43 @@
93#define FSISR (1 << 0) /* Software Reset */ 94#define FSISR (1 << 0) /* Software Reset */
94 95
95/* FIFO_SZ */ 96/* FIFO_SZ */
96#define OUT_SZ_MASK 0x7 97#define FIFO_SZ_MASK 0x7
97#define BO_SZ_SHIFT 8
98#define AO_SZ_SHIFT 0
99 98
100#define FSI_RATES SNDRV_PCM_RATE_8000_96000 99#define FSI_RATES SNDRV_PCM_RATE_8000_96000
101 100
102#define FSI_FMTS (SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S16_LE) 101#define FSI_FMTS (SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S16_LE)
103 102
104/************************************************************************ 103/*
104 * FSI driver use below type name for variable
105 *
106 * xxx_len : data length
107 * xxx_width : data width
108 * xxx_offset : data offset
109 * xxx_num : number of data
110 */
111
112/*
113 * struct
114 */
105 115
116struct fsi_stream {
117 struct snd_pcm_substream *substream;
106 118
107 struct 119 int fifo_max_num;
120 int chan_num;
108 121
122 int buff_offset;
123 int buff_len;
124 int period_len;
125 int period_num;
126};
109 127
110************************************************************************/
111struct fsi_priv { 128struct fsi_priv {
112 void __iomem *base; 129 void __iomem *base;
113 struct snd_pcm_substream *substream;
114 struct fsi_master *master; 130 struct fsi_master *master;
115 131
116 int fifo_max; 132 struct fsi_stream playback;
117 int chan; 133 struct fsi_stream capture;
118
119 int byte_offset;
120 int period_len;
121 int buffer_len;
122 int periods;
123 134
124 u32 mst_ctrl; 135 u32 mst_ctrl;
125}; 136};
@@ -142,13 +153,10 @@ struct fsi_master {
142 spinlock_t lock; 153 spinlock_t lock;
143}; 154};
144 155
145/************************************************************************ 156/*
146 157 * basic read write function
147 158 */
148 basic read write function
149
150 159
151************************************************************************/
152static void __fsi_reg_write(u32 reg, u32 data) 160static void __fsi_reg_write(u32 reg, u32 data)
153{ 161{
154 /* valid data area is 24bit */ 162 /* valid data area is 24bit */
@@ -251,13 +259,10 @@ static void fsi_master_mask_set(struct fsi_master *master,
251 spin_unlock_irqrestore(&master->lock, flags); 259 spin_unlock_irqrestore(&master->lock, flags);
252} 260}
253 261
254/************************************************************************ 262/*
255 263 * basic function
256 264 */
257 basic function
258
259 265
260************************************************************************/
261static struct fsi_master *fsi_get_master(struct fsi_priv *fsi) 266static struct fsi_master *fsi_get_master(struct fsi_priv *fsi)
262{ 267{
263 return fsi->master; 268 return fsi->master;
@@ -271,16 +276,19 @@ static int fsi_is_port_a(struct fsi_priv *fsi)
271static struct snd_soc_dai *fsi_get_dai(struct snd_pcm_substream *substream) 276static struct snd_soc_dai *fsi_get_dai(struct snd_pcm_substream *substream)
272{ 277{
273 struct snd_soc_pcm_runtime *rtd = substream->private_data; 278 struct snd_soc_pcm_runtime *rtd = substream->private_data;
274 struct snd_soc_dai_link *machine = rtd->dai;
275 279
276 return machine->cpu_dai; 280 return rtd->cpu_dai;
277} 281}
278 282
279static struct fsi_priv *fsi_get_priv(struct snd_pcm_substream *substream) 283static struct fsi_priv *fsi_get_priv(struct snd_pcm_substream *substream)
280{ 284{
281 struct snd_soc_dai *dai = fsi_get_dai(substream); 285 struct snd_soc_dai *dai = fsi_get_dai(substream);
286 struct fsi_master *master = snd_soc_dai_get_drvdata(dai);
282 287
283 return dai->private_data; 288 if (dai->id == 0)
289 return &master->fsia;
290 else
291 return &master->fsib;
284} 292}
285 293
286static u32 fsi_get_info_flags(struct fsi_priv *fsi) 294static u32 fsi_get_info_flags(struct fsi_priv *fsi)
@@ -292,6 +300,22 @@ static u32 fsi_get_info_flags(struct fsi_priv *fsi)
292 master->info->portb_flags; 300 master->info->portb_flags;
293} 301}
294 302
303static inline int fsi_stream_is_play(int stream)
304{
305 return stream == SNDRV_PCM_STREAM_PLAYBACK;
306}
307
308static inline int fsi_is_play(struct snd_pcm_substream *substream)
309{
310 return fsi_stream_is_play(substream->stream);
311}
312
313static inline struct fsi_stream *fsi_get_stream(struct fsi_priv *fsi,
314 int is_play)
315{
316 return is_play ? &fsi->playback : &fsi->capture;
317}
318
295static int fsi_is_master_mode(struct fsi_priv *fsi, int is_play) 319static int fsi_is_master_mode(struct fsi_priv *fsi, int is_play)
296{ 320{
297 u32 mode; 321 u32 mode;
@@ -307,63 +331,144 @@ static int fsi_is_master_mode(struct fsi_priv *fsi, int is_play)
307 return (mode & flags) != mode; 331 return (mode & flags) != mode;
308} 332}
309 333
310static u32 fsi_port_ab_io_bit(struct fsi_priv *fsi, int is_play) 334static u32 fsi_get_port_shift(struct fsi_priv *fsi, int is_play)
311{ 335{
312 int is_porta = fsi_is_port_a(fsi); 336 int is_porta = fsi_is_port_a(fsi);
313 u32 data; 337 u32 shift;
314 338
315 if (is_porta) 339 if (is_porta)
316 data = is_play ? (1 << 0) : (1 << 4); 340 shift = is_play ? AO_SHIFT : AI_SHIFT;
317 else 341 else
318 data = is_play ? (1 << 8) : (1 << 12); 342 shift = is_play ? BO_SHIFT : BI_SHIFT;
319 343
320 return data; 344 return shift;
321} 345}
322 346
323static void fsi_stream_push(struct fsi_priv *fsi, 347static void fsi_stream_push(struct fsi_priv *fsi,
348 int is_play,
324 struct snd_pcm_substream *substream, 349 struct snd_pcm_substream *substream,
325 u32 buffer_len, 350 u32 buffer_len,
326 u32 period_len) 351 u32 period_len)
327{ 352{
328 fsi->substream = substream; 353 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
329 fsi->buffer_len = buffer_len; 354
330 fsi->period_len = period_len; 355 io->substream = substream;
331 fsi->byte_offset = 0; 356 io->buff_len = buffer_len;
332 fsi->periods = 0; 357 io->buff_offset = 0;
358 io->period_len = period_len;
359 io->period_num = 0;
333} 360}
334 361
335static void fsi_stream_pop(struct fsi_priv *fsi) 362static void fsi_stream_pop(struct fsi_priv *fsi, int is_play)
336{ 363{
337 fsi->substream = NULL; 364 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
338 fsi->buffer_len = 0; 365
339 fsi->period_len = 0; 366 io->substream = NULL;
340 fsi->byte_offset = 0; 367 io->buff_len = 0;
341 fsi->periods = 0; 368 io->buff_offset = 0;
369 io->period_len = 0;
370 io->period_num = 0;
342} 371}
343 372
344static int fsi_get_fifo_residue(struct fsi_priv *fsi, int is_play) 373static int fsi_get_fifo_data_num(struct fsi_priv *fsi, int is_play)
345{ 374{
346 u32 status; 375 u32 status;
347 u32 reg = is_play ? DOFF_ST : DIFF_ST; 376 u32 reg = is_play ? DOFF_ST : DIFF_ST;
348 int residue; 377 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
378 int data_num;
349 379
350 status = fsi_reg_read(fsi, reg); 380 status = fsi_reg_read(fsi, reg);
351 residue = 0x1ff & (status >> 8); 381 data_num = 0x1ff & (status >> 8);
352 residue *= fsi->chan; 382 data_num *= io->chan_num;
383
384 return data_num;
385}
386
387static int fsi_len2num(int len, int width)
388{
389 return len / width;
390}
391
392#define fsi_num2offset(a, b) fsi_num2len(a, b)
393static int fsi_num2len(int num, int width)
394{
395 return num * width;
396}
397
398static int fsi_get_frame_width(struct fsi_priv *fsi, int is_play)
399{
400 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
401 struct snd_pcm_substream *substream = io->substream;
402 struct snd_pcm_runtime *runtime = substream->runtime;
403
404 return frames_to_bytes(runtime, 1) / io->chan_num;
405}
406
407/*
408 * dma function
409 */
410
411static u8 *fsi_dma_get_area(struct fsi_priv *fsi, int stream)
412{
413 int is_play = fsi_stream_is_play(stream);
414 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
415
416 return io->substream->runtime->dma_area + io->buff_offset;
417}
418
419static void fsi_dma_soft_push16(struct fsi_priv *fsi, int num)
420{
421 u16 *start;
422 int i;
423
424 start = (u16 *)fsi_dma_get_area(fsi, SNDRV_PCM_STREAM_PLAYBACK);
425
426 for (i = 0; i < num; i++)
427 fsi_reg_write(fsi, DODT, ((u32)*(start + i) << 8));
428}
429
430static void fsi_dma_soft_pop16(struct fsi_priv *fsi, int num)
431{
432 u16 *start;
433 int i;
353 434
354 return residue; 435 start = (u16 *)fsi_dma_get_area(fsi, SNDRV_PCM_STREAM_CAPTURE);
436
437
438 for (i = 0; i < num; i++)
439 *(start + i) = (u16)(fsi_reg_read(fsi, DIDT) >> 8);
355} 440}
356 441
357/************************************************************************ 442static void fsi_dma_soft_push32(struct fsi_priv *fsi, int num)
443{
444 u32 *start;
445 int i;
446
447 start = (u32 *)fsi_dma_get_area(fsi, SNDRV_PCM_STREAM_PLAYBACK);
448
449
450 for (i = 0; i < num; i++)
451 fsi_reg_write(fsi, DODT, *(start + i));
452}
358 453
454static void fsi_dma_soft_pop32(struct fsi_priv *fsi, int num)
455{
456 u32 *start;
457 int i;
359 458
360 irq function 459 start = (u32 *)fsi_dma_get_area(fsi, SNDRV_PCM_STREAM_CAPTURE);
361 460
461 for (i = 0; i < num; i++)
462 *(start + i) = fsi_reg_read(fsi, DIDT);
463}
464
465/*
466 * irq function
467 */
362 468
363************************************************************************/
364static void fsi_irq_enable(struct fsi_priv *fsi, int is_play) 469static void fsi_irq_enable(struct fsi_priv *fsi, int is_play)
365{ 470{
366 u32 data = fsi_port_ab_io_bit(fsi, is_play); 471 u32 data = AB_IO(1, fsi_get_port_shift(fsi, is_play));
367 struct fsi_master *master = fsi_get_master(fsi); 472 struct fsi_master *master = fsi_get_master(fsi);
368 473
369 fsi_master_mask_set(master, master->core->imsk, data, data); 474 fsi_master_mask_set(master, master->core->imsk, data, data);
@@ -372,7 +477,7 @@ static void fsi_irq_enable(struct fsi_priv *fsi, int is_play)
372 477
373static void fsi_irq_disable(struct fsi_priv *fsi, int is_play) 478static void fsi_irq_disable(struct fsi_priv *fsi, int is_play)
374{ 479{
375 u32 data = fsi_port_ab_io_bit(fsi, is_play); 480 u32 data = AB_IO(1, fsi_get_port_shift(fsi, is_play));
376 struct fsi_master *master = fsi_get_master(fsi); 481 struct fsi_master *master = fsi_get_master(fsi);
377 482
378 fsi_master_mask_set(master, master->core->imsk, data, 0); 483 fsi_master_mask_set(master, master->core->imsk, data, 0);
@@ -394,20 +499,18 @@ static void fsi_irq_clear_status(struct fsi_priv *fsi)
394 u32 data = 0; 499 u32 data = 0;
395 struct fsi_master *master = fsi_get_master(fsi); 500 struct fsi_master *master = fsi_get_master(fsi);
396 501
397 data |= fsi_port_ab_io_bit(fsi, 0); 502 data |= AB_IO(1, fsi_get_port_shift(fsi, 0));
398 data |= fsi_port_ab_io_bit(fsi, 1); 503 data |= AB_IO(1, fsi_get_port_shift(fsi, 1));
399 504
400 /* clear interrupt factor */ 505 /* clear interrupt factor */
401 fsi_master_mask_set(master, master->core->int_st, data, 0); 506 fsi_master_mask_set(master, master->core->int_st, data, 0);
402} 507}
403 508
404/************************************************************************ 509/*
405 510 * SPDIF master clock function
406 511 *
407 SPDIF master clock function 512 * These functions are used later FSI2
408 513 */
409These functions are used later FSI2
410************************************************************************/
411static void fsi_spdif_clk_ctrl(struct fsi_priv *fsi, int enable) 514static void fsi_spdif_clk_ctrl(struct fsi_priv *fsi, int enable)
412{ 515{
413 struct fsi_master *master = fsi_get_master(fsi); 516 struct fsi_master *master = fsi_get_master(fsi);
@@ -424,13 +527,10 @@ static void fsi_spdif_clk_ctrl(struct fsi_priv *fsi, int enable)
424 fsi_master_mask_set(master, fsi->mst_ctrl, val, 0); 527 fsi_master_mask_set(master, fsi->mst_ctrl, val, 0);
425} 528}
426 529
427/************************************************************************ 530/*
428 531 * ctrl function
429 532 */
430 ctrl function
431
432 533
433************************************************************************/
434static void fsi_clk_ctrl(struct fsi_priv *fsi, int enable) 534static void fsi_clk_ctrl(struct fsi_priv *fsi, int enable)
435{ 535{
436 u32 val = fsi_is_port_a(fsi) ? (1 << 0) : (1 << 4); 536 u32 val = fsi_is_port_a(fsi) ? (1 << 0) : (1 << 4);
@@ -447,14 +547,15 @@ static void fsi_fifo_init(struct fsi_priv *fsi,
447 struct snd_soc_dai *dai) 547 struct snd_soc_dai *dai)
448{ 548{
449 struct fsi_master *master = fsi_get_master(fsi); 549 struct fsi_master *master = fsi_get_master(fsi);
550 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
450 u32 ctrl, shift, i; 551 u32 ctrl, shift, i;
451 552
452 /* get on-chip RAM capacity */ 553 /* get on-chip RAM capacity */
453 shift = fsi_master_read(master, FIFO_SZ); 554 shift = fsi_master_read(master, FIFO_SZ);
454 shift >>= fsi_is_port_a(fsi) ? AO_SZ_SHIFT : BO_SZ_SHIFT; 555 shift >>= fsi_get_port_shift(fsi, is_play);
455 shift &= OUT_SZ_MASK; 556 shift &= FIFO_SZ_MASK;
456 fsi->fifo_max = 256 << shift; 557 io->fifo_max_num = 256 << shift;
457 dev_dbg(dai->dev, "fifo = %d words\n", fsi->fifo_max); 558 dev_dbg(dai->dev, "fifo = %d words\n", io->fifo_max_num);
458 559
459 /* 560 /*
460 * The maximum number of sample data varies depending 561 * The maximum number of sample data varies depending
@@ -475,9 +576,10 @@ static void fsi_fifo_init(struct fsi_priv *fsi,
475 * 7 channels: 32 ( 32 x 7 = 224) 576 * 7 channels: 32 ( 32 x 7 = 224)
476 * 8 channels: 32 ( 32 x 8 = 256) 577 * 8 channels: 32 ( 32 x 8 = 256)
477 */ 578 */
478 for (i = 1; i < fsi->chan; i <<= 1) 579 for (i = 1; i < io->chan_num; i <<= 1)
479 fsi->fifo_max >>= 1; 580 io->fifo_max_num >>= 1;
480 dev_dbg(dai->dev, "%d channel %d store\n", fsi->chan, fsi->fifo_max); 581 dev_dbg(dai->dev, "%d channel %d store\n",
582 io->chan_num, io->fifo_max_num);
481 583
482 ctrl = is_play ? DOFF_CTL : DIFF_CTL; 584 ctrl = is_play ? DOFF_CTL : DIFF_CTL;
483 585
@@ -500,84 +602,114 @@ static void fsi_soft_all_reset(struct fsi_master *master)
500 mdelay(10); 602 mdelay(10);
501} 603}
502 604
503/* playback interrupt */ 605static int fsi_fifo_data_ctrl(struct fsi_priv *fsi, int startup, int stream)
504static int fsi_data_push(struct fsi_priv *fsi, int startup)
505{ 606{
506 struct snd_pcm_runtime *runtime; 607 struct snd_pcm_runtime *runtime;
507 struct snd_pcm_substream *substream = NULL; 608 struct snd_pcm_substream *substream = NULL;
508 u32 status; 609 int is_play = fsi_stream_is_play(stream);
509 int send; 610 struct fsi_stream *io = fsi_get_stream(fsi, is_play);
510 int fifo_free; 611 u32 status_reg = is_play ? DOFF_ST : DIFF_ST;
511 int width; 612 int data_residue_num;
512 u8 *start; 613 int data_num;
513 int i, over_period; 614 int data_num_max;
615 int ch_width;
616 int over_period;
617 void (*fn)(struct fsi_priv *fsi, int size);
514 618
515 if (!fsi || 619 if (!fsi ||
516 !fsi->substream || 620 !io->substream ||
517 !fsi->substream->runtime) 621 !io->substream->runtime)
518 return -EINVAL; 622 return -EINVAL;
519 623
520 over_period = 0; 624 over_period = 0;
521 substream = fsi->substream; 625 substream = io->substream;
522 runtime = substream->runtime; 626 runtime = substream->runtime;
523 627
524 /* FSI FIFO has limit. 628 /* FSI FIFO has limit.
525 * So, this driver can not send periods data at a time 629 * So, this driver can not send periods data at a time
526 */ 630 */
527 if (fsi->byte_offset >= 631 if (io->buff_offset >=
528 fsi->period_len * (fsi->periods + 1)) { 632 fsi_num2offset(io->period_num + 1, io->period_len)) {
529 633
530 over_period = 1; 634 over_period = 1;
531 fsi->periods = (fsi->periods + 1) % runtime->periods; 635 io->period_num = (io->period_num + 1) % runtime->periods;
532 636
533 if (0 == fsi->periods) 637 if (0 == io->period_num)
534 fsi->byte_offset = 0; 638 io->buff_offset = 0;
535 } 639 }
536 640
537 /* get 1 channel data width */ 641 /* get 1 channel data width */
538 width = frames_to_bytes(runtime, 1) / fsi->chan; 642 ch_width = fsi_get_frame_width(fsi, is_play);
539 643
540 /* get send size for alsa */ 644 /* get residue data number of alsa */
541 send = (fsi->buffer_len - fsi->byte_offset) / width; 645 data_residue_num = fsi_len2num(io->buff_len - io->buff_offset,
542 646 ch_width);
543 /* get FIFO free size */ 647
544 fifo_free = (fsi->fifo_max * fsi->chan) - fsi_get_fifo_residue(fsi, 1); 648 if (is_play) {
545 649 /*
546 /* size check */ 650 * for play-back
547 if (fifo_free < send) 651 *
548 send = fifo_free; 652 * data_num_max : number of FSI fifo free space
653 * data_num : number of ALSA residue data
654 */
655 data_num_max = io->fifo_max_num * io->chan_num;
656 data_num_max -= fsi_get_fifo_data_num(fsi, is_play);
657
658 data_num = data_residue_num;
659
660 switch (ch_width) {
661 case 2:
662 fn = fsi_dma_soft_push16;
663 break;
664 case 4:
665 fn = fsi_dma_soft_push32;
666 break;
667 default:
668 return -EINVAL;
669 }
670 } else {
671 /*
672 * for capture
673 *
674 * data_num_max : number of ALSA free space
675 * data_num : number of data in FSI fifo
676 */
677 data_num_max = data_residue_num;
678 data_num = fsi_get_fifo_data_num(fsi, is_play);
679
680 switch (ch_width) {
681 case 2:
682 fn = fsi_dma_soft_pop16;
683 break;
684 case 4:
685 fn = fsi_dma_soft_pop32;
686 break;
687 default:
688 return -EINVAL;
689 }
690 }
549 691
550 start = runtime->dma_area; 692 data_num = min(data_num, data_num_max);
551 start += fsi->byte_offset;
552 693
553 switch (width) { 694 fn(fsi, data_num);
554 case 2:
555 for (i = 0; i < send; i++)
556 fsi_reg_write(fsi, DODT,
557 ((u32)*((u16 *)start + i) << 8));
558 break;
559 case 4:
560 for (i = 0; i < send; i++)
561 fsi_reg_write(fsi, DODT, *((u32 *)start + i));
562 break;
563 default:
564 return -EINVAL;
565 }
566 695
567 fsi->byte_offset += send * width; 696 /* update buff_offset */
697 io->buff_offset += fsi_num2offset(data_num, ch_width);
568 698
569 status = fsi_reg_read(fsi, DOFF_ST); 699 /* check fifo status */
570 if (!startup) { 700 if (!startup) {
571 struct snd_soc_dai *dai = fsi_get_dai(substream); 701 struct snd_soc_dai *dai = fsi_get_dai(substream);
702 u32 status = fsi_reg_read(fsi, status_reg);
572 703
573 if (status & ERR_OVER) 704 if (status & ERR_OVER)
574 dev_err(dai->dev, "over run\n"); 705 dev_err(dai->dev, "over run\n");
575 if (status & ERR_UNDER) 706 if (status & ERR_UNDER)
576 dev_err(dai->dev, "under run\n"); 707 dev_err(dai->dev, "under run\n");
577 } 708 }
578 fsi_reg_write(fsi, DOFF_ST, 0); 709 fsi_reg_write(fsi, status_reg, 0);
579 710
580 fsi_irq_enable(fsi, 1); 711 /* re-enable irq */
712 fsi_irq_enable(fsi, is_play);
581 713
582 if (over_period) 714 if (over_period)
583 snd_pcm_period_elapsed(substream); 715 snd_pcm_period_elapsed(substream);
@@ -587,85 +719,12 @@ static int fsi_data_push(struct fsi_priv *fsi, int startup)
587 719
588static int fsi_data_pop(struct fsi_priv *fsi, int startup) 720static int fsi_data_pop(struct fsi_priv *fsi, int startup)
589{ 721{
590 struct snd_pcm_runtime *runtime; 722 return fsi_fifo_data_ctrl(fsi, startup, SNDRV_PCM_STREAM_CAPTURE);
591 struct snd_pcm_substream *substream = NULL; 723}
592 u32 status;
593 int free;
594 int fifo_fill;
595 int width;
596 u8 *start;
597 int i, over_period;
598
599 if (!fsi ||
600 !fsi->substream ||
601 !fsi->substream->runtime)
602 return -EINVAL;
603
604 over_period = 0;
605 substream = fsi->substream;
606 runtime = substream->runtime;
607
608 /* FSI FIFO has limit.
609 * So, this driver can not send periods data at a time
610 */
611 if (fsi->byte_offset >=
612 fsi->period_len * (fsi->periods + 1)) {
613
614 over_period = 1;
615 fsi->periods = (fsi->periods + 1) % runtime->periods;
616
617 if (0 == fsi->periods)
618 fsi->byte_offset = 0;
619 }
620
621 /* get 1 channel data width */
622 width = frames_to_bytes(runtime, 1) / fsi->chan;
623
624 /* get free space for alsa */
625 free = (fsi->buffer_len - fsi->byte_offset) / width;
626
627 /* get recv size */
628 fifo_fill = fsi_get_fifo_residue(fsi, 0);
629
630 if (free < fifo_fill)
631 fifo_fill = free;
632
633 start = runtime->dma_area;
634 start += fsi->byte_offset;
635
636 switch (width) {
637 case 2:
638 for (i = 0; i < fifo_fill; i++)
639 *((u16 *)start + i) =
640 (u16)(fsi_reg_read(fsi, DIDT) >> 8);
641 break;
642 case 4:
643 for (i = 0; i < fifo_fill; i++)
644 *((u32 *)start + i) = fsi_reg_read(fsi, DIDT);
645 break;
646 default:
647 return -EINVAL;
648 }
649
650 fsi->byte_offset += fifo_fill * width;
651
652 status = fsi_reg_read(fsi, DIFF_ST);
653 if (!startup) {
654 struct snd_soc_dai *dai = fsi_get_dai(substream);
655
656 if (status & ERR_OVER)
657 dev_err(dai->dev, "over run\n");
658 if (status & ERR_UNDER)
659 dev_err(dai->dev, "under run\n");
660 }
661 fsi_reg_write(fsi, DIFF_ST, 0);
662
663 fsi_irq_enable(fsi, 0);
664
665 if (over_period)
666 snd_pcm_period_elapsed(substream);
667 724
668 return 0; 725static int fsi_data_push(struct fsi_priv *fsi, int startup)
726{
727 return fsi_fifo_data_ctrl(fsi, startup, SNDRV_PCM_STREAM_PLAYBACK);
669} 728}
670 729
671static irqreturn_t fsi_interrupt(int irq, void *data) 730static irqreturn_t fsi_interrupt(int irq, void *data)
@@ -677,13 +736,13 @@ static irqreturn_t fsi_interrupt(int irq, void *data)
677 fsi_master_mask_set(master, SOFT_RST, IR, 0); 736 fsi_master_mask_set(master, SOFT_RST, IR, 0);
678 fsi_master_mask_set(master, SOFT_RST, IR, IR); 737 fsi_master_mask_set(master, SOFT_RST, IR, IR);
679 738
680 if (int_st & INT_A_OUT) 739 if (int_st & AB_IO(1, AO_SHIFT))
681 fsi_data_push(&master->fsia, 0); 740 fsi_data_push(&master->fsia, 0);
682 if (int_st & INT_B_OUT) 741 if (int_st & AB_IO(1, BO_SHIFT))
683 fsi_data_push(&master->fsib, 0); 742 fsi_data_push(&master->fsib, 0);
684 if (int_st & INT_A_IN) 743 if (int_st & AB_IO(1, AI_SHIFT))
685 fsi_data_pop(&master->fsia, 0); 744 fsi_data_pop(&master->fsia, 0);
686 if (int_st & INT_B_IN) 745 if (int_st & AB_IO(1, BI_SHIFT))
687 fsi_data_pop(&master->fsib, 0); 746 fsi_data_pop(&master->fsib, 0);
688 747
689 fsi_irq_clear_all_status(master); 748 fsi_irq_clear_all_status(master);
@@ -691,25 +750,24 @@ static irqreturn_t fsi_interrupt(int irq, void *data)
691 return IRQ_HANDLED; 750 return IRQ_HANDLED;
692} 751}
693 752
694/************************************************************************ 753/*
695 754 * dai ops
696 755 */
697 dai ops
698
699 756
700************************************************************************/
701static int fsi_dai_startup(struct snd_pcm_substream *substream, 757static int fsi_dai_startup(struct snd_pcm_substream *substream,
702 struct snd_soc_dai *dai) 758 struct snd_soc_dai *dai)
703{ 759{
704 struct fsi_priv *fsi = fsi_get_priv(substream); 760 struct fsi_priv *fsi = fsi_get_priv(substream);
705 u32 flags = fsi_get_info_flags(fsi);
706 struct fsi_master *master = fsi_get_master(fsi); 761 struct fsi_master *master = fsi_get_master(fsi);
762 struct fsi_stream *io;
763 u32 flags = fsi_get_info_flags(fsi);
707 u32 fmt; 764 u32 fmt;
708 u32 reg; 765 u32 reg;
709 u32 data; 766 u32 data;
710 int is_play = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK); 767 int is_play = fsi_is_play(substream);
711 int is_master; 768 int is_master;
712 int ret = 0; 769
770 io = fsi_get_stream(fsi, is_play);
713 771
714 pm_runtime_get_sync(dai->dev); 772 pm_runtime_get_sync(dai->dev);
715 773
@@ -741,29 +799,29 @@ static int fsi_dai_startup(struct snd_pcm_substream *substream,
741 switch (fmt) { 799 switch (fmt) {
742 case SH_FSI_FMT_MONO: 800 case SH_FSI_FMT_MONO:
743 data = CR_MONO; 801 data = CR_MONO;
744 fsi->chan = 1; 802 io->chan_num = 1;
745 break; 803 break;
746 case SH_FSI_FMT_MONO_DELAY: 804 case SH_FSI_FMT_MONO_DELAY:
747 data = CR_MONO_D; 805 data = CR_MONO_D;
748 fsi->chan = 1; 806 io->chan_num = 1;
749 break; 807 break;
750 case SH_FSI_FMT_PCM: 808 case SH_FSI_FMT_PCM:
751 data = CR_PCM; 809 data = CR_PCM;
752 fsi->chan = 2; 810 io->chan_num = 2;
753 break; 811 break;
754 case SH_FSI_FMT_I2S: 812 case SH_FSI_FMT_I2S:
755 data = CR_I2S; 813 data = CR_I2S;
756 fsi->chan = 2; 814 io->chan_num = 2;
757 break; 815 break;
758 case SH_FSI_FMT_TDM: 816 case SH_FSI_FMT_TDM:
759 fsi->chan = is_play ? 817 io->chan_num = is_play ?
760 SH_FSI_GET_CH_O(flags) : SH_FSI_GET_CH_I(flags); 818 SH_FSI_GET_CH_O(flags) : SH_FSI_GET_CH_I(flags);
761 data = CR_TDM | (fsi->chan - 1); 819 data = CR_TDM | (io->chan_num - 1);
762 break; 820 break;
763 case SH_FSI_FMT_TDM_DELAY: 821 case SH_FSI_FMT_TDM_DELAY:
764 fsi->chan = is_play ? 822 io->chan_num = is_play ?
765 SH_FSI_GET_CH_O(flags) : SH_FSI_GET_CH_I(flags); 823 SH_FSI_GET_CH_O(flags) : SH_FSI_GET_CH_I(flags);
766 data = CR_TDM_D | (fsi->chan - 1); 824 data = CR_TDM_D | (io->chan_num - 1);
767 break; 825 break;
768 case SH_FSI_FMT_SPDIF: 826 case SH_FSI_FMT_SPDIF:
769 if (master->core->ver < 2) { 827 if (master->core->ver < 2) {
@@ -771,7 +829,7 @@ static int fsi_dai_startup(struct snd_pcm_substream *substream,
771 return -EINVAL; 829 return -EINVAL;
772 } 830 }
773 data = CR_SPDIF; 831 data = CR_SPDIF;
774 fsi->chan = 2; 832 io->chan_num = 2;
775 fsi_spdif_clk_ctrl(fsi, 1); 833 fsi_spdif_clk_ctrl(fsi, 1);
776 fsi_reg_mask_set(fsi, OUT_SEL, 0x0010, 0x0010); 834 fsi_reg_mask_set(fsi, OUT_SEL, 0x0010, 0x0010);
777 break; 835 break;
@@ -788,14 +846,14 @@ static int fsi_dai_startup(struct snd_pcm_substream *substream,
788 /* fifo init */ 846 /* fifo init */
789 fsi_fifo_init(fsi, is_play, dai); 847 fsi_fifo_init(fsi, is_play, dai);
790 848
791 return ret; 849 return 0;
792} 850}
793 851
794static void fsi_dai_shutdown(struct snd_pcm_substream *substream, 852static void fsi_dai_shutdown(struct snd_pcm_substream *substream,
795 struct snd_soc_dai *dai) 853 struct snd_soc_dai *dai)
796{ 854{
797 struct fsi_priv *fsi = fsi_get_priv(substream); 855 struct fsi_priv *fsi = fsi_get_priv(substream);
798 int is_play = substream->stream == SNDRV_PCM_STREAM_PLAYBACK; 856 int is_play = fsi_is_play(substream);
799 857
800 fsi_irq_disable(fsi, is_play); 858 fsi_irq_disable(fsi, is_play);
801 fsi_clk_ctrl(fsi, 0); 859 fsi_clk_ctrl(fsi, 0);
@@ -808,19 +866,19 @@ static int fsi_dai_trigger(struct snd_pcm_substream *substream, int cmd,
808{ 866{
809 struct fsi_priv *fsi = fsi_get_priv(substream); 867 struct fsi_priv *fsi = fsi_get_priv(substream);
810 struct snd_pcm_runtime *runtime = substream->runtime; 868 struct snd_pcm_runtime *runtime = substream->runtime;
811 int is_play = substream->stream == SNDRV_PCM_STREAM_PLAYBACK; 869 int is_play = fsi_is_play(substream);
812 int ret = 0; 870 int ret = 0;
813 871
814 switch (cmd) { 872 switch (cmd) {
815 case SNDRV_PCM_TRIGGER_START: 873 case SNDRV_PCM_TRIGGER_START:
816 fsi_stream_push(fsi, substream, 874 fsi_stream_push(fsi, is_play, substream,
817 frames_to_bytes(runtime, runtime->buffer_size), 875 frames_to_bytes(runtime, runtime->buffer_size),
818 frames_to_bytes(runtime, runtime->period_size)); 876 frames_to_bytes(runtime, runtime->period_size));
819 ret = is_play ? fsi_data_push(fsi, 1) : fsi_data_pop(fsi, 1); 877 ret = is_play ? fsi_data_push(fsi, 1) : fsi_data_pop(fsi, 1);
820 break; 878 break;
821 case SNDRV_PCM_TRIGGER_STOP: 879 case SNDRV_PCM_TRIGGER_STOP:
822 fsi_irq_disable(fsi, is_play); 880 fsi_irq_disable(fsi, is_play);
823 fsi_stream_pop(fsi); 881 fsi_stream_pop(fsi, is_play);
824 break; 882 break;
825 } 883 }
826 884
@@ -835,7 +893,7 @@ static int fsi_dai_hw_params(struct snd_pcm_substream *substream,
835 struct fsi_master *master = fsi_get_master(fsi); 893 struct fsi_master *master = fsi_get_master(fsi);
836 int (*set_rate)(int is_porta, int rate) = master->info->set_rate; 894 int (*set_rate)(int is_porta, int rate) = master->info->set_rate;
837 int fsi_ver = master->core->ver; 895 int fsi_ver = master->core->ver;
838 int is_play = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK); 896 int is_play = fsi_is_play(substream);
839 int ret; 897 int ret;
840 898
841 /* if slave mode, set_rate is not needed */ 899 /* if slave mode, set_rate is not needed */
@@ -916,13 +974,10 @@ static struct snd_soc_dai_ops fsi_dai_ops = {
916 .hw_params = fsi_dai_hw_params, 974 .hw_params = fsi_dai_hw_params,
917}; 975};
918 976
919/************************************************************************ 977/*
920 978 * pcm ops
921 979 */
922 pcm ops
923
924 980
925************************************************************************/
926static struct snd_pcm_hardware fsi_pcm_hardware = { 981static struct snd_pcm_hardware fsi_pcm_hardware = {
927 .info = SNDRV_PCM_INFO_INTERLEAVED | 982 .info = SNDRV_PCM_INFO_INTERLEAVED |
928 SNDRV_PCM_INFO_MMAP | 983 SNDRV_PCM_INFO_MMAP |
@@ -971,9 +1026,10 @@ static snd_pcm_uframes_t fsi_pointer(struct snd_pcm_substream *substream)
971{ 1026{
972 struct snd_pcm_runtime *runtime = substream->runtime; 1027 struct snd_pcm_runtime *runtime = substream->runtime;
973 struct fsi_priv *fsi = fsi_get_priv(substream); 1028 struct fsi_priv *fsi = fsi_get_priv(substream);
1029 struct fsi_stream *io = fsi_get_stream(fsi, fsi_is_play(substream));
974 long location; 1030 long location;
975 1031
976 location = (fsi->byte_offset - 1); 1032 location = (io->buff_offset - 1);
977 if (location < 0) 1033 if (location < 0)
978 location = 0; 1034 location = 0;
979 1035
@@ -988,13 +1044,10 @@ static struct snd_pcm_ops fsi_pcm_ops = {
988 .pointer = fsi_pointer, 1044 .pointer = fsi_pointer,
989}; 1045};
990 1046
991/************************************************************************ 1047/*
992 1048 * snd_soc_platform
993 1049 */
994 snd_soc_platform
995
996 1050
997************************************************************************/
998#define PREALLOC_BUFFER (32 * 1024) 1051#define PREALLOC_BUFFER (32 * 1024)
999#define PREALLOC_BUFFER_MAX (32 * 1024) 1052#define PREALLOC_BUFFER_MAX (32 * 1024)
1000 1053
@@ -1018,17 +1071,13 @@ static int fsi_pcm_new(struct snd_card *card,
1018 PREALLOC_BUFFER, PREALLOC_BUFFER_MAX); 1071 PREALLOC_BUFFER, PREALLOC_BUFFER_MAX);
1019} 1072}
1020 1073
1021/************************************************************************ 1074/*
1022 1075 * alsa struct
1023 1076 */
1024 alsa struct
1025
1026 1077
1027************************************************************************/ 1078static struct snd_soc_dai_driver fsi_soc_dai[] = {
1028struct snd_soc_dai fsi_soc_dai[] = {
1029 { 1079 {
1030 .name = "FSIA", 1080 .name = "fsia-dai",
1031 .id = 0,
1032 .playback = { 1081 .playback = {
1033 .rates = FSI_RATES, 1082 .rates = FSI_RATES,
1034 .formats = FSI_FMTS, 1083 .formats = FSI_FMTS,
@@ -1044,8 +1093,7 @@ struct snd_soc_dai fsi_soc_dai[] = {
1044 .ops = &fsi_dai_ops, 1093 .ops = &fsi_dai_ops,
1045 }, 1094 },
1046 { 1095 {
1047 .name = "FSIB", 1096 .name = "fsib-dai",
1048 .id = 1,
1049 .playback = { 1097 .playback = {
1050 .rates = FSI_RATES, 1098 .rates = FSI_RATES,
1051 .formats = FSI_FMTS, 1099 .formats = FSI_FMTS,
@@ -1061,23 +1109,17 @@ struct snd_soc_dai fsi_soc_dai[] = {
1061 .ops = &fsi_dai_ops, 1109 .ops = &fsi_dai_ops,
1062 }, 1110 },
1063}; 1111};
1064EXPORT_SYMBOL_GPL(fsi_soc_dai);
1065 1112
1066struct snd_soc_platform fsi_soc_platform = { 1113static struct snd_soc_platform_driver fsi_soc_platform = {
1067 .name = "fsi-pcm", 1114 .ops = &fsi_pcm_ops,
1068 .pcm_ops = &fsi_pcm_ops,
1069 .pcm_new = fsi_pcm_new, 1115 .pcm_new = fsi_pcm_new,
1070 .pcm_free = fsi_pcm_free, 1116 .pcm_free = fsi_pcm_free,
1071}; 1117};
1072EXPORT_SYMBOL_GPL(fsi_soc_platform);
1073
1074/************************************************************************
1075
1076
1077 platform function
1078 1118
1119/*
1120 * platform function
1121 */
1079 1122
1080************************************************************************/
1081static int fsi_probe(struct platform_device *pdev) 1123static int fsi_probe(struct platform_device *pdev)
1082{ 1124{
1083 struct fsi_master *master; 1125 struct fsi_master *master;
@@ -1132,11 +1174,7 @@ static int fsi_probe(struct platform_device *pdev)
1132 1174
1133 pm_runtime_enable(&pdev->dev); 1175 pm_runtime_enable(&pdev->dev);
1134 pm_runtime_resume(&pdev->dev); 1176 pm_runtime_resume(&pdev->dev);
1135 1177 dev_set_drvdata(&pdev->dev, master);
1136 fsi_soc_dai[0].dev = &pdev->dev;
1137 fsi_soc_dai[0].private_data = &master->fsia;
1138 fsi_soc_dai[1].dev = &pdev->dev;
1139 fsi_soc_dai[1].private_data = &master->fsib;
1140 1178
1141 fsi_soft_all_reset(master); 1179 fsi_soft_all_reset(master);
1142 1180
@@ -1147,13 +1185,13 @@ static int fsi_probe(struct platform_device *pdev)
1147 goto exit_iounmap; 1185 goto exit_iounmap;
1148 } 1186 }
1149 1187
1150 ret = snd_soc_register_platform(&fsi_soc_platform); 1188 ret = snd_soc_register_platform(&pdev->dev, &fsi_soc_platform);
1151 if (ret < 0) { 1189 if (ret < 0) {
1152 dev_err(&pdev->dev, "cannot snd soc register\n"); 1190 dev_err(&pdev->dev, "cannot snd soc register\n");
1153 goto exit_free_irq; 1191 goto exit_free_irq;
1154 } 1192 }
1155 1193
1156 return snd_soc_register_dais(fsi_soc_dai, ARRAY_SIZE(fsi_soc_dai)); 1194 return snd_soc_register_dais(&pdev->dev, fsi_soc_dai, ARRAY_SIZE(fsi_soc_dai));
1157 1195
1158exit_free_irq: 1196exit_free_irq:
1159 free_irq(irq, master); 1197 free_irq(irq, master);
@@ -1171,10 +1209,10 @@ static int fsi_remove(struct platform_device *pdev)
1171{ 1209{
1172 struct fsi_master *master; 1210 struct fsi_master *master;
1173 1211
1174 master = fsi_get_master(fsi_soc_dai[0].private_data); 1212 master = dev_get_drvdata(&pdev->dev);
1175 1213
1176 snd_soc_unregister_dais(fsi_soc_dai, ARRAY_SIZE(fsi_soc_dai)); 1214 snd_soc_unregister_dais(&pdev->dev, ARRAY_SIZE(fsi_soc_dai));
1177 snd_soc_unregister_platform(&fsi_soc_platform); 1215 snd_soc_unregister_platform(&pdev->dev);
1178 1216
1179 pm_runtime_disable(&pdev->dev); 1217 pm_runtime_disable(&pdev->dev);
1180 1218
@@ -1183,11 +1221,6 @@ static int fsi_remove(struct platform_device *pdev)
1183 iounmap(master->base); 1221 iounmap(master->base);
1184 kfree(master); 1222 kfree(master);
1185 1223
1186 fsi_soc_dai[0].dev = NULL;
1187 fsi_soc_dai[0].private_data = NULL;
1188 fsi_soc_dai[1].dev = NULL;
1189 fsi_soc_dai[1].private_data = NULL;
1190
1191 return 0; 1224 return 0;
1192} 1225}
1193 1226
@@ -1229,11 +1262,13 @@ static struct fsi_core fsi2_core = {
1229static struct platform_device_id fsi_id_table[] = { 1262static struct platform_device_id fsi_id_table[] = {
1230 { "sh_fsi", (kernel_ulong_t)&fsi1_core }, 1263 { "sh_fsi", (kernel_ulong_t)&fsi1_core },
1231 { "sh_fsi2", (kernel_ulong_t)&fsi2_core }, 1264 { "sh_fsi2", (kernel_ulong_t)&fsi2_core },
1265 {},
1232}; 1266};
1267MODULE_DEVICE_TABLE(platform, fsi_id_table);
1233 1268
1234static struct platform_driver fsi_driver = { 1269static struct platform_driver fsi_driver = {
1235 .driver = { 1270 .driver = {
1236 .name = "sh_fsi", 1271 .name = "fsi-pcm-audio",
1237 .pm = &fsi_pm_ops, 1272 .pm = &fsi_pm_ops,
1238 }, 1273 },
1239 .probe = fsi_probe, 1274 .probe = fsi_probe,
@@ -1250,6 +1285,7 @@ static void __exit fsi_mobile_exit(void)
1250{ 1285{
1251 platform_driver_unregister(&fsi_driver); 1286 platform_driver_unregister(&fsi_driver);
1252} 1287}
1288
1253module_init(fsi_mobile_init); 1289module_init(fsi_mobile_init);
1254module_exit(fsi_mobile_exit); 1290module_exit(fsi_mobile_exit);
1255 1291
diff --git a/sound/soc/sh/hac.c b/sound/soc/sh/hac.c
index 41db75af3c69..c87e3ff28a0a 100644
--- a/sound/soc/sh/hac.c
+++ b/sound/soc/sh/hac.c
@@ -239,8 +239,7 @@ static int hac_hw_params(struct snd_pcm_substream *substream,
239 struct snd_pcm_hw_params *params, 239 struct snd_pcm_hw_params *params,
240 struct snd_soc_dai *dai) 240 struct snd_soc_dai *dai)
241{ 241{
242 struct snd_soc_pcm_runtime *rtd = substream->private_data; 242 struct hac_priv *hac = &hac_cpu_data[dai->id];
243 struct hac_priv *hac = &hac_cpu_data[rtd->dai->cpu_dai->id];
244 int d = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0 : 1; 243 int d = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? 0 : 1;
245 244
246 switch (params->msbits) { 245 switch (params->msbits) {
@@ -271,10 +270,9 @@ static struct snd_soc_dai_ops hac_dai_ops = {
271 .hw_params = hac_hw_params, 270 .hw_params = hac_hw_params,
272}; 271};
273 272
274struct snd_soc_dai sh4_hac_dai[] = { 273static struct snd_soc_dai_driver sh4_hac_dai[] = {
275{ 274{
276 .name = "HAC0", 275 .name = "hac-dai.0",
277 .id = 0,
278 .ac97_control = 1, 276 .ac97_control = 1,
279 .playback = { 277 .playback = {
280 .rates = AC97_RATES, 278 .rates = AC97_RATES,
@@ -292,8 +290,7 @@ struct snd_soc_dai sh4_hac_dai[] = {
292}, 290},
293#ifdef CONFIG_CPU_SUBTYPE_SH7760 291#ifdef CONFIG_CPU_SUBTYPE_SH7760
294{ 292{
295 .name = "HAC1", 293 .name = "hac-dai.1",
296 .ac97_control = 1,
297 .id = 1, 294 .id = 1,
298 .playback = { 295 .playback = {
299 .rates = AC97_RATES, 296 .rates = AC97_RATES,
@@ -312,19 +309,40 @@ struct snd_soc_dai sh4_hac_dai[] = {
312}, 309},
313#endif 310#endif
314}; 311};
315EXPORT_SYMBOL_GPL(sh4_hac_dai);
316 312
317static int __init sh4_hac_init(void) 313static int __devinit hac_soc_platform_probe(struct platform_device *pdev)
314{
315 return snd_soc_register_dais(&pdev->dev, sh4_hac_dai,
316 ARRAY_SIZE(sh4_hac_dai));
317}
318
319static int __devexit hac_soc_platform_remove(struct platform_device *pdev)
320{
321 snd_soc_unregister_dais(&pdev->dev, ARRAY_SIZE(sh4_hac_dai));
322 return 0;
323}
324
325static struct platform_driver hac_pcm_driver = {
326 .driver = {
327 .name = "hac-pcm-audio",
328 .owner = THIS_MODULE,
329 },
330
331 .probe = hac_soc_platform_probe,
332 .remove = __devexit_p(hac_soc_platform_remove),
333};
334
335static int __init sh4_hac_pcm_init(void)
318{ 336{
319 return snd_soc_register_dais(sh4_hac_dai, ARRAY_SIZE(sh4_hac_dai)); 337 return platform_driver_register(&hac_pcm_driver);
320} 338}
321module_init(sh4_hac_init); 339module_init(sh4_hac_pcm_init);
322 340
323static void __exit sh4_hac_exit(void) 341static void __exit sh4_hac_pcm_exit(void)
324{ 342{
325 snd_soc_unregister_dais(sh4_hac_dai, ARRAY_SIZE(sh4_hac_dai)); 343 platform_driver_unregister(&hac_pcm_driver);
326} 344}
327module_exit(sh4_hac_exit); 345module_exit(sh4_hac_pcm_exit);
328 346
329MODULE_LICENSE("GPL"); 347MODULE_LICENSE("GPL");
330MODULE_DESCRIPTION("SuperH onchip HAC (AC97) audio driver"); 348MODULE_DESCRIPTION("SuperH onchip HAC (AC97) audio driver");
diff --git a/sound/soc/sh/migor.c b/sound/soc/sh/migor.c
index 87e2b7fcbf17..ac6c49ce6fdf 100644
--- a/sound/soc/sh/migor.c
+++ b/sound/soc/sh/migor.c
@@ -51,7 +51,7 @@ static int migor_hw_params(struct snd_pcm_substream *substream,
51 struct snd_pcm_hw_params *params) 51 struct snd_pcm_hw_params *params)
52{ 52{
53 struct snd_soc_pcm_runtime *rtd = substream->private_data; 53 struct snd_soc_pcm_runtime *rtd = substream->private_data;
54 struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; 54 struct snd_soc_dai *codec_dai = rtd->codec_dai;
55 int ret; 55 int ret;
56 unsigned int rate = params_rate(params); 56 unsigned int rate = params_rate(params);
57 57
@@ -69,7 +69,7 @@ static int migor_hw_params(struct snd_pcm_substream *substream,
69 if (ret < 0) 69 if (ret < 0)
70 return ret; 70 return ret;
71 71
72 ret = snd_soc_dai_set_fmt(rtd->dai->cpu_dai, SND_SOC_DAIFMT_NB_IF | 72 ret = snd_soc_dai_set_fmt(rtd->cpu_dai, SND_SOC_DAIFMT_NB_IF |
73 SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_CBS_CFS); 73 SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_CBS_CFS);
74 if (ret < 0) 74 if (ret < 0)
75 return ret; 75 return ret;
@@ -82,7 +82,7 @@ static int migor_hw_params(struct snd_pcm_substream *substream,
82 clk_set_rate(&siumckb_clk, codec_freq); 82 clk_set_rate(&siumckb_clk, codec_freq);
83 dev_dbg(codec_dai->dev, "%s: configure %luHz\n", __func__, codec_freq); 83 dev_dbg(codec_dai->dev, "%s: configure %luHz\n", __func__, codec_freq);
84 84
85 ret = snd_soc_dai_set_sysclk(rtd->dai->cpu_dai, SIU_CLKB_EXT, 85 ret = snd_soc_dai_set_sysclk(rtd->cpu_dai, SIU_CLKB_EXT,
86 codec_freq / 2, SND_SOC_CLOCK_IN); 86 codec_freq / 2, SND_SOC_CLOCK_IN);
87 87
88 if (!ret) 88 if (!ret)
@@ -94,7 +94,7 @@ static int migor_hw_params(struct snd_pcm_substream *substream,
94static int migor_hw_free(struct snd_pcm_substream *substream) 94static int migor_hw_free(struct snd_pcm_substream *substream)
95{ 95{
96 struct snd_soc_pcm_runtime *rtd = substream->private_data; 96 struct snd_soc_pcm_runtime *rtd = substream->private_data;
97 struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; 97 struct snd_soc_dai *codec_dai = rtd->codec_dai;
98 98
99 if (use_count) { 99 if (use_count) {
100 use_count--; 100 use_count--;
@@ -137,8 +137,10 @@ static const struct snd_soc_dapm_route audio_map[] = {
137 { "Mic Bias", NULL, "External Microphone" }, 137 { "Mic Bias", NULL, "External Microphone" },
138}; 138};
139 139
140static int migor_dai_init(struct snd_soc_codec *codec) 140static int migor_dai_init(struct snd_soc_pcm_runtime *rtd)
141{ 141{
142 struct snd_soc_codec *codec = rtd->codec;
143
142 snd_soc_dapm_new_controls(codec, migor_dapm_widgets, 144 snd_soc_dapm_new_controls(codec, migor_dapm_widgets,
143 ARRAY_SIZE(migor_dapm_widgets)); 145 ARRAY_SIZE(migor_dapm_widgets));
144 146
@@ -151,8 +153,10 @@ static int migor_dai_init(struct snd_soc_codec *codec)
151static struct snd_soc_dai_link migor_dai = { 153static struct snd_soc_dai_link migor_dai = {
152 .name = "wm8978", 154 .name = "wm8978",
153 .stream_name = "WM8978", 155 .stream_name = "WM8978",
154 .cpu_dai = &siu_i2s_dai, 156 .cpu_dai_name = "siu-i2s-dai",
155 .codec_dai = &wm8978_dai, 157 .codec_dai_name = "wm8978-hifi",
158 .platform_name = "siu-pcm-audio",
159 .codec_name = "wm8978.0-001a",
156 .ops = &migor_dai_ops, 160 .ops = &migor_dai_ops,
157 .init = migor_dai_init, 161 .init = migor_dai_init,
158}; 162};
@@ -160,17 +164,10 @@ static struct snd_soc_dai_link migor_dai = {
160/* migor audio machine driver */ 164/* migor audio machine driver */
161static struct snd_soc_card snd_soc_migor = { 165static struct snd_soc_card snd_soc_migor = {
162 .name = "Migo-R", 166 .name = "Migo-R",
163 .platform = &siu_platform,
164 .dai_link = &migor_dai, 167 .dai_link = &migor_dai,
165 .num_links = 1, 168 .num_links = 1,
166}; 169};
167 170
168/* migor audio subsystem */
169static struct snd_soc_device migor_snd_devdata = {
170 .card = &snd_soc_migor,
171 .codec_dev = &soc_codec_dev_wm8978,
172};
173
174static struct platform_device *migor_snd_device; 171static struct platform_device *migor_snd_device;
175 172
176static int __init migor_init(void) 173static int __init migor_init(void)
@@ -195,9 +192,7 @@ static int __init migor_init(void)
195 goto epdevalloc; 192 goto epdevalloc;
196 } 193 }
197 194
198 platform_set_drvdata(migor_snd_device, &migor_snd_devdata); 195 platform_set_drvdata(migor_snd_device, &snd_soc_migor);
199
200 migor_snd_devdata.dev = &migor_snd_device->dev;
201 196
202 ret = platform_device_add(migor_snd_device); 197 ret = platform_device_add(migor_snd_device);
203 if (ret) 198 if (ret)
diff --git a/sound/soc/sh/sh7760-ac97.c b/sound/soc/sh/sh7760-ac97.c
index ce7f95b59de3..b897f7b96d89 100644
--- a/sound/soc/sh/sh7760-ac97.c
+++ b/sound/soc/sh/sh7760-ac97.c
@@ -15,41 +15,35 @@
15#include <sound/soc-dapm.h> 15#include <sound/soc-dapm.h>
16#include <asm/io.h> 16#include <asm/io.h>
17 17
18#include "../codecs/ac97.h"
19
20#define IPSEL 0xFE400034 18#define IPSEL 0xFE400034
21 19
22/* platform specific structs can be declared here */ 20/* platform specific structs can be declared here */
23extern struct snd_soc_dai sh4_hac_dai[2]; 21extern struct snd_soc_dai_driver sh4_hac_dai[2];
24extern struct snd_soc_platform sh7760_soc_platform; 22extern struct snd_soc_platform_driver sh7760_soc_platform;
25 23
26static int machine_init(struct snd_soc_codec *codec) 24static int machine_init(struct snd_soc_pcm_runtime *rtd)
27{ 25{
28 snd_soc_dapm_sync(codec); 26 snd_soc_dapm_sync(rtd->codec);
29 return 0; 27 return 0;
30} 28}
31 29
32static struct snd_soc_dai_link sh7760_ac97_dai = { 30static struct snd_soc_dai_link sh7760_ac97_dai = {
33 .name = "AC97", 31 .name = "AC97",
34 .stream_name = "AC97 HiFi", 32 .stream_name = "AC97 HiFi",
35 .cpu_dai = &sh4_hac_dai[0], /* HAC0 */ 33 .cpu_dai_name = "hac-dai.0", /* HAC0 */
36 .codec_dai = &ac97_dai, 34 .codec_dai_name = "ac97-hifi",
35 .platform_name = "sh7760-pcm-audio",
36 .codec_name = "ac97-codec",
37 .init = machine_init, 37 .init = machine_init,
38 .ops = NULL, 38 .ops = NULL,
39}; 39};
40 40
41static struct snd_soc_card sh7760_ac97_soc_machine = { 41static struct snd_soc_card sh7760_ac97_soc_machine = {
42 .name = "SH7760 AC97", 42 .name = "SH7760 AC97",
43 .platform = &sh7760_soc_platform,
44 .dai_link = &sh7760_ac97_dai, 43 .dai_link = &sh7760_ac97_dai,
45 .num_links = 1, 44 .num_links = 1,
46}; 45};
47 46
48static struct snd_soc_device sh7760_ac97_snd_devdata = {
49 .card = &sh7760_ac97_soc_machine,
50 .codec_dev = &soc_codec_dev_ac97,
51};
52
53static struct platform_device *sh7760_ac97_snd_device; 47static struct platform_device *sh7760_ac97_snd_device;
54 48
55static int __init sh7760_ac97_init(void) 49static int __init sh7760_ac97_init(void)
@@ -67,8 +61,7 @@ static int __init sh7760_ac97_init(void)
67 goto out; 61 goto out;
68 62
69 platform_set_drvdata(sh7760_ac97_snd_device, 63 platform_set_drvdata(sh7760_ac97_snd_device,
70 &sh7760_ac97_snd_devdata); 64 &sh7760_ac97_soc_machine);
71 sh7760_ac97_snd_devdata.dev = &sh7760_ac97_snd_device->dev;
72 ret = platform_device_add(sh7760_ac97_snd_device); 65 ret = platform_device_add(sh7760_ac97_snd_device);
73 66
74 if (ret) 67 if (ret)
diff --git a/sound/soc/sh/siu.h b/sound/soc/sh/siu.h
index 492b1cae24cc..9f4dcb921ff0 100644
--- a/sound/soc/sh/siu.h
+++ b/sound/soc/sh/siu.h
@@ -98,7 +98,9 @@ enum {
98 SIU_CLKB_EXT 98 SIU_CLKB_EXT
99}; 99};
100 100
101struct device;
101struct siu_info { 102struct siu_info {
103 struct device *dev;
102 int port_id; 104 int port_id;
103 u32 __iomem *pram; 105 u32 __iomem *pram;
104 u32 __iomem *xram; 106 u32 __iomem *xram;
@@ -181,8 +183,8 @@ static inline u32 siu_read32(u32 __iomem *addr)
181#define SIU_BRGBSEL (0x108 / sizeof(u32)) 183#define SIU_BRGBSEL (0x108 / sizeof(u32))
182#define SIU_BRRB (0x10c / sizeof(u32)) 184#define SIU_BRRB (0x10c / sizeof(u32))
183 185
184extern struct snd_soc_platform siu_platform; 186extern struct snd_soc_platform_driver siu_platform;
185extern struct snd_soc_dai siu_i2s_dai; 187extern struct siu_info *siu_i2s_data;
186 188
187int siu_init_port(int port, struct siu_port **port_info, struct snd_card *card); 189int siu_init_port(int port, struct siu_port **port_info, struct snd_card *card);
188void siu_free_port(struct siu_port *port_info); 190void siu_free_port(struct siu_port *port_info);
diff --git a/sound/soc/sh/siu_dai.c b/sound/soc/sh/siu_dai.c
index eeed5edd722b..af53b64d8af2 100644
--- a/sound/soc/sh/siu_dai.c
+++ b/sound/soc/sh/siu_dai.c
@@ -71,6 +71,8 @@ struct port_flag {
71 struct format_flag capture; 71 struct format_flag capture;
72}; 72};
73 73
74struct siu_info *siu_i2s_data;
75
74static struct port_flag siu_flags[SIU_PORT_NUM] = { 76static struct port_flag siu_flags[SIU_PORT_NUM] = {
75 [SIU_PORT_A] = { 77 [SIU_PORT_A] = {
76 .playback = { 78 .playback = {
@@ -104,13 +106,13 @@ static struct port_flag siu_flags[SIU_PORT_NUM] = {
104 106
105static void siu_dai_start(struct siu_port *port_info) 107static void siu_dai_start(struct siu_port *port_info)
106{ 108{
107 struct siu_info *info = siu_i2s_dai.private_data; 109 struct siu_info *info = siu_i2s_data;
108 u32 __iomem *base = info->reg; 110 u32 __iomem *base = info->reg;
109 111
110 dev_dbg(port_info->pcm->card->dev, "%s\n", __func__); 112 dev_dbg(port_info->pcm->card->dev, "%s\n", __func__);
111 113
112 /* Turn on SIU clock */ 114 /* Turn on SIU clock */
113 pm_runtime_get_sync(siu_i2s_dai.dev); 115 pm_runtime_get_sync(info->dev);
114 116
115 /* Issue software reset to siu */ 117 /* Issue software reset to siu */
116 siu_write32(base + SIU_SRCTL, 0); 118 siu_write32(base + SIU_SRCTL, 0);
@@ -148,21 +150,21 @@ static void siu_dai_start(struct siu_port *port_info)
148 siu_write32(base + SIU_SBDVCB, port_info->capture.volume); 150 siu_write32(base + SIU_SBDVCB, port_info->capture.volume);
149} 151}
150 152
151static void siu_dai_stop(void) 153static void siu_dai_stop(struct siu_port *port_info)
152{ 154{
153 struct siu_info *info = siu_i2s_dai.private_data; 155 struct siu_info *info = siu_i2s_data;
154 u32 __iomem *base = info->reg; 156 u32 __iomem *base = info->reg;
155 157
156 /* SIU software reset */ 158 /* SIU software reset */
157 siu_write32(base + SIU_SRCTL, 0); 159 siu_write32(base + SIU_SRCTL, 0);
158 160
159 /* Turn off SIU clock */ 161 /* Turn off SIU clock */
160 pm_runtime_put_sync(siu_i2s_dai.dev); 162 pm_runtime_put_sync(info->dev);
161} 163}
162 164
163static void siu_dai_spbAselect(struct siu_port *port_info) 165static void siu_dai_spbAselect(struct siu_port *port_info)
164{ 166{
165 struct siu_info *info = siu_i2s_dai.private_data; 167 struct siu_info *info = siu_i2s_data;
166 struct siu_firmware *fw = &info->fw; 168 struct siu_firmware *fw = &info->fw;
167 u32 *ydef = fw->yram0; 169 u32 *ydef = fw->yram0;
168 u32 idx; 170 u32 idx;
@@ -187,7 +189,7 @@ static void siu_dai_spbAselect(struct siu_port *port_info)
187 189
188static void siu_dai_spbBselect(struct siu_port *port_info) 190static void siu_dai_spbBselect(struct siu_port *port_info)
189{ 191{
190 struct siu_info *info = siu_i2s_dai.private_data; 192 struct siu_info *info = siu_i2s_data;
191 struct siu_firmware *fw = &info->fw; 193 struct siu_firmware *fw = &info->fw;
192 u32 *ydef = fw->yram0; 194 u32 *ydef = fw->yram0;
193 u32 idx; 195 u32 idx;
@@ -207,7 +209,7 @@ static void siu_dai_spbBselect(struct siu_port *port_info)
207 209
208static void siu_dai_open(struct siu_stream *siu_stream) 210static void siu_dai_open(struct siu_stream *siu_stream)
209{ 211{
210 struct siu_info *info = siu_i2s_dai.private_data; 212 struct siu_info *info = siu_i2s_data;
211 u32 __iomem *base = info->reg; 213 u32 __iomem *base = info->reg;
212 u32 srctl, ifctl; 214 u32 srctl, ifctl;
213 215
@@ -238,7 +240,7 @@ static void siu_dai_open(struct siu_stream *siu_stream)
238 */ 240 */
239static void siu_dai_pcmdatapack(struct siu_stream *siu_stream) 241static void siu_dai_pcmdatapack(struct siu_stream *siu_stream)
240{ 242{
241 struct siu_info *info = siu_i2s_dai.private_data; 243 struct siu_info *info = siu_i2s_data;
242 u32 __iomem *base = info->reg; 244 u32 __iomem *base = info->reg;
243 u32 dpak; 245 u32 dpak;
244 246
@@ -258,7 +260,7 @@ static void siu_dai_pcmdatapack(struct siu_stream *siu_stream)
258 260
259static int siu_dai_spbstart(struct siu_port *port_info) 261static int siu_dai_spbstart(struct siu_port *port_info)
260{ 262{
261 struct siu_info *info = siu_i2s_dai.private_data; 263 struct siu_info *info = siu_i2s_data;
262 u32 __iomem *base = info->reg; 264 u32 __iomem *base = info->reg;
263 struct siu_firmware *fw = &info->fw; 265 struct siu_firmware *fw = &info->fw;
264 u32 *ydef = fw->yram0; 266 u32 *ydef = fw->yram0;
@@ -323,7 +325,7 @@ static int siu_dai_spbstart(struct siu_port *port_info)
323 325
324static void siu_dai_spbstop(struct siu_port *port_info) 326static void siu_dai_spbstop(struct siu_port *port_info)
325{ 327{
326 struct siu_info *info = siu_i2s_dai.private_data; 328 struct siu_info *info = siu_i2s_data;
327 u32 __iomem *base = info->reg; 329 u32 __iomem *base = info->reg;
328 330
329 siu_write32(base + SIU_SBACTIV, 0); 331 siu_write32(base + SIU_SBACTIV, 0);
@@ -402,7 +404,7 @@ static int siu_dai_put_volume(struct snd_kcontrol *kctrl,
402{ 404{
403 struct siu_port *port_info = snd_kcontrol_chip(kctrl); 405 struct siu_port *port_info = snd_kcontrol_chip(kctrl);
404 struct device *dev = port_info->pcm->card->dev; 406 struct device *dev = port_info->pcm->card->dev;
405 struct siu_info *info = siu_i2s_dai.private_data; 407 struct siu_info *info = siu_i2s_data;
406 u32 __iomem *base = info->reg; 408 u32 __iomem *base = info->reg;
407 u32 new_vol; 409 u32 new_vol;
408 u32 cur_vol; 410 u32 cur_vol;
@@ -510,7 +512,7 @@ void siu_free_port(struct siu_port *port_info)
510static int siu_dai_startup(struct snd_pcm_substream *substream, 512static int siu_dai_startup(struct snd_pcm_substream *substream,
511 struct snd_soc_dai *dai) 513 struct snd_soc_dai *dai)
512{ 514{
513 struct siu_info *info = siu_i2s_dai.private_data; 515 struct siu_info *info = snd_soc_dai_get_drvdata(dai);
514 struct snd_pcm_runtime *rt = substream->runtime; 516 struct snd_pcm_runtime *rt = substream->runtime;
515 struct siu_port *port_info = siu_port_info(substream); 517 struct siu_port *port_info = siu_port_info(substream);
516 int ret; 518 int ret;
@@ -532,7 +534,7 @@ static int siu_dai_startup(struct snd_pcm_substream *substream,
532static void siu_dai_shutdown(struct snd_pcm_substream *substream, 534static void siu_dai_shutdown(struct snd_pcm_substream *substream,
533 struct snd_soc_dai *dai) 535 struct snd_soc_dai *dai)
534{ 536{
535 struct siu_info *info = siu_i2s_dai.private_data; 537 struct siu_info *info = snd_soc_dai_get_drvdata(dai);
536 struct siu_port *port_info = siu_port_info(substream); 538 struct siu_port *port_info = siu_port_info(substream);
537 539
538 dev_dbg(substream->pcm->card->dev, "%s: port=%d@%p\n", __func__, 540 dev_dbg(substream->pcm->card->dev, "%s: port=%d@%p\n", __func__,
@@ -548,7 +550,7 @@ static void siu_dai_shutdown(struct snd_pcm_substream *substream,
548 /* during stmread or stmwrite ? */ 550 /* during stmread or stmwrite ? */
549 BUG_ON(port_info->playback.rw_flg || port_info->capture.rw_flg); 551 BUG_ON(port_info->playback.rw_flg || port_info->capture.rw_flg);
550 siu_dai_spbstop(port_info); 552 siu_dai_spbstop(port_info);
551 siu_dai_stop(); 553 siu_dai_stop(port_info);
552 } 554 }
553} 555}
554 556
@@ -556,7 +558,7 @@ static void siu_dai_shutdown(struct snd_pcm_substream *substream,
556static int siu_dai_prepare(struct snd_pcm_substream *substream, 558static int siu_dai_prepare(struct snd_pcm_substream *substream,
557 struct snd_soc_dai *dai) 559 struct snd_soc_dai *dai)
558{ 560{
559 struct siu_info *info = siu_i2s_dai.private_data; 561 struct siu_info *info = snd_soc_dai_get_drvdata(dai);
560 struct snd_pcm_runtime *rt = substream->runtime; 562 struct snd_pcm_runtime *rt = substream->runtime;
561 struct siu_port *port_info = siu_port_info(substream); 563 struct siu_port *port_info = siu_port_info(substream);
562 struct siu_stream *siu_stream; 564 struct siu_stream *siu_stream;
@@ -605,7 +607,7 @@ fail:
605static int siu_dai_set_fmt(struct snd_soc_dai *dai, 607static int siu_dai_set_fmt(struct snd_soc_dai *dai,
606 unsigned int fmt) 608 unsigned int fmt)
607{ 609{
608 struct siu_info *info = siu_i2s_dai.private_data; 610 struct siu_info *info = snd_soc_dai_get_drvdata(dai);
609 u32 __iomem *base = info->reg; 611 u32 __iomem *base = info->reg;
610 u32 ifctl; 612 u32 ifctl;
611 613
@@ -671,21 +673,37 @@ static int siu_dai_set_sysclk(struct snd_soc_dai *dai, int clk_id,
671 return -EINVAL; 673 return -EINVAL;
672 } 674 }
673 675
674 siu_clk = clk_get(siu_i2s_dai.dev, siu_name); 676 siu_clk = clk_get(dai->dev, siu_name);
675 if (IS_ERR(siu_clk)) 677 if (IS_ERR(siu_clk)) {
678 dev_err(dai->dev, "%s: cannot get a SIU clock: %ld\n", __func__,
679 PTR_ERR(siu_clk));
676 return PTR_ERR(siu_clk); 680 return PTR_ERR(siu_clk);
681 }
682
683 parent_clk = clk_get(dai->dev, parent_name);
684 if (IS_ERR(parent_clk)) {
685 ret = PTR_ERR(parent_clk);
686 dev_err(dai->dev, "cannot get a SIU clock parent: %d\n", ret);
687 goto epclkget;
688 }
677 689
678 parent_clk = clk_get(siu_i2s_dai.dev, parent_name); 690 ret = clk_set_parent(siu_clk, parent_clk);
679 if (!IS_ERR(parent_clk)) { 691 if (ret < 0) {
680 ret = clk_set_parent(siu_clk, parent_clk); 692 dev_err(dai->dev, "cannot reparent the SIU clock: %d\n", ret);
681 if (!ret) 693 goto eclksetp;
682 clk_set_rate(siu_clk, freq);
683 clk_put(parent_clk);
684 } 694 }
685 695
696 ret = clk_set_rate(siu_clk, freq);
697 if (ret < 0)
698 dev_err(dai->dev, "cannot set SIU clock rate: %d\n", ret);
699
700 /* TODO: when clkdev gets reference counting we'll move these to siu_dai_shutdown() */
701eclksetp:
702 clk_put(parent_clk);
703epclkget:
686 clk_put(siu_clk); 704 clk_put(siu_clk);
687 705
688 return 0; 706 return ret;
689} 707}
690 708
691static struct snd_soc_dai_ops siu_dai_ops = { 709static struct snd_soc_dai_ops siu_dai_ops = {
@@ -696,9 +714,8 @@ static struct snd_soc_dai_ops siu_dai_ops = {
696 .set_fmt = siu_dai_set_fmt, 714 .set_fmt = siu_dai_set_fmt,
697}; 715};
698 716
699struct snd_soc_dai siu_i2s_dai = { 717static struct snd_soc_dai_driver siu_i2s_dai = {
700 .name = "sh-siu", 718 .name = "siu-i2s-dai",
701 .id = 0,
702 .playback = { 719 .playback = {
703 .channels_min = 2, 720 .channels_min = 2,
704 .channels_max = 2, 721 .channels_max = 2,
@@ -713,7 +730,6 @@ struct snd_soc_dai siu_i2s_dai = {
713 }, 730 },
714 .ops = &siu_dai_ops, 731 .ops = &siu_dai_ops,
715}; 732};
716EXPORT_SYMBOL_GPL(siu_i2s_dai);
717 733
718static int __devinit siu_probe(struct platform_device *pdev) 734static int __devinit siu_probe(struct platform_device *pdev)
719{ 735{
@@ -725,6 +741,8 @@ static int __devinit siu_probe(struct platform_device *pdev)
725 info = kmalloc(sizeof(*info), GFP_KERNEL); 741 info = kmalloc(sizeof(*info), GFP_KERNEL);
726 if (!info) 742 if (!info)
727 return -ENOMEM; 743 return -ENOMEM;
744 siu_i2s_data = info;
745 info->dev = &pdev->dev;
728 746
729 ret = request_firmware(&fw_entry, "siu_spb.bin", &pdev->dev); 747 ret = request_firmware(&fw_entry, "siu_spb.bin", &pdev->dev);
730 if (ret) 748 if (ret)
@@ -767,14 +785,14 @@ static int __devinit siu_probe(struct platform_device *pdev)
767 if (!info->reg) 785 if (!info->reg)
768 goto emapreg; 786 goto emapreg;
769 787
770 siu_i2s_dai.dev = &pdev->dev; 788 dev_set_drvdata(&pdev->dev, info);
771 siu_i2s_dai.private_data = info;
772 789
773 ret = snd_soc_register_dais(&siu_i2s_dai, 1); 790 /* register using ARRAY version so we can keep dai name */
791 ret = snd_soc_register_dais(&pdev->dev, &siu_i2s_dai, 1);
774 if (ret < 0) 792 if (ret < 0)
775 goto edaiinit; 793 goto edaiinit;
776 794
777 ret = snd_soc_register_platform(&siu_platform); 795 ret = snd_soc_register_platform(&pdev->dev, &siu_platform);
778 if (ret < 0) 796 if (ret < 0)
779 goto esocregp; 797 goto esocregp;
780 798
@@ -783,7 +801,7 @@ static int __devinit siu_probe(struct platform_device *pdev)
783 return ret; 801 return ret;
784 802
785esocregp: 803esocregp:
786 snd_soc_unregister_dais(&siu_i2s_dai, 1); 804 snd_soc_unregister_dai(&pdev->dev);
787edaiinit: 805edaiinit:
788 iounmap(info->reg); 806 iounmap(info->reg);
789emapreg: 807emapreg:
@@ -804,13 +822,13 @@ ereqfw:
804 822
805static int __devexit siu_remove(struct platform_device *pdev) 823static int __devexit siu_remove(struct platform_device *pdev)
806{ 824{
807 struct siu_info *info = siu_i2s_dai.private_data; 825 struct siu_info *info = dev_get_drvdata(&pdev->dev);
808 struct resource *res; 826 struct resource *res;
809 827
810 pm_runtime_disable(&pdev->dev); 828 pm_runtime_disable(&pdev->dev);
811 829
812 snd_soc_unregister_platform(&siu_platform); 830 snd_soc_unregister_platform(&pdev->dev);
813 snd_soc_unregister_dais(&siu_i2s_dai, 1); 831 snd_soc_unregister_dai(&pdev->dev);
814 832
815 iounmap(info->reg); 833 iounmap(info->reg);
816 iounmap(info->yram); 834 iounmap(info->yram);
@@ -826,7 +844,8 @@ static int __devexit siu_remove(struct platform_device *pdev)
826 844
827static struct platform_driver siu_driver = { 845static struct platform_driver siu_driver = {
828 .driver = { 846 .driver = {
829 .name = "sh_siu", 847 .owner = THIS_MODULE,
848 .name = "siu-pcm-audio",
830 }, 849 },
831 .probe = siu_probe, 850 .probe = siu_probe,
832 .remove = __devexit_p(siu_remove), 851 .remove = __devexit_p(siu_remove),
diff --git a/sound/soc/sh/siu_pcm.c b/sound/soc/sh/siu_pcm.c
index b0ccd0b862fc..ed29c9e1ed4e 100644
--- a/sound/soc/sh/siu_pcm.c
+++ b/sound/soc/sh/siu_pcm.c
@@ -48,7 +48,7 @@ struct siu_port *siu_ports[SIU_PORT_NUM];
48/* transfersize is number of u32 dma transfers per period */ 48/* transfersize is number of u32 dma transfers per period */
49static int siu_pcm_stmwrite_stop(struct siu_port *port_info) 49static int siu_pcm_stmwrite_stop(struct siu_port *port_info)
50{ 50{
51 struct siu_info *info = siu_i2s_dai.private_data; 51 struct siu_info *info = siu_i2s_data;
52 u32 __iomem *base = info->reg; 52 u32 __iomem *base = info->reg;
53 struct siu_stream *siu_stream = &port_info->playback; 53 struct siu_stream *siu_stream = &port_info->playback;
54 u32 stfifo; 54 u32 stfifo;
@@ -114,7 +114,7 @@ static void siu_dma_tx_complete(void *arg)
114static int siu_pcm_wr_set(struct siu_port *port_info, 114static int siu_pcm_wr_set(struct siu_port *port_info,
115 dma_addr_t buff, u32 size) 115 dma_addr_t buff, u32 size)
116{ 116{
117 struct siu_info *info = siu_i2s_dai.private_data; 117 struct siu_info *info = siu_i2s_data;
118 u32 __iomem *base = info->reg; 118 u32 __iomem *base = info->reg;
119 struct siu_stream *siu_stream = &port_info->playback; 119 struct siu_stream *siu_stream = &port_info->playback;
120 struct snd_pcm_substream *substream = siu_stream->substream; 120 struct snd_pcm_substream *substream = siu_stream->substream;
@@ -162,7 +162,7 @@ static int siu_pcm_wr_set(struct siu_port *port_info,
162static int siu_pcm_rd_set(struct siu_port *port_info, 162static int siu_pcm_rd_set(struct siu_port *port_info,
163 dma_addr_t buff, size_t size) 163 dma_addr_t buff, size_t size)
164{ 164{
165 struct siu_info *info = siu_i2s_dai.private_data; 165 struct siu_info *info = siu_i2s_data;
166 u32 __iomem *base = info->reg; 166 u32 __iomem *base = info->reg;
167 struct siu_stream *siu_stream = &port_info->capture; 167 struct siu_stream *siu_stream = &port_info->capture;
168 struct snd_pcm_substream *substream = siu_stream->substream; 168 struct snd_pcm_substream *substream = siu_stream->substream;
@@ -272,7 +272,7 @@ static int siu_pcm_stmread_start(struct siu_port *port_info)
272 272
273static int siu_pcm_stmread_stop(struct siu_port *port_info) 273static int siu_pcm_stmread_stop(struct siu_port *port_info)
274{ 274{
275 struct siu_info *info = siu_i2s_dai.private_data; 275 struct siu_info *info = siu_i2s_data;
276 u32 __iomem *base = info->reg; 276 u32 __iomem *base = info->reg;
277 struct siu_stream *siu_stream = &port_info->capture; 277 struct siu_stream *siu_stream = &port_info->capture;
278 struct device *dev = siu_stream->substream->pcm->card->dev; 278 struct device *dev = siu_stream->substream->pcm->card->dev;
@@ -296,7 +296,7 @@ static int siu_pcm_stmread_stop(struct siu_port *port_info)
296static int siu_pcm_hw_params(struct snd_pcm_substream *ss, 296static int siu_pcm_hw_params(struct snd_pcm_substream *ss,
297 struct snd_pcm_hw_params *hw_params) 297 struct snd_pcm_hw_params *hw_params)
298{ 298{
299 struct siu_info *info = siu_i2s_dai.private_data; 299 struct siu_info *info = siu_i2s_data;
300 struct device *dev = ss->pcm->card->dev; 300 struct device *dev = ss->pcm->card->dev;
301 int ret; 301 int ret;
302 302
@@ -311,7 +311,7 @@ static int siu_pcm_hw_params(struct snd_pcm_substream *ss,
311 311
312static int siu_pcm_hw_free(struct snd_pcm_substream *ss) 312static int siu_pcm_hw_free(struct snd_pcm_substream *ss)
313{ 313{
314 struct siu_info *info = siu_i2s_dai.private_data; 314 struct siu_info *info = siu_i2s_data;
315 struct siu_port *port_info = siu_port_info(ss); 315 struct siu_port *port_info = siu_port_info(ss);
316 struct device *dev = ss->pcm->card->dev; 316 struct device *dev = ss->pcm->card->dev;
317 struct siu_stream *siu_stream; 317 struct siu_stream *siu_stream;
@@ -342,11 +342,12 @@ static bool filter(struct dma_chan *chan, void *slave)
342static int siu_pcm_open(struct snd_pcm_substream *ss) 342static int siu_pcm_open(struct snd_pcm_substream *ss)
343{ 343{
344 /* Playback / Capture */ 344 /* Playback / Capture */
345 struct siu_info *info = siu_i2s_dai.private_data; 345 struct snd_soc_pcm_runtime *rtd = ss->private_data;
346 struct siu_platform *pdata = rtd->platform->dev->platform_data;
347 struct siu_info *info = siu_i2s_data;
346 struct siu_port *port_info = siu_port_info(ss); 348 struct siu_port *port_info = siu_port_info(ss);
347 struct siu_stream *siu_stream; 349 struct siu_stream *siu_stream;
348 u32 port = info->port_id; 350 u32 port = info->port_id;
349 struct siu_platform *pdata = siu_i2s_dai.dev->platform_data;
350 struct device *dev = ss->pcm->card->dev; 351 struct device *dev = ss->pcm->card->dev;
351 dma_cap_mask_t mask; 352 dma_cap_mask_t mask;
352 struct sh_dmae_slave *param; 353 struct sh_dmae_slave *param;
@@ -383,7 +384,7 @@ static int siu_pcm_open(struct snd_pcm_substream *ss)
383 384
384static int siu_pcm_close(struct snd_pcm_substream *ss) 385static int siu_pcm_close(struct snd_pcm_substream *ss)
385{ 386{
386 struct siu_info *info = siu_i2s_dai.private_data; 387 struct siu_info *info = siu_i2s_data;
387 struct device *dev = ss->pcm->card->dev; 388 struct device *dev = ss->pcm->card->dev;
388 struct siu_port *port_info = siu_port_info(ss); 389 struct siu_port *port_info = siu_port_info(ss);
389 struct siu_stream *siu_stream; 390 struct siu_stream *siu_stream;
@@ -405,7 +406,7 @@ static int siu_pcm_close(struct snd_pcm_substream *ss)
405 406
406static int siu_pcm_prepare(struct snd_pcm_substream *ss) 407static int siu_pcm_prepare(struct snd_pcm_substream *ss)
407{ 408{
408 struct siu_info *info = siu_i2s_dai.private_data; 409 struct siu_info *info = siu_i2s_data;
409 struct siu_port *port_info = siu_port_info(ss); 410 struct siu_port *port_info = siu_port_info(ss);
410 struct device *dev = ss->pcm->card->dev; 411 struct device *dev = ss->pcm->card->dev;
411 struct snd_pcm_runtime *rt = ss->runtime; 412 struct snd_pcm_runtime *rt = ss->runtime;
@@ -451,7 +452,7 @@ static int siu_pcm_prepare(struct snd_pcm_substream *ss)
451 452
452static int siu_pcm_trigger(struct snd_pcm_substream *ss, int cmd) 453static int siu_pcm_trigger(struct snd_pcm_substream *ss, int cmd)
453{ 454{
454 struct siu_info *info = siu_i2s_dai.private_data; 455 struct siu_info *info = siu_i2s_data;
455 struct device *dev = ss->pcm->card->dev; 456 struct device *dev = ss->pcm->card->dev;
456 struct siu_port *port_info = siu_port_info(ss); 457 struct siu_port *port_info = siu_port_info(ss);
457 int ret; 458 int ret;
@@ -494,7 +495,7 @@ static int siu_pcm_trigger(struct snd_pcm_substream *ss, int cmd)
494static snd_pcm_uframes_t siu_pcm_pointer_dma(struct snd_pcm_substream *ss) 495static snd_pcm_uframes_t siu_pcm_pointer_dma(struct snd_pcm_substream *ss)
495{ 496{
496 struct device *dev = ss->pcm->card->dev; 497 struct device *dev = ss->pcm->card->dev;
497 struct siu_info *info = siu_i2s_dai.private_data; 498 struct siu_info *info = siu_i2s_data;
498 u32 __iomem *base = info->reg; 499 u32 __iomem *base = info->reg;
499 struct siu_port *port_info = siu_port_info(ss); 500 struct siu_port *port_info = siu_port_info(ss);
500 struct snd_pcm_runtime *rt = ss->runtime; 501 struct snd_pcm_runtime *rt = ss->runtime;
@@ -530,7 +531,7 @@ static int siu_pcm_new(struct snd_card *card, struct snd_soc_dai *dai,
530 struct snd_pcm *pcm) 531 struct snd_pcm *pcm)
531{ 532{
532 /* card->dev == socdev->dev, see snd_soc_new_pcms() */ 533 /* card->dev == socdev->dev, see snd_soc_new_pcms() */
533 struct siu_info *info = siu_i2s_dai.private_data; 534 struct siu_info *info = siu_i2s_data;
534 struct platform_device *pdev = to_platform_device(card->dev); 535 struct platform_device *pdev = to_platform_device(card->dev);
535 int ret; 536 int ret;
536 int i; 537 int i;
@@ -607,9 +608,8 @@ static struct snd_pcm_ops siu_pcm_ops = {
607 .pointer = siu_pcm_pointer_dma, 608 .pointer = siu_pcm_pointer_dma,
608}; 609};
609 610
610struct snd_soc_platform siu_platform = { 611struct snd_soc_platform_driver siu_platform = {
611 .name = "siu-audio", 612 .ops = &siu_pcm_ops,
612 .pcm_ops = &siu_pcm_ops,
613 .pcm_new = siu_pcm_new, 613 .pcm_new = siu_pcm_new,
614 .pcm_free = siu_pcm_free, 614 .pcm_free = siu_pcm_free,
615}; 615};
diff --git a/sound/soc/sh/ssi.c b/sound/soc/sh/ssi.c
index b378096cadb1..40bbdf1591dc 100644
--- a/sound/soc/sh/ssi.c
+++ b/sound/soc/sh/ssi.c
@@ -92,8 +92,7 @@ struct ssi_priv {
92static int ssi_startup(struct snd_pcm_substream *substream, 92static int ssi_startup(struct snd_pcm_substream *substream,
93 struct snd_soc_dai *dai) 93 struct snd_soc_dai *dai)
94{ 94{
95 struct snd_soc_pcm_runtime *rtd = substream->private_data; 95 struct ssi_priv *ssi = &ssi_cpu_data[dai->id];
96 struct ssi_priv *ssi = &ssi_cpu_data[rtd->dai->cpu_dai->id];
97 if (ssi->inuse) { 96 if (ssi->inuse) {
98 pr_debug("ssi: already in use!\n"); 97 pr_debug("ssi: already in use!\n");
99 return -EBUSY; 98 return -EBUSY;
@@ -105,8 +104,7 @@ static int ssi_startup(struct snd_pcm_substream *substream,
105static void ssi_shutdown(struct snd_pcm_substream *substream, 104static void ssi_shutdown(struct snd_pcm_substream *substream,
106 struct snd_soc_dai *dai) 105 struct snd_soc_dai *dai)
107{ 106{
108 struct snd_soc_pcm_runtime *rtd = substream->private_data; 107 struct ssi_priv *ssi = &ssi_cpu_data[dai->id];
109 struct ssi_priv *ssi = &ssi_cpu_data[rtd->dai->cpu_dai->id];
110 108
111 ssi->inuse = 0; 109 ssi->inuse = 0;
112} 110}
@@ -114,8 +112,7 @@ static void ssi_shutdown(struct snd_pcm_substream *substream,
114static int ssi_trigger(struct snd_pcm_substream *substream, int cmd, 112static int ssi_trigger(struct snd_pcm_substream *substream, int cmd,
115 struct snd_soc_dai *dai) 113 struct snd_soc_dai *dai)
116{ 114{
117 struct snd_soc_pcm_runtime *rtd = substream->private_data; 115 struct ssi_priv *ssi = &ssi_cpu_data[dai->id];
118 struct ssi_priv *ssi = &ssi_cpu_data[rtd->dai->cpu_dai->id];
119 116
120 switch (cmd) { 117 switch (cmd) {
121 case SNDRV_PCM_TRIGGER_START: 118 case SNDRV_PCM_TRIGGER_START:
@@ -135,8 +132,7 @@ static int ssi_hw_params(struct snd_pcm_substream *substream,
135 struct snd_pcm_hw_params *params, 132 struct snd_pcm_hw_params *params,
136 struct snd_soc_dai *dai) 133 struct snd_soc_dai *dai)
137{ 134{
138 struct snd_soc_pcm_runtime *rtd = substream->private_data; 135 struct ssi_priv *ssi = &ssi_cpu_data[dai->id];
139 struct ssi_priv *ssi = &ssi_cpu_data[rtd->dai->cpu_dai->id];
140 unsigned long ssicr = SSIREG(SSICR); 136 unsigned long ssicr = SSIREG(SSICR);
141 unsigned int bits, channels, swl, recv, i; 137 unsigned int bits, channels, swl, recv, i;
142 138
@@ -346,10 +342,9 @@ static struct snd_soc_dai_ops ssi_dai_ops = {
346 .set_fmt = ssi_set_fmt, 342 .set_fmt = ssi_set_fmt,
347}; 343};
348 344
349struct snd_soc_dai sh4_ssi_dai[] = { 345struct snd_soc_dai_driver sh4_ssi_dai[] = {
350{ 346{
351 .name = "SSI0", 347 .name = "ssi-dai.0",
352 .id = 0,
353 .playback = { 348 .playback = {
354 .rates = SSI_RATES, 349 .rates = SSI_RATES,
355 .formats = SSI_FMTS, 350 .formats = SSI_FMTS,
@@ -366,8 +361,7 @@ struct snd_soc_dai sh4_ssi_dai[] = {
366}, 361},
367#ifdef CONFIG_CPU_SUBTYPE_SH7760 362#ifdef CONFIG_CPU_SUBTYPE_SH7760
368{ 363{
369 .name = "SSI1", 364 .name = "ssi-dai.1",
370 .id = 1,
371 .playback = { 365 .playback = {
372 .rates = SSI_RATES, 366 .rates = SSI_RATES,
373 .formats = SSI_FMTS, 367 .formats = SSI_FMTS,
@@ -384,19 +378,40 @@ struct snd_soc_dai sh4_ssi_dai[] = {
384}, 378},
385#endif 379#endif
386}; 380};
387EXPORT_SYMBOL_GPL(sh4_ssi_dai);
388 381
389static int __init sh4_ssi_init(void) 382static int __devinit sh4_soc_dai_probe(struct platform_device *pdev)
383{
384 return snd_soc_register_dais(&pdev->dev, sh4_ssi_dai,
385 ARRAY_SIZE(sh4_ssi_dai));
386}
387
388static int __devexit sh4_soc_dai_remove(struct platform_device *pdev)
389{
390 snd_soc_unregister_dai(&pdev->dev, ARRAY_SIZE(sh4_ssi_dai));
391 return 0;
392}
393
394static struct platform_driver sh4_ssi_driver = {
395 .driver = {
396 .name = "sh4-ssi-dai",
397 .owner = THIS_MODULE,
398 },
399
400 .probe = sh4_soc_dai_probe,
401 .remove = __devexit_p(sh4_soc_dai_remove),
402};
403
404static int __init snd_sh4_ssi_init(void)
390{ 405{
391 return snd_soc_register_dais(sh4_ssi_dai, ARRAY_SIZE(sh4_ssi_dai)); 406 return platform_driver_register(&sh4_ssi_driver);
392} 407}
393module_init(sh4_ssi_init); 408module_init(snd_sh4_ssi_init);
394 409
395static void __exit sh4_ssi_exit(void) 410static void __exit snd_sh4_ssi_exit(void)
396{ 411{
397 snd_soc_unregister_dais(sh4_ssi_dai, ARRAY_SIZE(sh4_ssi_dai)); 412 platform_driver_unregister(&sh4_ssi_driver);
398} 413}
399module_exit(sh4_ssi_exit); 414module_exit(snd_sh4_ssi_exit);
400 415
401MODULE_LICENSE("GPL"); 416MODULE_LICENSE("GPL");
402MODULE_DESCRIPTION("SuperH onchip SSI (I2S) audio driver"); 417MODULE_DESCRIPTION("SuperH onchip SSI (I2S) audio driver");