فهرست منبع

Merge branch 'topic/multi-component' of git://git.kernel.org/pub/scm/linux/kernel/git/lrg/asoc-2.6 into for-2.6.37

Mark Brown 15 سال پیش
والد
کامیت
cf7af01aa7
100فایلهای تغییر یافته به همراه1824 افزوده شده و 2806 حذف شده
  1. 13 0
      arch/arm/mach-davinci/devices.c
  2. 6 0
      arch/arm/mach-ep93xx/core.c
  3. 6 0
      arch/arm/mach-kirkwood/common.c
  4. 2 2
      arch/arm/mach-mx2/clock_imx27.c
  5. 1 1
      arch/arm/mach-mx2/devices.c
  6. 2 2
      arch/arm/mach-mx3/clock-imx31.c
  7. 2 2
      arch/arm/mach-mx3/clock-imx35.c
  8. 2 2
      arch/arm/mach-mx3/devices.c
  9. 26 0
      arch/arm/mach-omap1/devices.c
  10. 15 0
      arch/arm/mach-omap2/board-n8x0.c
  11. 13 1
      arch/arm/mach-omap2/board-rx51-peripherals.c
  12. 25 3
      arch/arm/mach-omap2/board-zoom2.c
  13. 39 0
      arch/arm/mach-omap2/devices.c
  14. 2 0
      arch/arm/mach-omap2/include/mach/board-zoom.h
  15. 25 0
      arch/arm/mach-pxa/devices.c
  16. 6 0
      arch/arm/mach-pxa/devices.h
  17. 4 0
      arch/arm/mach-pxa/pxa27x.c
  18. 5 0
      arch/arm/mach-pxa/pxa3xx.c
  19. 11 0
      arch/arm/mach-pxa/zylonite.c
  20. 13 0
      arch/arm/mach-s3c64xx/dev-audio.c
  21. 1 0
      arch/arm/mach-s3c64xx/mach-smdk6410.c
  22. 2 2
      arch/arm/plat-mxc/audmux-v2.c
  23. 7 0
      arch/arm/plat-omap/include/plat/mcbsp.h
  24. 28 2
      arch/arm/plat-s3c24xx/devs.c
  25. 2 0
      arch/arm/plat-samsung/include/plat/devs.h
  26. 1 0
      arch/powerpc/boot/dts/mpc8610_hpcd.dts
  27. 76 35
      arch/powerpc/include/asm/fsl_guts.h
  28. 2 2
      drivers/input/misc/twl4030-vibra.c
  29. 3 3
      drivers/mfd/twl-core.c
  30. 4 4
      drivers/mfd/twl4030-codec.c
  31. 5 1
      include/linux/i2c/twl.h
  32. 2 2
      include/sound/sh_fsi.h
  33. 63 35
      include/sound/soc-dai.h
  34. 4 4
      include/sound/soc-dapm.h
  35. 0 25
      include/sound/soc-of-simple.h
  36. 143 93
      include/sound/soc.h
  37. 42 1
      include/sound/tlv320aic3x.h
  38. 36 23
      sound/soc/atmel/atmel-pcm.c
  39. 0 3
      sound/soc/atmel/atmel-pcm.h
  40. 72 25
      sound/soc/atmel/atmel_ssc_dai.c
  41. 0 1
      sound/soc/atmel/atmel_ssc_dai.h
  42. 12 53
      sound/soc/atmel/playpaq_wm8510.c
  43. 10 41
      sound/soc/atmel/sam9g20_wm8731.c
  44. 9 26
      sound/soc/atmel/snd-soc-afeb9260.c
  45. 12 23
      sound/soc/au1x/db1200.c
  46. 6 13
      sound/soc/au1x/dbdma2.c
  47. 6 14
      sound/soc/au1x/psc-ac97.c
  48. 6 15
      sound/soc/au1x/psc-i2s.c
  49. 0 3
      sound/soc/au1x/psc.h
  50. 31 12
      sound/soc/blackfin/bf5xx-ac97-pcm.c
  51. 0 3
      sound/soc/blackfin/bf5xx-ac97-pcm.h
  52. 30 11
      sound/soc/blackfin/bf5xx-ac97.c
  53. 0 2
      sound/soc/blackfin/bf5xx-ac97.h
  54. 9 14
      sound/soc/blackfin/bf5xx-ad1836.c
  55. 9 14
      sound/soc/blackfin/bf5xx-ad193x.c
  56. 7 12
      sound/soc/blackfin/bf5xx-ad1980.c
  57. 8 14
      sound/soc/blackfin/bf5xx-ad73311.c
  58. 31 13
      sound/soc/blackfin/bf5xx-i2s-pcm.c
  59. 0 3
      sound/soc/blackfin/bf5xx-i2s-pcm.h
  60. 31 14
      sound/soc/blackfin/bf5xx-i2s.c
  61. 0 14
      sound/soc/blackfin/bf5xx-i2s.h
  62. 9 29
      sound/soc/blackfin/bf5xx-ssm2602.c
  63. 31 12
      sound/soc/blackfin/bf5xx-tdm-pcm.c
  64. 0 3
      sound/soc/blackfin/bf5xx-tdm-pcm.h
  65. 6 9
      sound/soc/blackfin/bf5xx-tdm.c
  66. 0 2
      sound/soc/blackfin/bf5xx-tdm.h
  67. 55 69
      sound/soc/codecs/ac97.c
  68. 0 19
      sound/soc/codecs/ac97.h
  69. 55 136
      sound/soc/codecs/ad1836.c
  70. 0 2
      sound/soc/codecs/ad1836.h
  71. 77 140
      sound/soc/codecs/ad193x.c
  72. 0 3
      sound/soc/codecs/ad193x.h
  73. 46 61
      sound/soc/codecs/ad1980.c
  74. 0 3
      sound/soc/codecs/ad1980.h
  75. 19 47
      sound/soc/codecs/ad73311.c
  76. 0 2
      sound/soc/codecs/ad73311.h
  77. 11 61
      sound/soc/codecs/ads117x.c
  78. 2 2
      sound/soc/codecs/ads117x.h
  79. 53 96
      sound/soc/codecs/ak4104.c
  80. 0 7
      sound/soc/codecs/ak4104.h
  81. 61 175
      sound/soc/codecs/ak4535.c
  82. 0 8
      sound/soc/codecs/ak4535.h
  83. 37 138
      sound/soc/codecs/ak4642.c
  84. 0 20
      sound/soc/codecs/ak4642.h
  85. 30 111
      sound/soc/codecs/ak4671.c
  86. 0 3
      sound/soc/codecs/ak4671.h
  87. 29 103
      sound/soc/codecs/cq93vc.c
  88. 0 29
      sound/soc/codecs/cq93vc.h
  89. 138 255
      sound/soc/codecs/cs4270.c
  90. 0 28
      sound/soc/codecs/cs4270.h
  91. 92 201
      sound/soc/codecs/cs42l51.c
  92. 0 2
      sound/soc/codecs/cs42l51.h
  93. 49 124
      sound/soc/codecs/cx20442.c
  94. 0 2
      sound/soc/codecs/cx20442.h
  95. 32 125
      sound/soc/codecs/da7210.c
  96. 0 24
      sound/soc/codecs/da7210.h
  97. 26 90
      sound/soc/codecs/jz4740.c
  98. 0 20
      sound/soc/codecs/jz4740.h
  99. 38 54
      sound/soc/codecs/pcm3008.c
  100. 0 3
      sound/soc/codecs/pcm3008.h

+ 13 - 0
arch/arm/mach-davinci/devices.c

@@ -295,6 +295,18 @@ static void davinci_init_wdt(void)
 
 /*-------------------------------------------------------------------------*/
 
+struct platform_device davinci_pcm_device = {
+	.name		= "davinci-pcm-audio",
+	.id		= -1,
+};
+
+static void davinci_init_pcm(void)
+{
+	platform_device_register(&davinci_pcm_device);
+}
+
+/*-------------------------------------------------------------------------*/
+
 struct davinci_timer_instance davinci_timer_instance[2] = {
 	{
 		.base		= DAVINCI_TIMER0_BASE,
@@ -315,6 +327,7 @@ static int __init davinci_init_devices(void)
 	/* please keep these calls, and their implementations above,
 	 * in alphabetical order so they're easier to sort through.
 	 */
+	davinci_init_pcm();
 	davinci_init_wdt();
 
 	return 0;

+ 6 - 0
arch/arm/mach-ep93xx/core.c

@@ -732,9 +732,15 @@ static struct platform_device ep93xx_i2s_device = {
 	.resource	= ep93xx_i2s_resource,
 };
 
+static struct platform_device ep93xx_pcm_device = {
+	.name		= "ep93xx-pcm-audio",
+	.id		= -1,
+};
+
 void __init ep93xx_register_i2s(void)
 {
 	platform_device_register(&ep93xx_i2s_device);
+	platform_device_register(&ep93xx_pcm_device);
 }
 
 #define EP93XX_SYSCON_DEVCFG_I2S_MASK	(EP93XX_SYSCON_DEVCFG_I2SONSSP | \

+ 6 - 0
arch/arm/mach-kirkwood/common.c

@@ -896,10 +896,16 @@ static struct platform_device kirkwood_i2s_device = {
 	},
 };
 
+static struct platform_device kirkwood_pcm_device = {
+	.name		= "kirkwood-pcm",
+	.id		= -1,
+};
+
 void __init kirkwood_audio_init(void)
 {
 	kirkwood_clk_ctrl |= CGC_AUDIO;
 	platform_device_register(&kirkwood_i2s_device);
+	platform_device_register(&kirkwood_pcm_device);
 }
 
 /*****************************************************************************

+ 2 - 2
arch/arm/mach-mx2/clock_imx27.c

@@ -653,8 +653,8 @@ static struct clk_lookup lookups[] = {
 	_REGISTER_CLOCK("mxc-ehci.1", "usb_ahb", usb_clk1)
 	_REGISTER_CLOCK("mxc-ehci.2", "usb", usb_clk)
 	_REGISTER_CLOCK("mxc-ehci.2", "usb_ahb", usb_clk1)
-	_REGISTER_CLOCK("imx-ssi.0", NULL, ssi1_clk)
-	_REGISTER_CLOCK("imx-ssi.1", NULL, ssi2_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.0", NULL, ssi1_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.1", NULL, ssi2_clk)
 	_REGISTER_CLOCK("mxc_nand.0", NULL, nfc_clk)
 	_REGISTER_CLOCK(NULL, "vpu", vpu_clk)
 	_REGISTER_CLOCK(NULL, "dma", dma_clk)

+ 1 - 1
arch/arm/mach-mx2/devices.c

@@ -415,7 +415,7 @@ struct platform_device mxc_usbh2 = {
 	};								\
 									\
 	struct platform_device imx_ssi_device ## n = {			\
-		.name = "imx-ssi",					\
+		.name = "imx-ssi-dai",					\
 		.id = n,						\
 		.num_resources = ARRAY_SIZE(imx_ssi_resources ## n),	\
 		.resource = imx_ssi_resources ## n,			\

+ 2 - 2
arch/arm/mach-mx3/clock-imx31.c

@@ -558,8 +558,8 @@ static struct clk_lookup lookups[] = {
 	_REGISTER_CLOCK("mxc_w1.0", NULL, owire_clk)
 	_REGISTER_CLOCK("mxc-mmc.0", NULL, sdhc1_clk)
 	_REGISTER_CLOCK("mxc-mmc.1", NULL, sdhc2_clk)
-	_REGISTER_CLOCK("imx-ssi.0", NULL, ssi1_clk)
-	_REGISTER_CLOCK("imx-ssi.1", NULL, ssi2_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.0", NULL, ssi1_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.1", NULL, ssi2_clk)
 	_REGISTER_CLOCK(NULL, "firi", firi_clk)
 	_REGISTER_CLOCK(NULL, "ata", ata_clk)
 	_REGISTER_CLOCK(NULL, "rtic", rtic_clk)

+ 2 - 2
arch/arm/mach-mx3/clock-imx35.c

@@ -464,8 +464,8 @@ static struct clk_lookup lookups[] = {
 	_REGISTER_CLOCK(NULL, "sdma", sdma_clk)
 	_REGISTER_CLOCK(NULL, "spba", spba_clk)
 	_REGISTER_CLOCK(NULL, "spdif", spdif_clk)
-	_REGISTER_CLOCK("imx-ssi.0", NULL, ssi1_clk)
-	_REGISTER_CLOCK("imx-ssi.1", NULL, ssi2_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.0", NULL, ssi1_clk)
+	_REGISTER_CLOCK("imx-ssi-dai.1", NULL, ssi2_clk)
 	_REGISTER_CLOCK("imx-uart.0", NULL, uart1_clk)
 	_REGISTER_CLOCK("imx-uart.1", NULL, uart2_clk)
 	_REGISTER_CLOCK("imx-uart.2", NULL, uart3_clk)

+ 2 - 2
arch/arm/mach-mx3/devices.c

@@ -562,14 +562,14 @@ static struct resource imx_ssi_resources1[] = {
 };
 
 struct platform_device imx_ssi_device0 = {
-	.name = "imx-ssi",
+	.name = "imx-ssi-dai",
 	.id = 0,
 	.num_resources = ARRAY_SIZE(imx_ssi_resources0),
 	.resource = imx_ssi_resources0,
 };
 
 struct platform_device imx_ssi_device1 = {
-	.name = "imx-ssi",
+	.name = "imx-ssi-dai",
 	.id = 1,
 	.num_resources = ARRAY_SIZE(imx_ssi_resources1),
 	.resource = imx_ssi_resources1,

+ 26 - 0
arch/arm/mach-omap1/devices.c

@@ -25,6 +25,7 @@
 #include <mach/gpio.h>
 #include <plat/mmc.h>
 #include <plat/omap7xx.h>
+#include <plat/mcbsp.h>
 
 /*-------------------------------------------------------------------------*/
 
@@ -267,6 +268,30 @@ static inline void omap_init_sti(void)
 static inline void omap_init_sti(void) {}
 #endif
 
+#if defined(CONFIG_SND_SOC) || defined(CONFIG_SND_SOC_MODULE)
+
+static struct platform_device omap_pcm = {
+	.name	= "omap-pcm-audio",
+	.id	= -1,
+};
+
+OMAP_MCBSP_PLATFORM_DEVICE(1);
+OMAP_MCBSP_PLATFORM_DEVICE(2);
+OMAP_MCBSP_PLATFORM_DEVICE(3);
+
+static void omap_init_audio(void)
+{
+	platform_device_register(&omap_mcbsp1);
+	platform_device_register(&omap_mcbsp2);
+	if (!cpu_is_omap7xx())
+		platform_device_register(&omap_mcbsp3);
+	platform_device_register(&omap_pcm);
+}
+
+#else
+static inline void omap_init_audio(void) {}
+#endif
+
 /*-------------------------------------------------------------------------*/
 
 /*
@@ -299,6 +324,7 @@ static int __init omap1_init_devices(void)
 	omap_init_rtc();
 	omap_init_spi100k();
 	omap_init_sti();
+	omap_init_audio();
 
 	return 0;
 }

+ 15 - 0
arch/arm/mach-omap2/board-n8x0.c

@@ -20,6 +20,7 @@
 #include <linux/i2c.h>
 #include <linux/spi/spi.h>
 #include <linux/usb/musb.h>
+#include <sound/tlv320aic3x.h>
 
 #include <asm/mach/arch.h>
 #include <asm/mach-types.h>
@@ -612,11 +613,25 @@ static int n8x0_menelaus_late_init(struct device *dev)
 	return 0;
 }
 
+static struct aic3x_setup_data n810_aic33_setup = {
+	.gpio_func[0] = AIC3X_GPIO1_FUNC_DISABLED,
+	.gpio_func[1] = AIC3X_GPIO2_FUNC_DIGITAL_MIC_INPUT,
+};
+
+static struct aic3x_pdata n810_aic33_data = {
+	.setup = &n810_aic33_setup,
+	.gpio_reset = -1,
+};
+
 static struct i2c_board_info __initdata n8x0_i2c_board_info_1[] = {
 	{
 		I2C_BOARD_INFO("menelaus", 0x72),
 		.irq = INT_24XX_SYS_NIRQ,
 	},
+	{
+		I2C_BOARD_INFO("tlv320aic3x", 0x1b),
+		.platform_data = &n810_aic33_data,
+	},
 };
 
 static struct menelaus_platform_data n8x0_menelaus_platform_data = {

+ 13 - 1
arch/arm/mach-omap2/board-rx51-peripherals.c

@@ -23,6 +23,7 @@
 #include <linux/gpio.h>
 #include <linux/gpio_keys.h>
 #include <linux/mmc/host.h>
+#include <sound/tlv320aic3x.h>
 
 #include <plat/mcspi.h>
 #include <plat/mux.h>
@@ -686,7 +687,6 @@ static struct twl4030_power_data rx51_t2scripts_data __initdata = {
 };
 
 
-
 static struct twl4030_platform_data rx51_twldata __initdata = {
 	.irq_base		= TWL4030_IRQ_BASE,
 	.irq_end		= TWL4030_IRQ_END,
@@ -716,9 +716,21 @@ static struct i2c_board_info __initdata rx51_peripherals_i2c_board_info_1[] = {
 	},
 };
 
+/* Audio setup data */
+static struct aic3x_setup_data rx51_aic34_setup = {
+	.gpio_func[0] = AIC3X_GPIO1_FUNC_DISABLED,
+	.gpio_func[1] = AIC3X_GPIO2_FUNC_DIGITAL_MIC_INPUT,
+};
+
+static struct aic3x_pdata rx51_aic34_data = {
+	.setup = &rx51_aic34_setup,
+	.gpio_reset = 60,
+};
+
 static struct i2c_board_info __initdata rx51_peripherals_i2c_board_info_2[] = {
 	{
 		I2C_BOARD_INFO("tlv320aic3x", 0x18),
+		.platform_data = &rx51_aic34_data,
 	},
 };
 

+ 25 - 3
arch/arm/mach-omap2/board-zoom2.c

@@ -14,6 +14,7 @@
 #include <linux/platform_device.h>
 #include <linux/input.h>
 #include <linux/gpio.h>
+#include <linux/i2c/twl.h>
 
 #include <asm/mach-types.h>
 #include <asm/mach/arch.h>
@@ -34,8 +35,11 @@ static void __init omap_zoom2_init_irq(void)
 	omap_gpio_init();
 }
 
-/* REVISIT: These audio entries can be removed once MFD code is merged */
-#if 0
+/* EXTMUTE callback function */
+void zoom2_set_hs_extmute(int mute)
+{
+	gpio_set_value(ZOOM2_HEADSET_EXTMUTE_GPIO, mute);
+}
 
 static struct twl4030_madc_platform_data zoom2_madc_data = {
 	.irq_line	= 1,
@@ -43,6 +47,9 @@ static struct twl4030_madc_platform_data zoom2_madc_data = {
 
 static struct twl4030_codec_audio_data zoom2_audio_data = {
 	.audio_mclk = 26000000,
+	.ramp_delay_value = 3,	/* 161 ms */
+	.hs_extmute = 1,
+	.set_hs_extmute = zoom2_set_hs_extmute,
 };
 
 static struct twl4030_codec_data zoom2_codec_data = {
@@ -64,10 +71,24 @@ static struct twl4030_platform_data zoom2_twldata = {
 	.vmmc1          = &zoom2_vmmc1,
 	.vmmc2          = &zoom2_vmmc2,
 	.vsim           = &zoom2_vsim,
+};
 
+static struct i2c_board_info __initdata zoom2_i2c_boardinfo[] = {
+	{
+		I2C_BOARD_INFO("twl4030", 0x48),
+		.flags = I2C_CLIENT_WAKE,
+		.irq = INT_34XX_SYS_NIRQ,
+		.platform_data = &zoom2_twldata,
+	},
 };
 
-#endif
+static int __init omap3_zoom2_i2c_init(void)
+{
+	omap_register_i2c_bus(1, 2600, zoom2_i2c_boardinfo,
+			ARRAY_SIZE(zoom2_i2c_boardinfo));
+	return 0;
+}
+
 
 #ifdef CONFIG_OMAP_MUX
 static struct omap_board_mux board_mux[] __initdata = {
@@ -81,6 +102,7 @@ static void __init omap_zoom2_init(void)
 {
 	omap3_mux_init(board_mux, OMAP_PACKAGE_CBB);
 	zoom_peripherals_init();
+	omap3_zoom2_i2c_init();
 	zoom_debugboard_init();
 }
 

+ 39 - 0
arch/arm/mach-omap2/devices.c

@@ -29,6 +29,7 @@
 #include <mach/gpio.h>
 #include <plat/mmc.h>
 #include <plat/dma.h>
+#include <plat/mcbsp.h>
 
 #include "mux.h"
 
@@ -289,6 +290,43 @@ static inline void omap_init_sti(void)
 static inline void omap_init_sti(void) {}
 #endif
 
+#if defined(CONFIG_SND_SOC) || defined(CONFIG_SND_SOC_MODULE)
+
+static struct platform_device omap_pcm = {
+	.name	= "omap-pcm-audio",
+	.id	= -1,
+};
+
+/*
+ * OMAP2420 has 2 McBSP ports
+ * OMAP2430 has 5 McBSP ports
+ * OMAP3 has 5 McBSP ports
+ * OMAP4 has 4 McBSP ports
+ */
+OMAP_MCBSP_PLATFORM_DEVICE(1);
+OMAP_MCBSP_PLATFORM_DEVICE(2);
+OMAP_MCBSP_PLATFORM_DEVICE(3);
+OMAP_MCBSP_PLATFORM_DEVICE(4);
+OMAP_MCBSP_PLATFORM_DEVICE(5);
+
+static void omap_init_audio(void)
+{
+	platform_device_register(&omap_mcbsp1);
+	platform_device_register(&omap_mcbsp2);
+	if (cpu_is_omap243x() || cpu_is_omap34xx() || cpu_is_omap44xx()) {
+		platform_device_register(&omap_mcbsp3);
+		platform_device_register(&omap_mcbsp4);
+	}
+	if (cpu_is_omap243x() || cpu_is_omap34xx())
+		platform_device_register(&omap_mcbsp5);
+
+	platform_device_register(&omap_pcm);
+}
+
+#else
+static inline void omap_init_audio(void) {}
+#endif
+
 #if defined(CONFIG_SPI_OMAP24XX) || defined(CONFIG_SPI_OMAP24XX_MODULE)
 
 #include <plat/mcspi.h>
@@ -901,6 +939,7 @@ static int __init omap2_init_devices(void)
 	 * in alphabetical order so they're easier to sort through.
 	 */
 	omap_hsmmc_reset();
+	omap_init_audio();
 	omap_init_camera();
 	omap_init_mbox();
 	omap_init_mcspi();

+ 2 - 0
arch/arm/mach-omap2/include/mach/board-zoom.h

@@ -3,3 +3,5 @@
  */
 extern int __init zoom_debugboard_init(void);
 extern void __init zoom_peripherals_init(void);
+
+#define ZOOM2_HEADSET_EXTMUTE_GPIO	153

+ 25 - 0
arch/arm/mach-pxa/devices.c

@@ -340,6 +340,31 @@ struct platform_device pxa_device_i2s = {
 	.num_resources	= ARRAY_SIZE(pxai2s_resources),
 };
 
+struct platform_device pxa_device_asoc_ssp1 = {
+	.name		= "pxa-ssp-dai",
+	.id		= 0,
+};
+
+struct platform_device pxa_device_asoc_ssp2= {
+	.name		= "pxa-ssp-dai",
+	.id		= 1,
+};
+
+struct platform_device pxa_device_asoc_ssp3 = {
+	.name		= "pxa-ssp-dai",
+	.id		= 2,
+};
+
+struct platform_device pxa_device_asoc_ssp4 = {
+	.name		= "pxa-ssp-dai",
+	.id		= 3,
+};
+
+struct platform_device pxa_device_asoc_platform = {
+	.name		= "pxa-pcm-audio",
+	.id		= -1,
+};
+
 static u64 pxaficp_dmamask = ~(u32)0;
 
 struct platform_device pxa_device_ficp = {

+ 6 - 0
arch/arm/mach-pxa/devices.h

@@ -37,4 +37,10 @@ extern struct platform_device pxa3xx_device_i2c_power;
 
 extern struct platform_device pxa3xx_device_gcu;
 
+extern struct platform_device pxa_device_asoc_platform;
+extern struct platform_device pxa_device_asoc_ssp1;
+extern struct platform_device pxa_device_asoc_ssp2;
+extern struct platform_device pxa_device_asoc_ssp3;
+extern struct platform_device pxa_device_asoc_ssp4;
+
 void __init pxa_register_device(struct platform_device *dev, void *data);

+ 4 - 0
arch/arm/mach-pxa/pxa27x.c

@@ -384,6 +384,10 @@ void __init pxa27x_set_i2c_power_info(struct i2c_pxa_platform_data *info)
 static struct platform_device *devices[] __initdata = {
 	&pxa27x_device_udc,
 	&pxa_device_i2s,
+	&pxa_device_asoc_ssp1,
+	&pxa_device_asoc_ssp2,
+	&pxa_device_asoc_ssp3,
+	&pxa_device_asoc_platform,
 	&sa1100_device_rtc,
 	&pxa_device_rtc,
 	&pxa27x_device_ssp1,

+ 5 - 0
arch/arm/mach-pxa/pxa3xx.c

@@ -597,6 +597,11 @@ void __init pxa3xx_set_i2c_power_info(struct i2c_pxa_platform_data *info)
 static struct platform_device *devices[] __initdata = {
 	&pxa27x_device_udc,
 	&pxa_device_i2s,
+	&pxa_device_asoc_ssp1,
+	&pxa_device_asoc_ssp2,
+	&pxa_device_asoc_ssp3,
+	&pxa_device_asoc_ssp4,
+	&pxa_device_asoc_platform,
 	&sa1100_device_rtc,
 	&pxa_device_rtc,
 	&pxa27x_device_ssp1,

+ 11 - 0
arch/arm/mach-pxa/zylonite.c

@@ -45,6 +45,16 @@ int wm9713_irq;
 int lcd_id;
 int lcd_orientation;
 
+struct platform_device pxa_device_wm9713_audio = {
+	.name		= "wm9713-codec",
+	.id		= -1,
+};
+
+static void __init zylonite_init_wm9713_audio(void)
+{
+	platform_device_register(&pxa_device_wm9713_audio);
+}
+
 static struct resource smc91x_resources[] = {
 	[0] = {
 		.start	= ZYLONITE_ETH_PHYS + 0x300,
@@ -408,6 +418,7 @@ static void __init zylonite_init(void)
 	zylonite_init_nand();
 	zylonite_init_leds();
 	zylonite_init_ohci();
+	zylonite_init_wm9713_audio();
 }
 
 MACHINE_START(ZYLONITE, "PXA3xx Platform Development Kit (aka Zylonite)")

+ 13 - 0
arch/arm/mach-s3c64xx/dev-audio.c

@@ -333,3 +333,16 @@ void __init s3c64xx_ac97_setup_gpio(int num)
 	else
 		s3c_ac97_pdata.cfg_gpio = s3c64xx_ac97_cfg_gpe;
 }
+
+static u64 s3c_device_audio_dmamask = 0xffffffffUL;
+
+struct platform_device s3c_device_pcm = {
+	.name		  = "s3c24xx-pcm-audio",
+	.id		  = -1,
+	.dev              = {
+		.dma_mask = &s3c_device_audio_dmamask,
+		.coherent_dma_mask = 0xffffffffUL
+	}
+};
+EXPORT_SYMBOL(s3c_device_pcm);
+

+ 1 - 0
arch/arm/mach-s3c64xx/mach-smdk6410.c

@@ -256,6 +256,7 @@ static struct platform_device *smdk6410_devices[] __initdata = {
 	&s3c_device_fb,
 	&s3c_device_ohci,
 	&s3c_device_usb_hsotg,
+	&s3c_device_pcm,
 	&s3c64xx_device_iisv4,
 
 #ifdef CONFIG_REGULATOR

+ 2 - 2
arch/arm/plat-mxc/audmux-v2.c

@@ -49,9 +49,9 @@ static const char *audmux_port_string(int port)
 {
 	switch (port) {
 	case MX31_AUDMUX_PORT1_SSI0:
-		return "imx-ssi.0";
+		return "imx-ssi-dai.0";
 	case MX31_AUDMUX_PORT2_SSI1:
-		return "imx-ssi.1";
+		return "imx-ssi-dai.1";
 	case MX31_AUDMUX_PORT3_SSI_PINS_3:
 		return "SSI3";
 	case MX31_AUDMUX_PORT4_SSI_PINS_4:

+ 7 - 0
arch/arm/plat-omap/include/plat/mcbsp.h

@@ -30,6 +30,13 @@
 #include <mach/hardware.h>
 #include <plat/clock.h>
 
+/* macro for building platform_device for McBSP ports */
+#define OMAP_MCBSP_PLATFORM_DEVICE(port_nr)		\
+static struct platform_device omap_mcbsp##port_nr = {	\
+	.name	= "omap-mcbsp-dai",			\
+	.id	= OMAP_MCBSP##port_nr,			\
+}
+
 #define OMAP7XX_MCBSP1_BASE	0xfffb1000
 #define OMAP7XX_MCBSP2_BASE	0xfffb1800
 

+ 28 - 2
arch/arm/plat-s3c24xx/devs.c

@@ -481,7 +481,7 @@ static struct resource s3c_ac97_resource[] = {
 	},
 };
 
-static u64 s3c_device_ac97_dmamask = 0xffffffffUL;
+static u64 s3c_device_audio_dmamask = 0xffffffffUL;
 
 struct platform_device s3c_device_ac97 = {
 	.name		  = "s3c-ac97",
@@ -489,11 +489,37 @@ struct platform_device s3c_device_ac97 = {
 	.num_resources	  = ARRAY_SIZE(s3c_ac97_resource),
 	.resource	  = s3c_ac97_resource,
 	.dev              = {
-		.dma_mask = &s3c_device_ac97_dmamask,
+		.dma_mask = &s3c_device_audio_dmamask,
 		.coherent_dma_mask = 0xffffffffUL
 	}
 };
 
 EXPORT_SYMBOL(s3c_device_ac97);
 
+/* ASoC PCM DMA */
+
+struct platform_device s3c_device_pcm = {
+	.name		  = "s3c24xx-pcm-audio",
+	.id		  = -1,
+	.dev              = {
+		.dma_mask = &s3c_device_audio_dmamask,
+		.coherent_dma_mask = 0xffffffffUL
+	}
+};
+
+EXPORT_SYMBOL(s3c_device_pcm);
+
+/* ASoC I2S */
+
+struct platform_device s3c2412_device_iis = {
+	.name		  = "s3c2412-iis",
+	.id		  = -1,
+	.dev              = {
+		.dma_mask = &s3c_device_audio_dmamask,
+		.coherent_dma_mask = 0xffffffffUL
+	}
+};
+
+EXPORT_SYMBOL(s3c2412_device_iis);
+
 #endif // CONFIG_CPU_S32440

+ 2 - 0
arch/arm/plat-samsung/include/plat/devs.h

@@ -32,6 +32,8 @@ extern struct platform_device s3c64xx_device_iisv4;
 extern struct platform_device s3c64xx_device_spi0;
 extern struct platform_device s3c64xx_device_spi1;
 
+extern struct platform_device s3c_device_pcm;
+
 extern struct platform_device s3c64xx_device_pcm0;
 extern struct platform_device s3c64xx_device_pcm1;
 

+ 1 - 0
arch/powerpc/boot/dts/mpc8610_hpcd.dts

@@ -286,6 +286,7 @@
 
 		ssi@16100 {
 			compatible = "fsl,mpc8610-ssi";
+			status = "disabled";
 			cell-index = <1>;
 			reg = <0x16100 0x100>;
 			interrupt-parent = <&mpic>;

+ 76 - 35
arch/powerpc/include/asm/immap_86xx.h → arch/powerpc/include/asm/fsl_guts.h

@@ -1,5 +1,5 @@
 /**
- * MPC86xx Internal Memory Map
+ * Freecale 85xx and 86xx Global Utilties register set
  *
  * Authors: Jeff Brown
  *          Timur Tabi <timur@freescale.com>
@@ -10,73 +10,112 @@
  * under  the terms of  the GNU General  Public License as published by the
  * Free Software Foundation;  either version 2 of the  License, or (at your
  * option) any later version.
- *
- * This header file defines structures for various 86xx SOC devices that are
- * used by multiple source files.
  */
 
-#ifndef __ASM_POWERPC_IMMAP_86XX_H__
-#define __ASM_POWERPC_IMMAP_86XX_H__
+#ifndef __ASM_POWERPC_FSL_GUTS_H__
+#define __ASM_POWERPC_FSL_GUTS_H__
 #ifdef __KERNEL__
 
-/* Global Utility Registers */
-struct ccsr_guts {
+/*
+ * These #ifdefs are safe because it's not possible to build a kernel that
+ * runs on e500 and e600 cores.
+ */
+
+#if !defined(CONFIG_PPC_85xx) && !defined(CONFIG_PPC_86xx)
+#error Only 85xx and 86xx SOCs are supported
+#endif
+
+/**
+ * Global Utility Registers.
+ *
+ * Not all registers defined in this structure are available on all chips, so
+ * you are expected to know whether a given register actually exists on your
+ * chip before you access it.
+ *
+ * Also, some registers are similar on different chips but have slightly
+ * different names.  In these cases, one name is chosen to avoid extraneous
+ * #ifdefs.
+ */
+#ifdef CONFIG_PPC_85xx
+struct ccsr_guts_85xx {
+#else
+struct ccsr_guts_86xx {
+#endif
 	__be32	porpllsr;	/* 0x.0000 - POR PLL Ratio Status Register */
 	__be32	porbmsr;	/* 0x.0004 - POR Boot Mode Status Register */
 	__be32	porimpscr;	/* 0x.0008 - POR I/O Impedance Status and Control Register */
 	__be32	pordevsr;	/* 0x.000c - POR I/O Device Status Register */
 	__be32	pordbgmsr;	/* 0x.0010 - POR Debug Mode Status Register */
-	u8	res1[0x20 - 0x14];
+	__be32	pordevsr2;	/* 0x.0014 - POR device status register 2 */
+	u8	res018[0x20 - 0x18];
 	__be32	porcir;		/* 0x.0020 - POR Configuration Information Register */
-	u8	res2[0x30 - 0x24];
+	u8	res024[0x30 - 0x24];
 	__be32	gpiocr;		/* 0x.0030 - GPIO Control Register */
-	u8	res3[0x40 - 0x34];
+	u8	res034[0x40 - 0x34];
 	__be32	gpoutdr;	/* 0x.0040 - General-Purpose Output Data Register */
-	u8	res4[0x50 - 0x44];
+	u8	res044[0x50 - 0x44];
 	__be32	gpindr;		/* 0x.0050 - General-Purpose Input Data Register */
-	u8	res5[0x60 - 0x54];
+	u8	res054[0x60 - 0x54];
 	__be32	pmuxcr;		/* 0x.0060 - Alternate Function Signal Multiplex Control */
-	u8	res6[0x70 - 0x64];
+        __be32  pmuxcr2;	/* 0x.0064 - Alternate function signal multiplex control 2 */
+        __be32  dmuxcr;		/* 0x.0068 - DMA Mux Control Register */
+        u8	res06c[0x70 - 0x6c];
 	__be32	devdisr;	/* 0x.0070 - Device Disable Control */
 	__be32	devdisr2;	/* 0x.0074 - Device Disable Control 2 */
-	u8	res7[0x80 - 0x78];
+	u8	res078[0x7c - 0x78];
+	__be32  pmjcr;		/* 0x.007c - 4 Power Management Jog Control Register */
 	__be32	powmgtcsr;	/* 0x.0080 - Power Management Status and Control Register */
-	u8	res8[0x90 - 0x84];
+	__be32  pmrccr;		/* 0x.0084 - Power Management Reset Counter Configuration Register */
+	__be32  pmpdccr;	/* 0x.0088 - Power Management Power Down Counter Configuration Register */
+	__be32  pmcdr;		/* 0x.008c - 4Power management clock disable register */
 	__be32	mcpsumr;	/* 0x.0090 - Machine Check Summary Register */
 	__be32	rstrscr;	/* 0x.0094 - Reset Request Status and Control Register */
-	u8	res9[0xA0 - 0x98];
+	__be32  ectrstcr;	/* 0x.0098 - Exception reset control register */
+	__be32  autorstsr;	/* 0x.009c - Automatic reset status register */
 	__be32	pvr;		/* 0x.00a0 - Processor Version Register */
 	__be32	svr;		/* 0x.00a4 - System Version Register */
-	u8	res10[0xB0 - 0xA8];
+	u8	res0a8[0xb0 - 0xa8];
 	__be32	rstcr;		/* 0x.00b0 - Reset Control Register */
-	u8	res11[0xC0 - 0xB4];
+	u8	res0b4[0xc0 - 0xb4];
+#ifdef CONFIG_PPC_85xx
+	__be32  iovselsr;	/* 0x.00c0 - I/O voltage select status register */
+#else
 	__be32	elbcvselcr;	/* 0x.00c0 - eLBC Voltage Select Ctrl Reg */
-	u8	res12[0x800 - 0xC4];
+#endif
+	u8	res0c4[0x224 - 0xc4];
+	__be32  iodelay1;	/* 0x.0224 - IO delay control register 1 */
+	__be32  iodelay2;	/* 0x.0228 - IO delay control register 2 */
+	u8	res22c[0x800 - 0x22c];
 	__be32	clkdvdr;	/* 0x.0800 - Clock Divide Register */
-	u8	res13[0x900 - 0x804];
+	u8	res804[0x900 - 0x804];
 	__be32	ircr;		/* 0x.0900 - Infrared Control Register */
-	u8	res14[0x908 - 0x904];
+	u8	res904[0x908 - 0x904];
 	__be32	dmacr;		/* 0x.0908 - DMA Control Register */
-	u8	res15[0x914 - 0x90C];
+	u8	res90c[0x914 - 0x90c];
 	__be32	elbccr;		/* 0x.0914 - eLBC Control Register */
-	u8	res16[0xB20 - 0x918];
+	u8	res918[0xb20 - 0x918];
 	__be32	ddr1clkdr;	/* 0x.0b20 - DDR1 Clock Disable Register */
 	__be32	ddr2clkdr;	/* 0x.0b24 - DDR2 Clock Disable Register */
 	__be32	ddrclkdr;	/* 0x.0b28 - DDR Clock Disable Register */
-	u8	res17[0xE00 - 0xB2C];
+	u8	resb2c[0xe00 - 0xb2c];
 	__be32	clkocr;		/* 0x.0e00 - Clock Out Select Register */
-	u8	res18[0xE10 - 0xE04];
+	u8	rese04[0xe10 - 0xe04];
 	__be32	ddrdllcr;	/* 0x.0e10 - DDR DLL Control Register */
-	u8	res19[0xE20 - 0xE14];
+	u8	rese14[0xe20 - 0xe14];
 	__be32	lbcdllcr;	/* 0x.0e20 - LBC DLL Control Register */
-	u8	res20[0xF04 - 0xE24];
+	__be32  cpfor;		/* 0x.0e24 - L2 charge pump fuse override register */
+	u8	rese28[0xf04 - 0xe28];
 	__be32	srds1cr0;	/* 0x.0f04 - SerDes1 Control Register 0 */
 	__be32	srds1cr1;	/* 0x.0f08 - SerDes1 Control Register 0 */
-	u8	res21[0xF40 - 0xF0C];
-	__be32	srds2cr0;	/* 0x.0f40 - SerDes1 Control Register 0 */
-	__be32	srds2cr1;	/* 0x.0f44 - SerDes1 Control Register 0 */
+	u8	resf0c[0xf2c - 0xf0c];
+	__be32  itcr;		/* 0x.0f2c - Internal transaction control register */
+	u8	resf30[0xf40 - 0xf30];
+	__be32	srds2cr0;	/* 0x.0f40 - SerDes2 Control Register 0 */
+	__be32	srds2cr1;	/* 0x.0f44 - SerDes2 Control Register 0 */
 } __attribute__ ((packed));
 
+#ifdef CONFIG_PPC_86xx
+
 #define CCSR_GUTS_DMACR_DEV_SSI	0	/* DMA controller/channel set to SSI */
 #define CCSR_GUTS_DMACR_DEV_IR	1	/* DMA controller/channel set to IR */
 
@@ -93,7 +132,7 @@ struct ccsr_guts {
  * ch: The channel on the DMA controller (0, 1, 2, or 3)
  * device: The device to set as the source (CCSR_GUTS_DMACR_DEV_xx)
  */
-static inline void guts_set_dmacr(struct ccsr_guts __iomem *guts,
+static inline void guts_set_dmacr(struct ccsr_guts_86xx __iomem *guts,
 	unsigned int co, unsigned int ch, unsigned int device)
 {
 	unsigned int shift = 16 + (8 * (1 - co) + 2 * (3 - ch));
@@ -129,7 +168,7 @@ static inline void guts_set_dmacr(struct ccsr_guts __iomem *guts,
  * ch: The channel on the DMA controller (0, 1, 2, or 3)
  * value: the new value for the bit (0 or 1)
  */
-static inline void guts_set_pmuxcr_dma(struct ccsr_guts __iomem *guts,
+static inline void guts_set_pmuxcr_dma(struct ccsr_guts_86xx __iomem *guts,
 	unsigned int co, unsigned int ch, unsigned int value)
 {
 	if ((ch == 0) || (ch == 3)) {
@@ -152,5 +191,7 @@ static inline void guts_set_pmuxcr_dma(struct ccsr_guts __iomem *guts,
 #define CCSR_GUTS_CLKDVDR_SSICLK_MASK	0x000000FF
 #define CCSR_GUTS_CLKDVDR_SSICLK(x) ((x) & CCSR_GUTS_CLKDVDR_SSICLK_MASK)
 
-#endif /* __ASM_POWERPC_IMMAP_86XX_H__ */
-#endif /* __KERNEL__ */
+#endif
+
+#endif
+#endif

+ 2 - 2
drivers/input/misc/twl4030-vibra.c

@@ -271,7 +271,7 @@ static struct platform_driver twl4030_vibra_driver = {
 	.probe		= twl4030_vibra_probe,
 	.remove		= __devexit_p(twl4030_vibra_remove),
 	.driver		= {
-		.name	= "twl4030_codec_vibra",
+		.name	= "twl4030-vibra",
 		.owner	= THIS_MODULE,
 #ifdef CONFIG_PM
 		.pm	= &twl4030_vibra_pm_ops,
@@ -291,7 +291,7 @@ static void __exit twl4030_vibra_exit(void)
 }
 module_exit(twl4030_vibra_exit);
 
-MODULE_ALIAS("platform:twl4030_codec_vibra");
+MODULE_ALIAS("platform:twl4030-vibra");
 
 MODULE_DESCRIPTION("TWL4030 Vibra driver");
 MODULE_LICENSE("GPL");

+ 3 - 3
drivers/mfd/twl-core.c

@@ -698,17 +698,17 @@ add_children(struct twl4030_platform_data *pdata, unsigned long features)
 
 	if (twl_has_codec() && pdata->codec && twl_class_is_4030()) {
 		sub_chip_id = twl_map[TWL_MODULE_AUDIO_VOICE].sid;
-		child = add_child(sub_chip_id, "twl4030_codec",
+		child = add_child(sub_chip_id, "twl4030-audio",
 				pdata->codec, sizeof(*pdata->codec),
 				false, 0, 0);
 		if (IS_ERR(child))
 			return PTR_ERR(child);
 	}
 
-	/* Phoenix*/
+	/* Phoenix codec driver is probed directly atm */
 	if (twl_has_codec() && pdata->codec && twl_class_is_6030()) {
 		sub_chip_id = twl_map[TWL_MODULE_AUDIO_VOICE].sid;
-		child = add_child(sub_chip_id, "twl6040_codec",
+		child = add_child(sub_chip_id, "twl6040-codec",
 				pdata->codec, sizeof(*pdata->codec),
 				false, 0, 0);
 		if (IS_ERR(child))

+ 4 - 4
drivers/mfd/twl4030-codec.c

@@ -207,14 +207,14 @@ static int __devinit twl4030_codec_probe(struct platform_device *pdev)
 
 	if (pdata->audio) {
 		cell = &codec->cells[childs];
-		cell->name = "twl4030_codec_audio";
+		cell->name = "twl4030-codec";
 		cell->platform_data = pdata->audio;
 		cell->data_size = sizeof(*pdata->audio);
 		childs++;
 	}
 	if (pdata->vibra) {
 		cell = &codec->cells[childs];
-		cell->name = "twl4030_codec_vibra";
+		cell->name = "twl4030-vibra";
 		cell->platform_data = pdata->vibra;
 		cell->data_size = sizeof(*pdata->vibra);
 		childs++;
@@ -249,14 +249,14 @@ static int __devexit twl4030_codec_remove(struct platform_device *pdev)
 	return 0;
 }
 
-MODULE_ALIAS("platform:twl4030_codec");
+MODULE_ALIAS("platform:twl4030-audio");
 
 static struct platform_driver twl4030_codec_driver = {
 	.probe		= twl4030_codec_probe,
 	.remove		= __devexit_p(twl4030_codec_remove),
 	.driver		= {
 		.owner	= THIS_MODULE,
-		.name	= "twl4030_codec",
+		.name	= "twl4030-audio",
 	},
 };
 

+ 5 - 1
include/linux/i2c/twl.h

@@ -553,8 +553,12 @@ extern void twl4030_power_init(struct twl4030_power_data *triton2_scripts);
 extern int twl4030_remove_script(u8 flags);
 
 struct twl4030_codec_audio_data {
-	unsigned int	audio_mclk;
+	unsigned int audio_mclk; /* not used, will be removed */
+	unsigned int digimic_delay; /* in ms */
 	unsigned int ramp_delay_value;
+	unsigned int offset_cncl_path;
+	unsigned int check_defaults:1;
+	unsigned int reset_registers:1;
 	unsigned int hs_extmute:1;
 	void (*set_hs_extmute)(int mute);
 };

+ 2 - 2
include/sound/sh_fsi.h

@@ -114,7 +114,7 @@ struct sh_fsi_platform_info {
 	int (*set_rate)(int is_porta, int rate); /* for master mode */
 };
 
-extern struct snd_soc_dai fsi_soc_dai[2];
-extern struct snd_soc_platform fsi_soc_platform;
+extern struct snd_soc_dai_driver fsi_soc_dai[2];
+extern struct snd_soc_platform_driver fsi_soc_platform;
 
 #endif /* __SOUND_FSI_H */

+ 63 - 35
include/sound/soc-dai.h

@@ -91,15 +91,17 @@ struct snd_pcm_substream;
                                SNDRV_PCM_FMTBIT_S32_LE |\
                                SNDRV_PCM_FMTBIT_S32_BE)
 
-struct snd_soc_dai_ops;
+struct snd_soc_dai_driver;
 struct snd_soc_dai;
 struct snd_ac97_bus_ops;
 
 /* Digital Audio Interface registration */
-int snd_soc_register_dai(struct snd_soc_dai *dai);
-void snd_soc_unregister_dai(struct snd_soc_dai *dai);
-int snd_soc_register_dais(struct snd_soc_dai *dai, size_t count);
-void snd_soc_unregister_dais(struct snd_soc_dai *dai, size_t count);
+int snd_soc_register_dai(struct device *dev,
+		struct snd_soc_dai_driver *dai_drv);
+void snd_soc_unregister_dai(struct device *dev);
+int snd_soc_register_dais(struct device *dev,
+		struct snd_soc_dai_driver *dai_drv, size_t count);
+void snd_soc_unregister_dais(struct device *dev, size_t count);
 
 /* Digital Audio Interface clocking API.*/
 int snd_soc_dai_set_sysclk(struct snd_soc_dai *dai, int clk_id,
@@ -126,16 +128,6 @@ int snd_soc_dai_set_tristate(struct snd_soc_dai *dai, int tristate);
 /* Digital Audio Interface mute */
 int snd_soc_dai_digital_mute(struct snd_soc_dai *dai, int mute);
 
-/*
- * Digital Audio Interface.
- *
- * Describes the Digital Audio Interface in terms of its ALSA, DAI and AC97
- * operations and capabilities. Codec and platform drivers will register this
- * structure for every DAI they have.
- *
- * This structure covers the clocking, formating and ALSA operations for each
- * interface.
- */
 struct snd_soc_dai_ops {
 	/*
 	 * DAI clocking configuration, all optional.
@@ -191,24 +183,24 @@ struct snd_soc_dai_ops {
 };
 
 /*
- * Digital Audio Interface runtime data.
+ * Digital Audio Interface Driver.
  *
- * Holds runtime data for a DAI.
+ * Describes the Digital Audio Interface in terms of its ALSA, DAI and AC97
+ * operations and capabilities. Codec and platform drivers will register this
+ * structure for every DAI they have.
+ *
+ * This structure covers the clocking, formating and ALSA operations for each
+ * interface.
  */
-struct snd_soc_dai {
+struct snd_soc_dai_driver {
 	/* DAI description */
-	char *name;
+	const char *name;
 	unsigned int id;
 	int ac97_control;
 
-	struct device *dev;
-	void *ac97_pdata;	/* platform_data for the ac97 codec */
-
-	/* DAI callbacks */
-	int (*probe)(struct platform_device *pdev,
-		     struct snd_soc_dai *dai);
-	void (*remove)(struct platform_device *pdev,
-		       struct snd_soc_dai *dai);
+	/* DAI driver callbacks */
+	int (*probe)(struct snd_soc_dai *dai);
+	int (*remove)(struct snd_soc_dai *dai);
 	int (*suspend)(struct snd_soc_dai *dai);
 	int (*resume)(struct snd_soc_dai *dai);
 
@@ -219,26 +211,51 @@ struct snd_soc_dai {
 	struct snd_soc_pcm_stream capture;
 	struct snd_soc_pcm_stream playback;
 	unsigned int symmetric_rates:1;
+};
+
+/*
+ * Digital Audio Interface runtime data.
+ *
+ * Holds runtime data for a DAI.
+ */
+struct snd_soc_dai {
+	const char *name;
+	int id;
+	struct device *dev;
+	void *ac97_pdata;	/* platform_data for the ac97 codec */
+
+	/* driver ops */
+	struct snd_soc_dai_driver *driver;
 
 	/* DAI runtime info */
-	struct snd_soc_codec *codec;
+	unsigned int capture_active:1;		/* stream is in use */
+	unsigned int playback_active:1;		/* stream is in use */
+	unsigned int symmetric_rates:1;
+	struct snd_pcm_runtime *runtime;
 	unsigned int active;
 	unsigned char pop_wait:1;
+	unsigned char probed:1;
 
-	/* DAI private data */
-	void *private_data;
+	/* DAI DMA data */
+	void *playback_dma_data;
+	void *capture_dma_data;
 
-	/* parent platform */
-	struct snd_soc_platform *platform;
+	/* parent platform/codec */
+	union {
+		struct snd_soc_platform *platform;
+		struct snd_soc_codec *codec;
+	};
+	struct snd_soc_card *card;
 
 	struct list_head list;
+	struct list_head card_list;
 };
 
 static inline void *snd_soc_dai_get_dma_data(const struct snd_soc_dai *dai,
 					     const struct snd_pcm_substream *ss)
 {
 	return (ss->stream == SNDRV_PCM_STREAM_PLAYBACK) ?
-		dai->playback.dma_data : dai->capture.dma_data;
+		dai->playback_dma_data : dai->capture_dma_data;
 }
 
 static inline void snd_soc_dai_set_dma_data(struct snd_soc_dai *dai,
@@ -246,9 +263,20 @@ static inline void snd_soc_dai_set_dma_data(struct snd_soc_dai *dai,
 					    void *data)
 {
 	if (ss->stream == SNDRV_PCM_STREAM_PLAYBACK)
-		dai->playback.dma_data = data;
+		dai->playback_dma_data = data;
 	else
-		dai->capture.dma_data = data;
+		dai->capture_dma_data = data;
+}
+
+static inline void snd_soc_dai_set_drvdata(struct snd_soc_dai *dai,
+		void *data)
+{
+	dev_set_drvdata(dai->dev, data);
+}
+
+static inline void *snd_soc_dai_get_drvdata(struct snd_soc_dai *dai)
+{
+	return dev_get_drvdata(dai->dev);
 }
 
 #endif

+ 4 - 4
include/sound/soc-dapm.h

@@ -322,14 +322,14 @@ int snd_soc_dapm_new_controls(struct snd_soc_codec *codec,
 
 /* dapm path setup */
 int snd_soc_dapm_new_widgets(struct snd_soc_codec *codec);
-void snd_soc_dapm_free(struct snd_soc_device *socdev);
+void snd_soc_dapm_free(struct snd_soc_codec *codec);
 int snd_soc_dapm_add_routes(struct snd_soc_codec *codec,
 			    const struct snd_soc_dapm_route *route, int num);
 
 /* dapm events */
-int snd_soc_dapm_stream_event(struct snd_soc_codec *codec, char *stream,
-	int event);
-void snd_soc_dapm_shutdown(struct snd_soc_device *socdev);
+int snd_soc_dapm_stream_event(struct snd_soc_pcm_runtime *rtd,
+	const char *stream, int event);
+void snd_soc_dapm_shutdown(struct snd_soc_card *card);
 
 /* dapm sys fs - used by the core */
 int snd_soc_dapm_sys_add(struct device *dev);

+ 0 - 25
include/sound/soc-of-simple.h

@@ -1,25 +0,0 @@
-/*
- * OF helpers for ALSA SoC
- *
- * Copyright (C) 2008, Secret Lab Technologies Ltd.
- */
-
-#ifndef _INCLUDE_SOC_OF_H_
-#define _INCLUDE_SOC_OF_H_
-
-#if defined(CONFIG_SND_SOC_OF_SIMPLE) || defined(CONFIG_SND_SOC_OF_SIMPLE_MODULE)
-
-#include <linux/of.h>
-#include <sound/soc.h>
-
-int of_snd_soc_register_codec(struct snd_soc_codec_device *codec_dev,
-			      void *codec_data, struct snd_soc_dai *dai,
-			      struct device_node *node);
-
-int of_snd_soc_register_platform(struct snd_soc_platform *platform,
-				 struct device_node *node,
-				 struct snd_soc_dai *cpu_dai);
-
-#endif
-
-#endif /* _INCLUDE_SOC_OF_H_ */

+ 143 - 93
include/sound/soc.h

@@ -228,13 +228,17 @@ struct snd_soc_ops;
 struct snd_soc_dai_mode;
 struct snd_soc_pcm_runtime;
 struct snd_soc_dai;
+struct snd_soc_dai_driver;
 struct snd_soc_platform;
 struct snd_soc_dai_link;
+struct snd_soc_platform_driver;
 struct snd_soc_codec;
+struct snd_soc_codec_driver;
 struct soc_enum;
 struct snd_soc_ac97_ops;
 struct snd_soc_jack;
 struct snd_soc_jack_pin;
+
 #ifdef CONFIG_GPIOLIB
 struct snd_soc_jack_gpio;
 #endif
@@ -249,19 +253,18 @@ enum snd_soc_control_type {
 	SND_SOC_SPI,
 };
 
-int snd_soc_register_platform(struct snd_soc_platform *platform);
-void snd_soc_unregister_platform(struct snd_soc_platform *platform);
-int snd_soc_register_codec(struct snd_soc_codec *codec);
-void snd_soc_unregister_codec(struct snd_soc_codec *codec);
+int snd_soc_register_platform(struct device *dev,
+		struct snd_soc_platform_driver *platform_drv);
+void snd_soc_unregister_platform(struct device *dev);
+int snd_soc_register_codec(struct device *dev,
+		struct snd_soc_codec_driver *codec_drv,
+		struct snd_soc_dai_driver *dai_drv, int num_dai);
+void snd_soc_unregister_codec(struct device *dev);
 int snd_soc_codec_volatile_register(struct snd_soc_codec *codec, int reg);
 int snd_soc_codec_set_cache_io(struct snd_soc_codec *codec,
 			       int addr_bits, int data_bits,
 			       enum snd_soc_control_type control);
 
-/* pcm <-> DAI connect */
-void snd_soc_free_pcms(struct snd_soc_device *socdev);
-int snd_soc_new_pcms(struct snd_soc_device *socdev, int idx, const char *xid);
-
 /* Utility functions to get clock rates from various things */
 int snd_soc_calc_frame_size(int sample_size, int channels, int tdm_slots);
 int snd_soc_params_to_frame_size(struct snd_pcm_hw_params *params);
@@ -273,7 +276,7 @@ int snd_soc_set_runtime_hwparams(struct snd_pcm_substream *substream,
 	const struct snd_pcm_hardware *hw);
 
 /* Jack reporting */
-int snd_soc_jack_new(struct snd_soc_card *card, const char *id, int type,
+int snd_soc_jack_new(struct snd_soc_codec *codec, const char *id, int type,
 		     struct snd_soc_jack *jack);
 void snd_soc_jack_report(struct snd_soc_jack *jack, int status, int mask);
 int snd_soc_jack_add_pins(struct snd_soc_jack *jack, int count,
@@ -390,7 +393,7 @@ struct snd_soc_jack_gpio {
 
 struct snd_soc_jack {
 	struct snd_jack *jack;
-	struct snd_soc_card *card;
+	struct snd_soc_codec *codec;
 	struct list_head pins;
 	int status;
 	struct blocking_notifier_head notifier;
@@ -398,15 +401,13 @@ struct snd_soc_jack {
 
 /* SoC PCM stream information */
 struct snd_soc_pcm_stream {
-	char *stream_name;
+	const char *stream_name;
 	u64 formats;			/* SNDRV_PCM_FMTBIT_* */
 	unsigned int rates;		/* SNDRV_PCM_RATE_* */
 	unsigned int rate_min;		/* min rate */
 	unsigned int rate_max;		/* max rate */
 	unsigned int channels_min;	/* min channels */
 	unsigned int channels_max;	/* max channels */
-	unsigned int active;		/* stream is in use */
-	void *dma_data;			/* used by platform code */
 };
 
 /* SoC audio ops */
@@ -419,44 +420,35 @@ struct snd_soc_ops {
 	int (*trigger)(struct snd_pcm_substream *, int);
 };
 
-/* SoC Audio Codec */
+/* SoC Audio Codec device */
 struct snd_soc_codec {
-	char *name;
-	struct module *owner;
-	struct mutex mutex;
+	const char *name;
+	int id;
 	struct device *dev;
-	struct snd_soc_device *socdev;
+	struct snd_soc_codec_driver *driver;
 
+	struct mutex mutex;
+	struct snd_soc_card *card;
 	struct list_head list;
-
-	/* callbacks */
-	int (*set_bias_level)(struct snd_soc_codec *,
-			      enum snd_soc_bias_level level);
+	struct list_head card_list;
+	int num_dai;
 
 	/* runtime */
-	struct snd_card *card;
 	struct snd_ac97 *ac97;  /* for ad-hoc ac97 devices */
 	unsigned int active;
-	unsigned int pcm_devs;
-	void *drvdata;
+	unsigned int idle_bias_off:1; /* Use BIAS_OFF instead of STANDBY */
+	unsigned int cache_only:1;  /* Suppress writes to hardware */
+	unsigned int cache_sync:1; /* Cache needs to be synced to hardware */
+	unsigned int suspended:1; /* Codec is in suspend PM state */
+	unsigned int probed:1; /* Codec has been probed */
+	unsigned int ac97_registered:1; /* Codec has been AC97 registered */
+	unsigned int sysfs_registered:1; /* codec has been sysfs registered */
 
 	/* codec IO */
 	void *control_data; /* codec control (i2c/3wire) data */
-	unsigned int (*read)(struct snd_soc_codec *, unsigned int);
-	int (*write)(struct snd_soc_codec *, unsigned int, unsigned int);
-	int (*display_register)(struct snd_soc_codec *, char *,
-				size_t, unsigned int);
-	int (*volatile_register)(unsigned int);
-	int (*readable_register)(unsigned int);
 	hw_write_t hw_write;
 	unsigned int (*hw_read)(struct snd_soc_codec *, unsigned int);
 	void *reg_cache;
-	short reg_cache_size;
-	short reg_cache_step;
-
-	unsigned int idle_bias_off:1; /* Use BIAS_OFF instead of STANDBY */
-	unsigned int cache_only:1;  /* Suppress writes to hardware */
-	unsigned int cache_sync:1; /* Cache needs to be synced to hardware */
 
 	/* dapm */
 	u32 pop_time;
@@ -466,10 +458,6 @@ struct snd_soc_codec {
 	enum snd_soc_bias_level suspend_bias_level;
 	struct delayed_work delayed_work;
 
-	/* codec DAI's */
-	struct snd_soc_dai *dai;
-	unsigned int num_dai;
-
 #ifdef CONFIG_DEBUG_FS
 	struct dentry *debugfs_codec_root;
 	struct dentry *debugfs_reg;
@@ -478,23 +466,40 @@ struct snd_soc_codec {
 #endif
 };
 
-/* codec device */
-struct snd_soc_codec_device {
-	int (*probe)(struct platform_device *pdev);
-	int (*remove)(struct platform_device *pdev);
-	int (*suspend)(struct platform_device *pdev, pm_message_t state);
-	int (*resume)(struct platform_device *pdev);
+/* codec driver */
+struct snd_soc_codec_driver {
+
+	/* driver ops */
+	int (*probe)(struct snd_soc_codec *);
+	int (*remove)(struct snd_soc_codec *);
+	int (*suspend)(struct snd_soc_codec *,
+			pm_message_t state);
+	int (*resume)(struct snd_soc_codec *);
+
+	/* codec IO */
+	unsigned int (*read)(struct snd_soc_codec *, unsigned int);
+	int (*write)(struct snd_soc_codec *, unsigned int, unsigned int);
+	int (*display_register)(struct snd_soc_codec *, char *,
+				size_t, unsigned int);
+	int (*volatile_register)(unsigned int);
+	int (*readable_register)(unsigned int);
+	short reg_cache_size;
+	short reg_cache_step;
+	short reg_word_size;
+	const void *reg_cache_default;
+
+	/* codec bias level */
+	int (*set_bias_level)(struct snd_soc_codec *,
+			      enum snd_soc_bias_level level);
 };
 
 /* SoC platform interface */
-struct snd_soc_platform {
-	char *name;
-	struct list_head list;
+struct snd_soc_platform_driver {
 
-	int (*probe)(struct platform_device *pdev);
-	int (*remove)(struct platform_device *pdev);
-	int (*suspend)(struct snd_soc_dai_link *dai_link);
-	int (*resume)(struct snd_soc_dai_link *dai_link);
+	int (*probe)(struct snd_soc_platform *);
+	int (*remove)(struct snd_soc_platform *);
+	int (*suspend)(struct snd_soc_dai *dai);
+	int (*resume)(struct snd_soc_dai *dai);
 
 	/* pcm creation and destruction */
 	int (*pcm_new)(struct snd_card *, struct snd_soc_dai *,
@@ -509,23 +514,31 @@ struct snd_soc_platform {
 		struct snd_soc_dai *);
 
 	/* platform stream ops */
-	struct snd_pcm_ops *pcm_ops;
+	struct snd_pcm_ops *ops;
 };
 
-/* SoC machine DAI configuration, glues a codec and cpu DAI together */
-struct snd_soc_dai_link  {
-	char *name;			/* Codec name */
-	char *stream_name;		/* Stream name */
+struct snd_soc_platform {
+	const char *name;
+	int id;
+	struct device *dev;
+	struct snd_soc_platform_driver *driver;
 
-	/* DAI */
-	struct snd_soc_dai *codec_dai;
-	struct snd_soc_dai *cpu_dai;
+	unsigned int suspended:1; /* platform is suspended */
+	unsigned int probed:1;
 
-	/* machine stream operations */
-	struct snd_soc_ops *ops;
+	struct snd_soc_card *card;
+	struct list_head list;
+	struct list_head card_list;
+};
 
-	/* codec/machine specific init - e.g. add machine controls */
-	int (*init)(struct snd_soc_codec *codec);
+struct snd_soc_dai_link {
+	/* config - must be set by machine driver */
+	const char *name;			/* Codec name */
+	const char *stream_name;		/* Stream name */
+	const char *codec_name;		/* for multi-codec */
+	const char *platform_name;	/* for multi-platform */
+	const char *cpu_dai_name;
+	const char *codec_dai_name;
 
 	/* Keep DAI active over suspend */
 	unsigned int ignore_suspend:1;
@@ -533,21 +546,24 @@ struct snd_soc_dai_link  {
 	/* Symmetry requirements */
 	unsigned int symmetric_rates:1;
 
-	/* Symmetry data - only valid if symmetry is being enforced */
-	unsigned int rate;
+	/* codec/machine specific init - e.g. add machine controls */
+	int (*init)(struct snd_soc_pcm_runtime *rtd);
 
-	/* DAI pcm */
-	struct snd_pcm *pcm;
+	/* machine stream operations */
+	struct snd_soc_ops *ops;
 };
 
 /* SoC card */
 struct snd_soc_card {
-	char *name;
+	const char *name;
 	struct device *dev;
+	struct snd_card *snd_card;
+	struct module *owner;
 
 	struct list_head list;
+	struct mutex mutex;
 
-	int instantiated;
+	bool instantiated;
 
 	int (*probe)(struct platform_device *pdev);
 	int (*remove)(struct platform_device *pdev);
@@ -568,28 +584,38 @@ struct snd_soc_card {
 	/* CPU <--> Codec DAI links  */
 	struct snd_soc_dai_link *dai_link;
 	int num_links;
+	struct snd_soc_pcm_runtime *rtd;
+	int num_rtd;
 
-	struct snd_soc_device *socdev;
-
-	struct snd_soc_codec *codec;
-
-	struct snd_soc_platform *platform;
-	struct delayed_work delayed_work;
 	struct work_struct deferred_resume_work;
+
+	/* lists of probed devices belonging to this card */
+	struct list_head codec_dev_list;
+	struct list_head platform_dev_list;
+	struct list_head dai_dev_list;
 };
 
-/* SoC Device - the audio subsystem */
-struct snd_soc_device {
-	struct device *dev;
+/* SoC machine DAI configuration, glues a codec and cpu DAI together */
+struct snd_soc_pcm_runtime  {
+	struct device dev;
 	struct snd_soc_card *card;
-	struct snd_soc_codec_device *codec_dev;
-	void *codec_data;
-};
+	struct snd_soc_dai_link *dai_link;
+
+	unsigned int complete:1;
+	unsigned int dev_registered:1;
 
-/* runtime channel data */
-struct snd_soc_pcm_runtime {
-	struct snd_soc_dai_link *dai;
-	struct snd_soc_device *socdev;
+	/* Symmetry data - only valid if symmetry is being enforced */
+	unsigned int rate;
+	long pmdown_time;
+
+	/* runtime devices */
+	struct snd_pcm *pcm;
+	struct snd_soc_codec *codec;
+	struct snd_soc_platform *platform;
+	struct snd_soc_dai *codec_dai;
+	struct snd_soc_dai *cpu_dai;
+
+	struct delayed_work delayed_work;
 };
 
 /* mixer control */
@@ -615,24 +641,48 @@ struct soc_enum {
 static inline unsigned int snd_soc_read(struct snd_soc_codec *codec,
 					unsigned int reg)
 {
-	return codec->read(codec, reg);
+	return codec->driver->read(codec, reg);
 }
 
 static inline unsigned int snd_soc_write(struct snd_soc_codec *codec,
 					 unsigned int reg, unsigned int val)
 {
-	return codec->write(codec, reg, val);
+	return codec->driver->write(codec, reg, val);
 }
 
+/* device driver data */
+
 static inline void snd_soc_codec_set_drvdata(struct snd_soc_codec *codec,
-					     void *data)
+		void *data)
 {
-	codec->drvdata = data;
+	dev_set_drvdata(codec->dev, data);
 }
 
 static inline void *snd_soc_codec_get_drvdata(struct snd_soc_codec *codec)
 {
-	return codec->drvdata;
+	return dev_get_drvdata(codec->dev);
+}
+
+static inline void snd_soc_platform_set_drvdata(struct snd_soc_platform *platform,
+		void *data)
+{
+	dev_set_drvdata(platform->dev, data);
+}
+
+static inline void *snd_soc_platform_get_drvdata(struct snd_soc_platform *platform)
+{
+	return dev_get_drvdata(platform->dev);
+}
+
+static inline void snd_soc_pcm_set_drvdata(struct snd_soc_pcm_runtime *rtd,
+		void *data)
+{
+	dev_set_drvdata(&rtd->dev, data);
+}
+
+static inline void *snd_soc_pcm_get_drvdata(struct snd_soc_pcm_runtime *rtd)
+{
+	return dev_get_drvdata(&rtd->dev);
 }
 
 #include <sound/soc-dai.h>

+ 42 - 1
include/sound/tlv320aic3x.h

@@ -10,8 +10,49 @@
 #ifndef __TLV320AIC3x_H__
 #define __TLV320AIC3x_H__
 
+/* GPIO API */
+enum {
+	AIC3X_GPIO1_FUNC_DISABLED		= 0,
+	AIC3X_GPIO1_FUNC_AUDIO_WORDCLK_ADC	= 1,
+	AIC3X_GPIO1_FUNC_CLOCK_MUX		= 2,
+	AIC3X_GPIO1_FUNC_CLOCK_MUX_DIV2		= 3,
+	AIC3X_GPIO1_FUNC_CLOCK_MUX_DIV4		= 4,
+	AIC3X_GPIO1_FUNC_CLOCK_MUX_DIV8		= 5,
+	AIC3X_GPIO1_FUNC_SHORT_CIRCUIT_IRQ	= 6,
+	AIC3X_GPIO1_FUNC_AGC_NOISE_IRQ		= 7,
+	AIC3X_GPIO1_FUNC_INPUT			= 8,
+	AIC3X_GPIO1_FUNC_OUTPUT			= 9,
+	AIC3X_GPIO1_FUNC_DIGITAL_MIC_MODCLK	= 10,
+	AIC3X_GPIO1_FUNC_AUDIO_WORDCLK		= 11,
+	AIC3X_GPIO1_FUNC_BUTTON_IRQ		= 12,
+	AIC3X_GPIO1_FUNC_HEADSET_DETECT_IRQ	= 13,
+	AIC3X_GPIO1_FUNC_HEADSET_DETECT_OR_BUTTON_IRQ	= 14,
+	AIC3X_GPIO1_FUNC_ALL_IRQ		= 16
+};
+
+enum {
+	AIC3X_GPIO2_FUNC_DISABLED		= 0,
+	AIC3X_GPIO2_FUNC_HEADSET_DETECT_IRQ	= 2,
+	AIC3X_GPIO2_FUNC_INPUT			= 3,
+	AIC3X_GPIO2_FUNC_OUTPUT			= 4,
+	AIC3X_GPIO2_FUNC_DIGITAL_MIC_INPUT	= 5,
+	AIC3X_GPIO2_FUNC_AUDIO_BITCLK		= 8,
+	AIC3X_GPIO2_FUNC_HEADSET_DETECT_OR_BUTTON_IRQ = 9,
+	AIC3X_GPIO2_FUNC_ALL_IRQ		= 10,
+	AIC3X_GPIO2_FUNC_SHORT_CIRCUIT_OR_AGC_IRQ = 11,
+	AIC3X_GPIO2_FUNC_HEADSET_OR_BUTTON_PRESS_OR_SHORT_CIRCUIT_IRQ = 12,
+	AIC3X_GPIO2_FUNC_SHORT_CIRCUIT_IRQ	= 13,
+	AIC3X_GPIO2_FUNC_AGC_NOISE_IRQ		= 14,
+	AIC3X_GPIO2_FUNC_BUTTON_PRESS_IRQ	= 15
+};
+
+struct aic3x_setup_data {
+	unsigned int gpio_func[2];
+};
+
 struct aic3x_pdata {
 	int gpio_reset; /* < 0 if not used */
+	struct aic3x_setup_data *setup;
 };
 
-#endif
+#endif

+ 36 - 23
sound/soc/atmel/atmel-pcm.c

@@ -179,7 +179,7 @@ static int atmel_pcm_hw_params(struct snd_pcm_substream *substream,
 	snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer);
 	runtime->dma_bytes = params_buffer_bytes(params);
 
-	prtd->params = snd_soc_dai_get_dma_data(rtd->dai->cpu_dai, substream);
+	prtd->params = snd_soc_dai_get_dma_data(rtd->cpu_dai, substream);
 	prtd->params->dma_intr_handler = atmel_pcm_dma_irq;
 
 	prtd->dma_buffer = runtime->dma_addr;
@@ -374,14 +374,14 @@ static int atmel_pcm_new(struct snd_card *card,
 	if (!card->dev->coherent_dma_mask)
 		card->dev->coherent_dma_mask = 0xffffffff;
 
-	if (dai->playback.channels_min) {
+	if (dai->driver->playback.channels_min) {
 		ret = atmel_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_PLAYBACK);
 		if (ret)
 			goto out;
 	}
 
-	if (dai->capture.channels_min) {
+	if (dai->driver->capture.channels_min) {
 		pr_debug("at32-pcm:"
 				"Allocating PCM capture DMA buffer\n");
 		ret = atmel_pcm_preallocate_dma_buffer(pcm,
@@ -414,12 +414,9 @@ static void atmel_pcm_free_dma_buffers(struct snd_pcm *pcm)
 }
 
 #ifdef CONFIG_PM
-static int atmel_pcm_suspend(struct snd_soc_dai_link *dai_link)
+static int atmel_pcm_suspend(struct snd_soc_dai *dai)
 {
-	struct snd_pcm *pcm = dai_link->pcm;
-	struct snd_pcm_str *stream = &pcm->streams[0];
-	struct snd_pcm_substream *substream = stream->substream;
-	struct snd_pcm_runtime *runtime = substream->runtime;
+	struct snd_pcm_runtime *runtime = dai->runtime;
 	struct atmel_runtime_data *prtd;
 	struct atmel_pcm_dma_params *params;
 
@@ -441,12 +438,9 @@ static int atmel_pcm_suspend(struct snd_soc_dai_link *dai_link)
 	return 0;
 }
 
-static int atmel_pcm_resume(struct snd_soc_dai_link *dai_link)
+static int atmel_pcm_resume(struct snd_soc_dai *dai)
 {
-	struct snd_pcm *pcm = dai_link->pcm;
-	struct snd_pcm_str *stream = &pcm->streams[0];
-	struct snd_pcm_substream *substream = stream->substream;
-	struct snd_pcm_runtime *runtime = substream->runtime;
+	struct snd_pcm_runtime *runtime = dai->runtime;
 	struct atmel_runtime_data *prtd;
 	struct atmel_pcm_dma_params *params;
 
@@ -470,27 +464,46 @@ static int atmel_pcm_resume(struct snd_soc_dai_link *dai_link)
 #define atmel_pcm_resume	NULL
 #endif
 
-struct snd_soc_platform atmel_soc_platform = {
-	.name		= "atmel-audio",
-	.pcm_ops 	= &atmel_pcm_ops,
+static struct snd_soc_platform_driver atmel_soc_platform = {
+	.ops		= &atmel_pcm_ops,
 	.pcm_new	= atmel_pcm_new,
 	.pcm_free	= atmel_pcm_free_dma_buffers,
 	.suspend	= atmel_pcm_suspend,
 	.resume		= atmel_pcm_resume,
 };
-EXPORT_SYMBOL_GPL(atmel_soc_platform);
 
-static int __init atmel_pcm_modinit(void)
+static int __devinit atmel_soc_platform_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_platform(&pdev->dev, &atmel_soc_platform);
+}
+
+static int __devexit atmel_soc_platform_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_platform(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver atmel_pcm_driver = {
+	.driver = {
+			.name = "atmel-pcm-audio",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = atmel_soc_platform_probe,
+	.remove = __devexit_p(atmel_soc_platform_remove),
+};
+
+static int __init snd_atmel_pcm_init(void)
 {
-	return snd_soc_register_platform(&atmel_soc_platform);
+	return platform_driver_register(&atmel_pcm_driver);
 }
-module_init(atmel_pcm_modinit);
+module_init(snd_atmel_pcm_init);
 
-static void __exit atmel_pcm_modexit(void)
+static void __exit snd_atmel_pcm_exit(void)
 {
-	snd_soc_unregister_platform(&atmel_soc_platform);
+	platform_driver_unregister(&atmel_pcm_driver);
 }
-module_exit(atmel_pcm_modexit);
+module_exit(snd_atmel_pcm_exit);
 
 MODULE_AUTHOR("Sedji Gaouaou <sedji.gaouaou@atmel.com>");
 MODULE_DESCRIPTION("Atmel PCM module");

+ 0 - 3
sound/soc/atmel/atmel-pcm.h

@@ -74,9 +74,6 @@ struct atmel_pcm_dma_params {
 	void (*dma_intr_handler)(u32, struct snd_pcm_substream *);
 };
 
-extern struct snd_soc_platform atmel_soc_platform;
-
-
 /*
  * SSC register access (since ssc_writel() / ssc_readl() require literal name)
  */

+ 72 - 25
sound/soc/atmel/atmel_ssc_dai.c

@@ -205,8 +205,7 @@ static irqreturn_t atmel_ssc_interrupt(int irq, void *dev_id)
 static int atmel_ssc_startup(struct snd_pcm_substream *substream,
 			     struct snd_soc_dai *dai)
 {
-	struct snd_soc_pcm_runtime *rtd = snd_pcm_substream_chip(substream);
-	struct atmel_ssc_info *ssc_p = &ssc_info[rtd->dai->cpu_dai->id];
+	struct atmel_ssc_info *ssc_p = &ssc_info[dai->id];
 	int dir_mask;
 
 	pr_debug("atmel_ssc_startup: SSC_SR=0x%u\n",
@@ -235,8 +234,7 @@ static int atmel_ssc_startup(struct snd_pcm_substream *substream,
 static void atmel_ssc_shutdown(struct snd_pcm_substream *substream,
 			       struct snd_soc_dai *dai)
 {
-	struct snd_soc_pcm_runtime *rtd = snd_pcm_substream_chip(substream);
-	struct atmel_ssc_info *ssc_p = &ssc_info[rtd->dai->cpu_dai->id];
+	struct atmel_ssc_info *ssc_p = &ssc_info[dai->id];
 	struct atmel_pcm_dma_params *dma_params;
 	int dir, dir_mask;
 
@@ -338,7 +336,7 @@ static int atmel_ssc_hw_params(struct snd_pcm_substream *substream,
 	struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = snd_pcm_substream_chip(substream);
-	int id = rtd->dai->cpu_dai->id;
+	int id = dai->id;
 	struct atmel_ssc_info *ssc_p = &ssc_info[id];
 	struct atmel_pcm_dma_params *dma_params;
 	int dir, channels, bits;
@@ -368,7 +366,7 @@ static int atmel_ssc_hw_params(struct snd_pcm_substream *substream,
 	 * function.  It should not be used for other purposes
 	 * as it is common to all substreams.
 	 */
-	snd_soc_dai_set_dma_data(rtd->dai->cpu_dai, substream, dma_params);
+	snd_soc_dai_set_dma_data(rtd->cpu_dai, substream, dma_params);
 
 	channels = params_channels(params);
 
@@ -605,8 +603,7 @@ static int atmel_ssc_hw_params(struct snd_pcm_substream *substream,
 static int atmel_ssc_prepare(struct snd_pcm_substream *substream,
 			     struct snd_soc_dai *dai)
 {
-	struct snd_soc_pcm_runtime *rtd = snd_pcm_substream_chip(substream);
-	struct atmel_ssc_info *ssc_p = &ssc_info[rtd->dai->cpu_dai->id];
+	struct atmel_ssc_info *ssc_p = &ssc_info[dai->id];
 	struct atmel_pcm_dma_params *dma_params;
 	int dir;
 
@@ -690,6 +687,32 @@ static int atmel_ssc_resume(struct snd_soc_dai *cpu_dai)
 #  define atmel_ssc_resume	NULL
 #endif /* CONFIG_PM */
 
+static int atmel_ssc_probe(struct snd_soc_dai *dai)
+{
+	struct atmel_ssc_info *ssc_p = &ssc_info[dai->id];
+	int ret = 0;
+
+	snd_soc_dai_set_drvdata(dai, ssc_p);
+
+	/*
+	 * Request SSC device
+	 */
+	ssc_p->ssc = ssc_request(dai->id);
+	if (IS_ERR(ssc_p->ssc)) {
+		printk(KERN_ERR "ASoC: Failed to request SSC %d\n", dai->id);
+		ret = PTR_ERR(ssc_p->ssc);
+	}
+
+	return ret;
+}
+
+static int atmel_ssc_remove(struct snd_soc_dai *dai)
+{
+	struct atmel_ssc_info *ssc_p = snd_soc_dai_get_drvdata(dai);
+
+	ssc_free(ssc_p->ssc);
+	return 0;
+}
 
 #define ATMEL_SSC_RATES (SNDRV_PCM_RATE_8000_96000)
 
@@ -705,9 +728,11 @@ static struct snd_soc_dai_ops atmel_ssc_dai_ops = {
 	.set_clkdiv	= atmel_ssc_set_dai_clkdiv,
 };
 
-struct snd_soc_dai atmel_ssc_dai[NUM_SSC_DEVICES] = {
-	{	.name = "atmel-ssc0",
-		.id = 0,
+static struct snd_soc_dai_driver atmel_ssc_dai[NUM_SSC_DEVICES] = {
+	{
+		.name = "atmel-ssc-dai.0",
+		.probe = atmel_ssc_probe,
+		.remove = atmel_ssc_remove,
 		.suspend = atmel_ssc_suspend,
 		.resume = atmel_ssc_resume,
 		.playback = {
@@ -721,11 +746,12 @@ struct snd_soc_dai atmel_ssc_dai[NUM_SSC_DEVICES] = {
 			.rates = ATMEL_SSC_RATES,
 			.formats = ATMEL_SSC_FORMATS,},
 		.ops = &atmel_ssc_dai_ops,
-		.private_data = &ssc_info[0],
 	},
 #if NUM_SSC_DEVICES == 3
-	{	.name = "atmel-ssc1",
-		.id = 1,
+	{
+		.name = "atmel-ssc-dai.1",
+		.probe = atmel_ssc_probe,
+		.remove = atmel_ssc_remove,
 		.suspend = atmel_ssc_suspend,
 		.resume = atmel_ssc_resume,
 		.playback = {
@@ -739,10 +765,11 @@ struct snd_soc_dai atmel_ssc_dai[NUM_SSC_DEVICES] = {
 			.rates = ATMEL_SSC_RATES,
 			.formats = ATMEL_SSC_FORMATS,},
 		.ops = &atmel_ssc_dai_ops,
-		.private_data = &ssc_info[1],
 	},
-	{	.name = "atmel-ssc2",
-		.id = 2,
+	{
+		.name = "atmel-ssc-dai.2",
+		.probe = atmel_ssc_probe,
+		.remove = atmel_ssc_remove,
 		.suspend = atmel_ssc_suspend,
 		.resume = atmel_ssc_resume,
 		.playback = {
@@ -756,23 +783,43 @@ struct snd_soc_dai atmel_ssc_dai[NUM_SSC_DEVICES] = {
 			.rates = ATMEL_SSC_RATES,
 			.formats = ATMEL_SSC_FORMATS,},
 		.ops = &atmel_ssc_dai_ops,
-		.private_data = &ssc_info[2],
 	},
 #endif
 };
-EXPORT_SYMBOL_GPL(atmel_ssc_dai);
 
-static int __init atmel_ssc_modinit(void)
+static __devinit int asoc_ssc_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_dais(&pdev->dev, atmel_ssc_dai,
+			ARRAY_SIZE(atmel_ssc_dai));
+}
+
+static int __devexit asoc_ssc_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_dais(&pdev->dev, ARRAY_SIZE(atmel_ssc_dai));
+	return 0;
+}
+
+static struct platform_driver asoc_ssc_driver = {
+	.driver = {
+			.name = "atmel-ssc-dai",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = asoc_ssc_probe,
+	.remove = __devexit_p(asoc_ssc_remove),
+};
+
+static int __init snd_atmel_ssc_init(void)
 {
-	return snd_soc_register_dais(atmel_ssc_dai, ARRAY_SIZE(atmel_ssc_dai));
+	return platform_driver_register(&asoc_ssc_driver);
 }
-module_init(atmel_ssc_modinit);
+module_init(snd_atmel_ssc_init);
 
-static void __exit atmel_ssc_modexit(void)
+static void __exit snd_atmel_ssc_exit(void)
 {
-	snd_soc_unregister_dais(atmel_ssc_dai, ARRAY_SIZE(atmel_ssc_dai));
+	platform_driver_unregister(&asoc_ssc_driver);
 }
-module_exit(atmel_ssc_modexit);
+module_exit(snd_atmel_ssc_exit);
 
 /* Module information */
 MODULE_AUTHOR("Sedji Gaouaou, sedji.gaouaou@atmel.com, www.atmel.com");

+ 0 - 1
sound/soc/atmel/atmel_ssc_dai.h

@@ -116,6 +116,5 @@ struct atmel_ssc_info {
 	struct atmel_pcm_dma_params *dma_params[2];
 	struct atmel_ssc_state ssc_state;
 };
-extern struct snd_soc_dai atmel_ssc_dai[];
 
 #endif /* _AT91_SSC_DAI_H */

+ 12 - 53
sound/soc/atmel/playpaq_wm8510.c

@@ -83,7 +83,7 @@ static struct ssc_clock_data playpaq_wm8510_calc_ssc_clock(
 	struct snd_pcm_hw_params *params,
 	struct snd_soc_dai *cpu_dai)
 {
-	struct at32_ssc_info *ssc_p = cpu_dai->private_data;
+	struct at32_ssc_info *ssc_p = snd_soc_dai_get_drvdata(cpu_dai);
 	struct ssc_device *ssc = ssc_p->ssc;
 	struct ssc_clock_data cd;
 	unsigned int rate, width_bits, channels;
@@ -131,9 +131,9 @@ static int playpaq_wm8510_hw_params(struct snd_pcm_substream *substream,
 				    struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
-	struct at32_ssc_info *ssc_p = cpu_dai->private_data;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
+	struct at32_ssc_info *ssc_p = snd_soc_dai_get_drvdata(cpu_dai);
 	struct ssc_device *ssc = ssc_p->ssc;
 	unsigned int pll_out = 0, bclk = 0, mclk_div = 0;
 	int ret;
@@ -315,8 +315,9 @@ static const struct snd_soc_dapm_route intercon[] = {
 
 
 
-static int playpaq_wm8510_init(struct snd_soc_codec *codec)
+static int playpaq_wm8510_init(struct snd_soc_pcm_runtime *rtd)
 {
+	struct snd_soc_codec *codec = rtd->codec;
 	int i;
 
 	/*
@@ -342,7 +343,7 @@ static int playpaq_wm8510_init(struct snd_soc_codec *codec)
 
 
 	/* Make CSB show PLL rate */
-	snd_soc_dai_set_clkdiv(codec->dai, WM8510_OPCLKDIV,
+	snd_soc_dai_set_clkdiv(rtd->codec_dai, WM8510_OPCLKDIV,
 				       WM8510_OPCLKDIV_1 | 4);
 
 	return 0;
@@ -353,8 +354,10 @@ static int playpaq_wm8510_init(struct snd_soc_codec *codec)
 static struct snd_soc_dai_link playpaq_wm8510_dai = {
 	.name = "WM8510",
 	.stream_name = "WM8510 PCM",
-	.cpu_dai = &at32_ssc_dai[0],
-	.codec_dai = &wm8510_dai,
+	.cpu_dai_name= "atmel-ssc-dai.0",
+	.platform_name = "atmel-pcm-audio",
+	.codec_name = "wm8510-codec.0-0x1a",
+	.codec_dai_name = "wm8510-hifi",
 	.init = playpaq_wm8510_init,
 	.ops = &playpaq_wm8510_ops,
 };
@@ -363,46 +366,16 @@ static struct snd_soc_dai_link playpaq_wm8510_dai = {
 
 static struct snd_soc_card snd_soc_playpaq = {
 	.name = "LRS_PlayPaq_WM8510",
-	.platform = &at32_soc_platform,
 	.dai_link = &playpaq_wm8510_dai,
 	.num_links = 1,
 };
 
-
-
-static struct wm8510_setup_data playpaq_wm8510_setup = {
-	.i2c_bus = 0,
-	.i2c_address = 0x1a,
-};
-
-
-
-static struct snd_soc_device playpaq_wm8510_snd_devdata = {
-	.card = &snd_soc_playpaq,
-	.codec_dev = &soc_codec_dev_wm8510,
-	.codec_data = &playpaq_wm8510_setup,
-};
-
 static struct platform_device *playpaq_snd_device;
 
 
 static int __init playpaq_asoc_init(void)
 {
 	int ret = 0;
-	struct at32_ssc_info *ssc_p = playpaq_wm8510_dai.cpu_dai->private_data;
-	struct ssc_device *ssc = NULL;
-
-
-	/*
-	 * Request SSC device
-	 */
-	ssc = ssc_request(0);
-	if (IS_ERR(ssc)) {
-		ret = PTR_ERR(ssc);
-		goto err_ssc;
-	}
-	ssc_p->ssc = ssc;
-
 
 	/*
 	 * Configure MCLK for WM8510
@@ -439,8 +412,7 @@ static int __init playpaq_asoc_init(void)
 		goto err_device_alloc;
 	}
 
-	platform_set_drvdata(playpaq_snd_device, &playpaq_wm8510_snd_devdata);
-	playpaq_wm8510_snd_devdata.dev = &playpaq_snd_device->dev;
+	platform_set_drvdata(playpaq_snd_device, &snd_soc_playpaq);
 
 	ret = platform_device_add(playpaq_snd_device);
 	if (ret) {
@@ -468,25 +440,12 @@ err_pll0:
 		clk_put(_gclk0);
 		_gclk0 = NULL;
 	}
-err_gclk0:
-	ssc_free(ssc);
-err_ssc:
 	return ret;
 }
 
 
 static void __exit playpaq_asoc_exit(void)
 {
-	struct at32_ssc_info *ssc_p = playpaq_wm8510_dai.cpu_dai->private_data;
-	struct ssc_device *ssc;
-
-	if (ssc_p != NULL) {
-		ssc = ssc_p->ssc;
-		if (ssc != NULL)
-			ssc_free(ssc);
-		ssc_p->ssc = NULL;
-	}
-
 	if (_gclk0 != NULL) {
 		clk_put(_gclk0);
 		_gclk0 = NULL;

+ 10 - 41
sound/soc/atmel/sam9g20_wm8731.c

@@ -69,8 +69,8 @@ static int at91sam9g20ek_hw_params(struct snd_pcm_substream *substream,
 	struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 	int ret;
 
 	/* set codec DAI configuration */
@@ -136,9 +136,10 @@ static const struct snd_soc_dapm_route intercon[] = {
 /*
  * Logic for a wm8731 as connected on a at91sam9g20ek board.
  */
-static int at91sam9g20ek_wm8731_init(struct snd_soc_codec *codec)
+static int at91sam9g20ek_wm8731_init(struct snd_soc_pcm_runtime *rtd)
 {
-	struct snd_soc_dai *codec_dai = &codec->dai[0];
+	struct snd_soc_codec *codec = rtd->codec;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
 	int ret;
 
 	printk(KERN_DEBUG
@@ -179,31 +180,25 @@ static int at91sam9g20ek_wm8731_init(struct snd_soc_codec *codec)
 static struct snd_soc_dai_link at91sam9g20ek_dai = {
 	.name = "WM8731",
 	.stream_name = "WM8731 PCM",
-	.cpu_dai = &atmel_ssc_dai[0],
-	.codec_dai = &wm8731_dai,
+	.cpu_dai_name = "atmel-ssc-dai.0",
+	.codec_dai_name = "wm8731-hifi",
 	.init = at91sam9g20ek_wm8731_init,
+	.platform_name = "atmel_pcm-audio",
+	.codec_name = "wm8731-codec.0-001a",
 	.ops = &at91sam9g20ek_ops,
 };
 
 static struct snd_soc_card snd_soc_at91sam9g20ek = {
 	.name = "AT91SAMG20-EK",
-	.platform = &atmel_soc_platform,
 	.dai_link = &at91sam9g20ek_dai,
 	.num_links = 1,
 	.set_bias_level = at91sam9g20ek_set_bias_level,
 };
 
-static struct snd_soc_device at91sam9g20ek_snd_devdata = {
-	.card = &snd_soc_at91sam9g20ek,
-	.codec_dev = &soc_codec_dev_wm8731,
-};
-
 static struct platform_device *at91sam9g20ek_snd_device;
 
 static int __init at91sam9g20ek_init(void)
 {
-	struct atmel_ssc_info *ssc_p = at91sam9g20ek_dai.cpu_dai->private_data;
-	struct ssc_device *ssc = NULL;
 	struct clk *pllb;
 	int ret;
 
@@ -235,18 +230,6 @@ static int __init at91sam9g20ek_init(void)
 
 	clk_set_rate(mclk, MCLK_RATE);
 
-	/*
-	 * Request SSC device
-	 */
-	ssc = ssc_request(0);
-	if (IS_ERR(ssc)) {
-		printk(KERN_ERR "ASoC: Failed to request SSC 0\n");
-		ret = PTR_ERR(ssc);
-		ssc = NULL;
-		goto err_ssc;
-	}
-	ssc_p->ssc = ssc;
-
 	at91sam9g20ek_snd_device = platform_device_alloc("soc-audio", -1);
 	if (!at91sam9g20ek_snd_device) {
 		printk(KERN_ERR "ASoC: Platform device allocation failed\n");
@@ -254,8 +237,7 @@ static int __init at91sam9g20ek_init(void)
 	}
 
 	platform_set_drvdata(at91sam9g20ek_snd_device,
-			&at91sam9g20ek_snd_devdata);
-	at91sam9g20ek_snd_devdata.dev = &at91sam9g20ek_snd_device->dev;
+			&snd_soc_at91sam9g20ek);
 
 	ret = platform_device_add(at91sam9g20ek_snd_device);
 	if (ret) {
@@ -265,9 +247,6 @@ static int __init at91sam9g20ek_init(void)
 
 	return ret;
 
-err_ssc:
-	ssc_free(ssc);
-	ssc_p->ssc = NULL;
 err_mclk:
 	clk_put(mclk);
 	mclk = NULL;
@@ -277,16 +256,6 @@ err:
 
 static void __exit at91sam9g20ek_exit(void)
 {
-	struct atmel_ssc_info *ssc_p = at91sam9g20ek_dai.cpu_dai->private_data;
-	struct ssc_device *ssc;
-
-	if (ssc_p != NULL) {
-		ssc = ssc_p->ssc;
-		if (ssc != NULL)
-			ssc_free(ssc);
-		ssc_p->ssc = NULL;
-	}
-
 	platform_device_unregister(at91sam9g20ek_snd_device);
 	at91sam9g20ek_snd_device = NULL;
 	clk_put(mclk);

+ 9 - 26
sound/soc/atmel/snd-soc-afeb9260.c

@@ -46,8 +46,8 @@ static int afeb9260_hw_params(struct snd_pcm_substream *substream,
 			 struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 	int err;
 
 	/* Set codec DAI configuration */
@@ -102,8 +102,9 @@ static const struct snd_soc_dapm_route audio_map[] = {
 	{"MICIN", NULL, "Mic Jack"},
 };
 
-static int afeb9260_tlv320aic23_init(struct snd_soc_codec *codec)
+static int afeb9260_tlv320aic23_init(struct snd_soc_pcm_runtime *rtd)
 {
+	struct snd_soc_codec *codec = rtd->codec;
 
 	/* Add afeb9260 specific widgets */
 	snd_soc_dapm_new_controls(codec, tlv320aic23_dapm_widgets,
@@ -125,8 +126,10 @@ static int afeb9260_tlv320aic23_init(struct snd_soc_codec *codec)
 static struct snd_soc_dai_link afeb9260_dai = {
 	.name = "TLV320AIC23",
 	.stream_name = "AIC23",
-	.cpu_dai = &atmel_ssc_dai[0],
-	.codec_dai = &tlv320aic23_dai,
+	.cpu_dai_name = "atmel-ssc-dai.0",
+	.codec_dai_name = "tlv320aic23-hifi",
+	.platform_name = "atmel_pcm-audio",
+	.codec_name = "tlv320aic23-codec.0-0x1a",
 	.init = afeb9260_tlv320aic23_init,
 	.ops = &afeb9260_ops,
 };
@@ -134,37 +137,20 @@ static struct snd_soc_dai_link afeb9260_dai = {
 /* Audio machine driver */
 static struct snd_soc_card snd_soc_machine_afeb9260 = {
 	.name = "AFEB9260",
-	.platform = &atmel_soc_platform,
 	.dai_link = &afeb9260_dai,
 	.num_links = 1,
 };
 
-/* Audio subsystem */
-static struct snd_soc_device afeb9260_snd_devdata = {
-	.card = &snd_soc_machine_afeb9260,
-	.codec_dev = &soc_codec_dev_tlv320aic23,
-};
-
 static struct platform_device *afeb9260_snd_device;
 
 static int __init afeb9260_soc_init(void)
 {
 	int err;
 	struct device *dev;
-	struct atmel_ssc_info *ssc_p = afeb9260_dai.cpu_dai->private_data;
-	struct ssc_device *ssc = NULL;
 
 	if (!(machine_is_afeb9260()))
 		return -ENODEV;
 
-	ssc = ssc_request(0);
-	if (IS_ERR(ssc)) {
-		printk(KERN_ERR "ASoC: Failed to request SSC 0\n");
-		err = PTR_ERR(ssc);
-		ssc = NULL;
-		goto err_ssc;
-	}
-	ssc_p->ssc = ssc;
 
 	afeb9260_snd_device = platform_device_alloc("soc-audio", -1);
 	if (!afeb9260_snd_device) {
@@ -172,8 +158,7 @@ static int __init afeb9260_soc_init(void)
 		return -ENOMEM;
 	}
 
-	platform_set_drvdata(afeb9260_snd_device, &afeb9260_snd_devdata);
-	afeb9260_snd_devdata.dev = &afeb9260_snd_device->dev;
+	platform_set_drvdata(afeb9260_snd_device, &snd_soc_machine_afeb9260);
 	err = platform_device_add(afeb9260_snd_device);
 	if (err)
 		goto err1;
@@ -184,9 +169,7 @@ static int __init afeb9260_soc_init(void)
 err1:
 	platform_device_del(afeb9260_snd_device);
 	platform_device_put(afeb9260_snd_device);
-err_ssc:
 	return err;
-
 }
 
 static void __exit afeb9260_soc_exit(void)

+ 12 - 23
sound/soc/au1x/db1200.c

@@ -19,7 +19,6 @@
 #include <asm/mach-au1x00/au1xxx_dbdma.h>
 #include <asm/mach-db1x00/bcsr.h>
 
-#include "../codecs/ac97.h"
 #include "../codecs/wm8731.h"
 #include "psc.h"
 
@@ -28,20 +27,16 @@
 static struct snd_soc_dai_link db1200_ac97_dai = {
 	.name		= "AC97",
 	.stream_name	= "AC97 HiFi",
-	.cpu_dai	= &au1xpsc_ac97_dai,
-	.codec_dai	= &ac97_dai,
+	.cpu_dai_name	= "au1xpsc-ac97",
+	.codec_dai_name	= "ac97-hifi",
+	.platform_name	=  "au1xpsc-pcm-audio",
+	.codec_name	= "ac97-codec",
 };
 
 static struct snd_soc_card db1200_ac97_machine = {
 	.name		= "DB1200_AC97",
 	.dai_link	= &db1200_ac97_dai,
 	.num_links	= 1,
-	.platform	= &au1xpsc_soc_platform,
-};
-
-static struct snd_soc_device db1200_ac97_devdata = {
-	.card		= &db1200_ac97_machine,
-	.codec_dev	= &soc_codec_dev_ac97,
 };
 
 /*-------------------------  I2S PART  ---------------------------*/
@@ -49,8 +44,8 @@ static struct snd_soc_device db1200_ac97_devdata = {
 static int db1200_i2s_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 	int ret;
 
 	/* WM8731 has its own 12MHz crystal */
@@ -80,8 +75,10 @@ static struct snd_soc_ops db1200_i2s_wm8731_ops = {
 static struct snd_soc_dai_link db1200_i2s_dai = {
 	.name		= "WM8731",
 	.stream_name	= "WM8731 PCM",
-	.cpu_dai	= &au1xpsc_i2s_dai,
-	.codec_dai	= &wm8731_dai,
+	.cpu_dai_name	= "au1xpsc",
+	.codec_dai_name	= "wm8731-hifi"
+	.platform_name	= "au1xpsc-pcm-audio",
+	.codec_name	= "wm8731-codec.0-001a",
 	.ops		= &db1200_i2s_wm8731_ops,
 };
 
@@ -89,12 +86,6 @@ static struct snd_soc_card db1200_i2s_machine = {
 	.name		= "DB1200_I2S",
 	.dai_link	= &db1200_i2s_dai,
 	.num_links	= 1,
-	.platform	= &au1xpsc_soc_platform,
-};
-
-static struct snd_soc_device db1200_i2s_devdata = {
-	.card		= &db1200_i2s_machine,
-	.codec_dev	= &soc_codec_dev_wm8731,
 };
 
 /*-------------------------  COMMON PART  ---------------------------*/
@@ -112,12 +103,10 @@ static int __init db1200_audio_load(void)
 
 	/* DB1200 board setup set PSC1MUX to preferred audio device */
 	if (bcsr_read(BCSR_RESETS) & BCSR_RESETS_PSC1MUX)
-		platform_set_drvdata(db1200_asoc_dev, &db1200_i2s_devdata);
+		platform_set_drvdata(db1200_asoc_dev, &db1200_i2s_machine);
 	else
-		platform_set_drvdata(db1200_asoc_dev, &db1200_ac97_devdata);
+		platform_set_drvdata(db1200_asoc_dev, &db1200_ac97_machine);
 
-	db1200_ac97_devdata.dev = &db1200_asoc_dev->dev;
-	db1200_i2s_devdata.dev = &db1200_asoc_dev->dev;
 	ret = platform_device_add(db1200_asoc_dev);
 
 	if (ret) {

+ 6 - 13
sound/soc/au1x/dbdma2.c

@@ -329,7 +329,7 @@ static int au1xpsc_pcm_new(struct snd_card *card,
 	return 0;
 }
 
-static int au1xpsc_pcm_probe(struct platform_device *pdev)
+static int au1xpsc_pcm_probe(struct snd_soc_platform *platform)
 {
 	if (!au1xpsc_audio_pcmdma[PCM_TX] || !au1xpsc_audio_pcmdma[PCM_RX])
 		return -ENODEV;
@@ -337,17 +337,10 @@ static int au1xpsc_pcm_probe(struct platform_device *pdev)
 	return 0;
 }
 
-static int au1xpsc_pcm_remove(struct platform_device *pdev)
-{
-	return 0;
-}
-
 /* au1xpsc audio platform */
-struct snd_soc_platform au1xpsc_soc_platform = {
-	.name		= "au1xpsc-pcm-dbdma",
+struct snd_soc_platform_driver au1xpsc_soc_platform = {
 	.probe		= au1xpsc_pcm_probe,
-	.remove		= au1xpsc_pcm_remove,
-	.pcm_ops 	= &au1xpsc_pcm_ops,
+	.ops		= &au1xpsc_pcm_ops,
 	.pcm_new	= au1xpsc_pcm_new,
 	.pcm_free	= au1xpsc_pcm_free_dma_buffers,
 };
@@ -387,7 +380,7 @@ static int __devinit au1xpsc_pcm_drvprobe(struct platform_device *pdev)
 	}
 	(au1xpsc_audio_pcmdma[PCM_RX])->ddma_id = r->start;
 
-	ret = snd_soc_register_platform(&au1xpsc_soc_platform);
+	ret = snd_soc_register_platform(&pdev->dev, &au1xpsc_soc_platform);
 	if (!ret)
 		return ret;
 
@@ -404,7 +397,7 @@ static int __devexit au1xpsc_pcm_drvremove(struct platform_device *pdev)
 {
 	int i;
 
-	snd_soc_unregister_platform(&au1xpsc_soc_platform);
+	snd_soc_unregister_platform(&pdev->dev);
 
 	for (i = 0; i < 2; i++) {
 		if (au1xpsc_audio_pcmdma[i]) {
@@ -419,7 +412,7 @@ static int __devexit au1xpsc_pcm_drvremove(struct platform_device *pdev)
 
 static struct platform_driver au1xpsc_pcm_driver = {
 	.driver	= {
-		.name	= "au1xpsc-pcm",
+		.name	= "au1xpsc-pcm-audio",
 		.owner	= THIS_MODULE,
 	},
 	.probe		= au1xpsc_pcm_drvprobe,

+ 6 - 14
sound/soc/au1x/psc-ac97.c

@@ -315,27 +315,19 @@ static int au1xpsc_ac97_trigger(struct snd_pcm_substream *substream,
 	return ret;
 }
 
-static int au1xpsc_ac97_probe(struct platform_device *pdev,
-			      struct snd_soc_dai *dai)
+static int au1xpsc_ac97_probe(struct snd_soc_dai *dai)
 {
 	return au1xpsc_ac97_workdata ? 0 : -ENODEV;
 }
 
-static void au1xpsc_ac97_remove(struct platform_device *pdev,
-				struct snd_soc_dai *dai)
-{
-}
-
 static struct snd_soc_dai_ops au1xpsc_ac97_dai_ops = {
 	.trigger	= au1xpsc_ac97_trigger,
 	.hw_params	= au1xpsc_ac97_hw_params,
 };
 
-struct snd_soc_dai au1xpsc_ac97_dai = {
-	.name			= "au1xpsc_ac97",
+struct snd_soc_dai_driver au1xpsc_ac97_dai = {
 	.ac97_control		= 1,
 	.probe			= au1xpsc_ac97_probe,
-	.remove			= au1xpsc_ac97_remove,
 	.playback = {
 		.rates		= AC97_RATES,
 		.formats	= AC97_FMTS,
@@ -395,7 +387,7 @@ static int __devinit au1xpsc_ac97_drvprobe(struct platform_device *pdev)
 	au_writel(PSC_SEL_PS_AC97MODE | sel, PSC_SEL(wd));
 	au_sync();
 
-	ret = snd_soc_register_dai(&au1xpsc_ac97_dai);
+	ret = snd_soc_register_dai(&pdev->dev, &au1xpsc_ac97_dai);
 	if (ret)
 		goto out1;
 
@@ -406,7 +398,7 @@ static int __devinit au1xpsc_ac97_drvprobe(struct platform_device *pdev)
 		return 0;
 	}
 
-	snd_soc_unregister_dai(&au1xpsc_ac97_dai);
+	snd_soc_unregister_dai(&pdev->dev);
 out1:
 	release_mem_region(r->start, resource_size(r));
 out0:
@@ -422,7 +414,7 @@ static int __devexit au1xpsc_ac97_drvremove(struct platform_device *pdev)
 	if (wd->dmapd)
 		au1xpsc_pcm_destroy(wd->dmapd);
 
-	snd_soc_unregister_dai(&au1xpsc_ac97_dai);
+	snd_soc_unregister_dai(&pdev->dev);
 
 	/* disable PSC completely */
 	au_writel(0, AC97_CFG(wd));
@@ -485,7 +477,7 @@ static struct dev_pm_ops au1xpscac97_pmops = {
 
 static struct platform_driver au1xpsc_ac97_driver = {
 	.driver	= {
-		.name	= "au1xpsc_ac97",
+		.name	= "au1xpsc-ac97",
 		.owner	= THIS_MODULE,
 		.pm	= AU1XPSCAC97_PMOPS,
 	},

+ 6 - 15
sound/soc/au1x/psc-i2s.c

@@ -263,27 +263,19 @@ static int au1xpsc_i2s_trigger(struct snd_pcm_substream *substream, int cmd,
 	return ret;
 }
 
-static int au1xpsc_i2s_probe(struct platform_device *pdev,
-			     struct snd_soc_dai *dai)
+static int au1xpsc_i2s_probe(struct snd_soc_dai *dai)
 {
 	return 	au1xpsc_i2s_workdata ? 0 : -ENODEV;
 }
 
-static void au1xpsc_i2s_remove(struct platform_device *pdev,
-			       struct snd_soc_dai *dai)
-{
-}
-
 static struct snd_soc_dai_ops au1xpsc_i2s_dai_ops = {
 	.trigger	= au1xpsc_i2s_trigger,
 	.hw_params	= au1xpsc_i2s_hw_params,
 	.set_fmt	= au1xpsc_i2s_set_fmt,
 };
 
-struct snd_soc_dai au1xpsc_i2s_dai = {
-	.name			= "au1xpsc_i2s",
+static struct snd_soc_dai_driver au1xpsc_i2s_dai = {
 	.probe			= au1xpsc_i2s_probe,
-	.remove			= au1xpsc_i2s_remove,
 	.playback = {
 		.rates		= AU1XPSC_I2S_RATES,
 		.formats	= AU1XPSC_I2S_FMTS,
@@ -298,7 +290,6 @@ struct snd_soc_dai au1xpsc_i2s_dai = {
 	},
 	.ops = &au1xpsc_i2s_dai_ops,
 };
-EXPORT_SYMBOL(au1xpsc_i2s_dai);
 
 static int __devinit au1xpsc_i2s_drvprobe(struct platform_device *pdev)
 {
@@ -346,7 +337,7 @@ static int __devinit au1xpsc_i2s_drvprobe(struct platform_device *pdev)
 	 * time out.
 	 */
 
-	ret = snd_soc_register_dai(&au1xpsc_i2s_dai);
+	ret = snd_soc_register_dai(&pdev->dev, &au1xpsc_i2s_dai);
 	if (ret)
 		goto out1;
 
@@ -358,7 +349,7 @@ static int __devinit au1xpsc_i2s_drvprobe(struct platform_device *pdev)
 		return 0;
 	}
 
-	snd_soc_unregister_dai(&au1xpsc_i2s_dai);
+	snd_soc_unregister_dai(&pdev->dev);
 out1:
 	release_mem_region(r->start, resource_size(r));
 out0:
@@ -374,7 +365,7 @@ static int __devexit au1xpsc_i2s_drvremove(struct platform_device *pdev)
 	if (wd->dmapd)
 		au1xpsc_pcm_destroy(wd->dmapd);
 
-	snd_soc_unregister_dai(&au1xpsc_i2s_dai);
+	snd_soc_unregister_dai(&pdev->dev);
 
 	au_writel(0, I2S_CFG(wd));
 	au_sync();
@@ -436,7 +427,7 @@ static struct dev_pm_ops au1xpsci2s_pmops = {
 
 static struct platform_driver au1xpsc_i2s_driver = {
 	.driver		= {
-		.name	= "au1xpsc_i2s",
+		.name	= "au1xpsc",
 		.owner	= THIS_MODULE,
 		.pm	= AU1XPSCI2S_PMOPS,
 	},

+ 0 - 3
sound/soc/au1x/psc.h

@@ -16,9 +16,6 @@
 #ifndef _AU1X_PCM_H
 #define _AU1X_PCM_H
 
-extern struct snd_soc_dai au1xpsc_ac97_dai;
-extern struct snd_soc_dai au1xpsc_i2s_dai;
-extern struct snd_soc_platform au1xpsc_soc_platform;
 extern struct snd_ac97_bus_ops soc_ac97_ops;
 
 /* DBDMA helpers */

+ 31 - 12
sound/soc/blackfin/bf5xx-ac97-pcm.c

@@ -422,14 +422,14 @@ int bf5xx_pcm_ac97_new(struct snd_card *card, struct snd_soc_dai *dai,
 	if (!card->dev->coherent_dma_mask)
 		card->dev->coherent_dma_mask = DMA_BIT_MASK(32);
 
-	if (dai->playback.channels_min) {
+	if (dai->driver->playback.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_PLAYBACK);
 		if (ret)
 			goto out;
 	}
 
-	if (dai->capture.channels_min) {
+	if (dai->driver->capture.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_CAPTURE);
 		if (ret)
@@ -439,25 +439,44 @@ int bf5xx_pcm_ac97_new(struct snd_card *card, struct snd_soc_dai *dai,
 	return ret;
 }
 
-struct snd_soc_platform bf5xx_ac97_soc_platform = {
-	.name		= "bf5xx-audio",
-	.pcm_ops 	= &bf5xx_pcm_ac97_ops,
+static struct snd_soc_platform_driver bf5xx_ac97_soc_platform = {
+	.ops			= &bf5xx_pcm_ac97_ops,
 	.pcm_new	= bf5xx_pcm_ac97_new,
 	.pcm_free	= bf5xx_pcm_free_dma_buffers,
 };
-EXPORT_SYMBOL_GPL(bf5xx_ac97_soc_platform);
 
-static int __init bfin_ac97_init(void)
+static int __devinit bf5xx_soc_platform_probe(struct platform_device *pdev)
 {
-	return snd_soc_register_platform(&bf5xx_ac97_soc_platform);
+	return snd_soc_register_platform(&pdev->dev, &bf5xx_ac97_soc_platform);
 }
-module_init(bfin_ac97_init);
 
-static void __exit bfin_ac97_exit(void)
+static int __devexit bf5xx_soc_platform_remove(struct platform_device *pdev)
 {
-	snd_soc_unregister_platform(&bf5xx_ac97_soc_platform);
+	snd_soc_unregister_platform(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver bf5xx_pcm_driver = {
+	.driver = {
+			.name = "bf5xx-pcm-audio",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = bf5xx_soc_platform_probe,
+	.remove = __devexit_p(bf5xx_soc_platform_remove),
+};
+
+static int __init snd_bf5xx_pcm_init(void)
+{
+	return platform_driver_register(&bf5xx_pcm_driver);
+}
+module_init(snd_bf5xx_pcm_init);
+
+static void __exit snd_bf5xx_pcm_exit(void)
+{
+	platform_driver_unregister(&bf5xx_pcm_driver);
 }
-module_exit(bfin_ac97_exit);
+module_exit(snd_bf5xx_pcm_exit);
 
 MODULE_AUTHOR("Cliff Cai");
 MODULE_DESCRIPTION("ADI Blackfin AC97 PCM DMA module");

+ 0 - 3
sound/soc/blackfin/bf5xx-ac97-pcm.h

@@ -23,7 +23,4 @@ struct bf5xx_gpio {
 	u32 frm;
 };
 
-/* platform data */
-extern struct snd_soc_platform bf5xx_ac97_soc_platform;
-
 #endif

+ 30 - 11
sound/soc/blackfin/bf5xx-ac97.c

@@ -255,7 +255,7 @@ EXPORT_SYMBOL_GPL(soc_ac97_ops);
 #ifdef CONFIG_PM
 static int bf5xx_ac97_suspend(struct snd_soc_dai *dai)
 {
-	struct sport_device *sport = dai->private_data;
+	struct sport_device *sport = snd_soc_dai_get_drvdata(dai);
 
 	pr_debug("%s : sport %d\n", __func__, dai->id);
 	if (!dai->active)
@@ -270,7 +270,7 @@ static int bf5xx_ac97_suspend(struct snd_soc_dai *dai)
 static int bf5xx_ac97_resume(struct snd_soc_dai *dai)
 {
 	int ret;
-	struct sport_device *sport = dai->private_data;
+	struct sport_device *sport = snd_soc_dai_get_drvdata(dai);
 
 	pr_debug("%s : sport %d\n", __func__, dai->id);
 	if (!dai->active)
@@ -306,8 +306,7 @@ static int bf5xx_ac97_resume(struct snd_soc_dai *dai)
 #define bf5xx_ac97_resume	NULL
 #endif
 
-static int bf5xx_ac97_probe(struct platform_device *pdev,
-			    struct snd_soc_dai *dai)
+static int bf5xx_ac97_probe(struct snd_soc_dai *dai)
 {
 	int ret = 0;
 	cmd_count = (int *)get_zeroed_page(GFP_KERNEL);
@@ -379,8 +378,7 @@ peripheral_err:
 	return ret;
 }
 
-static void bf5xx_ac97_remove(struct platform_device *pdev,
-			      struct snd_soc_dai *dai)
+static int bf5xx_ac97_remove(struct snd_soc_dai *dai)
 {
 	free_page((unsigned long)cmd_count);
 	cmd_count = NULL;
@@ -388,11 +386,10 @@ static void bf5xx_ac97_remove(struct platform_device *pdev,
 #ifdef CONFIG_SND_BF5XX_HAVE_COLD_RESET
 	gpio_free(CONFIG_SND_BF5XX_RESET_GPIO_NUM);
 #endif
+	return 0;
 }
 
-struct snd_soc_dai bfin_ac97_dai = {
-	.name = "bf5xx-ac97",
-	.id = 0,
+struct snd_soc_dai_driver bfin_ac97_dai = {
 	.ac97_control = 1,
 	.probe = bf5xx_ac97_probe,
 	.remove = bf5xx_ac97_remove,
@@ -417,18 +414,40 @@ struct snd_soc_dai bfin_ac97_dai = {
 };
 EXPORT_SYMBOL_GPL(bfin_ac97_dai);
 
+static __devinit int asoc_bfin_ac97_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_dai(&pdev->dev, &bfin_ac97_dai);
+}
+
+static int __devexit asoc_bfin_ac97_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_dai(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver asoc_bfin_ac97_driver = {
+	.driver = {
+			.name = "bfin-ac97",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = asoc_bfin_ac97_probe,
+	.remove = __devexit_p(asoc_bfin_ac97_remove),
+};
+
 static int __init bfin_ac97_init(void)
 {
-	return snd_soc_register_dai(&bfin_ac97_dai);
+	return platform_driver_register(&asoc_bfin_ac97_driver);
 }
 module_init(bfin_ac97_init);
 
 static void __exit bfin_ac97_exit(void)
 {
-	snd_soc_unregister_dai(&bfin_ac97_dai);
+	platform_driver_unregister(&asoc_bfin_ac97_driver);
 }
 module_exit(bfin_ac97_exit);
 
+
 MODULE_AUTHOR("Roy Huang");
 MODULE_DESCRIPTION("AC97 driver for ADI Blackfin");
 MODULE_LICENSE("GPL");

+ 0 - 2
sound/soc/blackfin/bf5xx-ac97.h

@@ -50,8 +50,6 @@ struct ac97_frame {
 #define TAG_PCM_SR		0x0080
 #define TAG_PCM_LFE		0x0040
 
-extern struct snd_soc_dai bfin_ac97_dai;
-
 void bf5xx_pcm_to_ac97(struct ac97_frame *dst, const __u16 *src, \
 		size_t count, unsigned int chan_mask);
 

+ 9 - 14
sound/soc/blackfin/bf5xx-ad1836.c

@@ -40,9 +40,9 @@ static struct snd_soc_card bf5xx_ad1836;
 static int bf5xx_ad1836_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 
-	cpu_dai->private_data = sport_handle;
+	snd_soc_dai_set_drvdata(cpu_dai, sport_handle);
 	return 0;
 }
 
@@ -50,8 +50,8 @@ static int bf5xx_ad1836_hw_params(struct snd_pcm_substream *substream,
 	struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
 	unsigned int channel_map[] = {0, 4, 1, 5, 2, 6, 3, 7};
 	int ret = 0;
 	/* set cpu DAI configuration */
@@ -83,23 +83,19 @@ static struct snd_soc_ops bf5xx_ad1836_ops = {
 static struct snd_soc_dai_link bf5xx_ad1836_dai = {
 	.name = "ad1836",
 	.stream_name = "AD1836",
-	.cpu_dai = &bf5xx_tdm_dai,
-	.codec_dai = &ad1836_dai,
+	.cpu_dai_name = "bf5xx-tdm",
+	.codec_dai_name = "ad1836-hifi",
+	.platform_name = "bf5xx-tdm-pcm-audio",
+	.codec_name = "ad1836-codec.0",
 	.ops = &bf5xx_ad1836_ops,
 };
 
 static struct snd_soc_card bf5xx_ad1836 = {
 	.name = "bf5xx_ad1836",
-	.platform = &bf5xx_tdm_soc_platform,
 	.dai_link = &bf5xx_ad1836_dai,
 	.num_links = 1,
 };
 
-static struct snd_soc_device bf5xx_ad1836_snd_devdata = {
-	.card = &bf5xx_ad1836,
-	.codec_dev = &soc_codec_dev_ad1836,
-};
-
 static struct platform_device *bfxx_ad1836_snd_device;
 
 static int __init bf5xx_ad1836_init(void)
@@ -110,8 +106,7 @@ static int __init bf5xx_ad1836_init(void)
 	if (!bfxx_ad1836_snd_device)
 		return -ENOMEM;
 
-	platform_set_drvdata(bfxx_ad1836_snd_device, &bf5xx_ad1836_snd_devdata);
-	bf5xx_ad1836_snd_devdata.dev = &bfxx_ad1836_snd_device->dev;
+	platform_set_drvdata(bfxx_ad1836_snd_device, &bf5xx_ad1836);
 	ret = platform_device_add(bfxx_ad1836_snd_device);
 
 	if (ret)

+ 9 - 14
sound/soc/blackfin/bf5xx-ad193x.c

@@ -49,9 +49,9 @@ static struct snd_soc_card bf5xx_ad193x;
 static int bf5xx_ad193x_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 
-	cpu_dai->private_data = sport_handle;
+	snd_soc_dai_set_drvdata(cpu_dai, sport_handle);
 	return 0;
 }
 
@@ -59,8 +59,8 @@ static int bf5xx_ad193x_hw_params(struct snd_pcm_substream *substream,
 	struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
 	unsigned int channel_map[] = {0, 1, 2, 3, 4, 5, 6, 7};
 	int ret = 0;
 	/* set cpu DAI configuration */
@@ -97,23 +97,19 @@ static struct snd_soc_ops bf5xx_ad193x_ops = {
 static struct snd_soc_dai_link bf5xx_ad193x_dai = {
 	.name = "ad193x",
 	.stream_name = "AD193X",
-	.cpu_dai = &bf5xx_tdm_dai,
-	.codec_dai = &ad193x_dai,
+	.cpu_dai_name = "bf5xx-tdm",
+	.codec_dai_name ="ad193x-hifi",
+	.platform_name = "bf5xx-tdm-pcm-audio",
+	.codec_name = "ad193x-codec.5",
 	.ops = &bf5xx_ad193x_ops,
 };
 
 static struct snd_soc_card bf5xx_ad193x = {
 	.name = "bf5xx_ad193x",
-	.platform = &bf5xx_tdm_soc_platform,
 	.dai_link = &bf5xx_ad193x_dai,
 	.num_links = 1,
 };
 
-static struct snd_soc_device bf5xx_ad193x_snd_devdata = {
-	.card = &bf5xx_ad193x,
-	.codec_dev = &soc_codec_dev_ad193x,
-};
-
 static struct platform_device *bfxx_ad193x_snd_device;
 
 static int __init bf5xx_ad193x_init(void)
@@ -124,8 +120,7 @@ static int __init bf5xx_ad193x_init(void)
 	if (!bfxx_ad193x_snd_device)
 		return -ENOMEM;
 
-	platform_set_drvdata(bfxx_ad193x_snd_device, &bf5xx_ad193x_snd_devdata);
-	bf5xx_ad193x_snd_devdata.dev = &bfxx_ad193x_snd_device->dev;
+	platform_set_drvdata(bfxx_ad193x_snd_device, &bf5xx_ad193x);
 	ret = platform_device_add(bfxx_ad193x_snd_device);
 
 	if (ret)

+ 7 - 12
sound/soc/blackfin/bf5xx-ad1980.c

@@ -48,10 +48,10 @@ static struct snd_soc_card bf5xx_board;
 static int bf5xx_board_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 
 	pr_debug("%s enter\n", __func__);
-	cpu_dai->private_data = sport_handle;
+	snd_soc_dai_set_drvdata(cpu_dai, sport_handle);
 	return 0;
 }
 
@@ -62,23 +62,19 @@ static struct snd_soc_ops bf5xx_board_ops = {
 static struct snd_soc_dai_link bf5xx_board_dai = {
 	.name = "AC97",
 	.stream_name = "AC97 HiFi",
-	.cpu_dai = &bfin_ac97_dai,
-	.codec_dai = &ad1980_dai,
+	.cpu_dai_name = "bfin-ac97",
+	.codec_dai_name = "ad1980-hifi",
+	.platform_name = "bfin-pcm-audio",
+	.codec_name = "ad1980-codec",
 	.ops = &bf5xx_board_ops,
 };
 
 static struct snd_soc_card bf5xx_board = {
 	.name = "bf5xx-board",
-	.platform = &bf5xx_ac97_soc_platform,
 	.dai_link = &bf5xx_board_dai,
 	.num_links = 1,
 };
 
-static struct snd_soc_device bf5xx_board_snd_devdata = {
-	.card = &bf5xx_board,
-	.codec_dev = &soc_codec_dev_ad1980,
-};
-
 static struct platform_device *bf5xx_board_snd_device;
 
 static int __init bf5xx_board_init(void)
@@ -89,8 +85,7 @@ static int __init bf5xx_board_init(void)
 	if (!bf5xx_board_snd_device)
 		return -ENOMEM;
 
-	platform_set_drvdata(bf5xx_board_snd_device, &bf5xx_board_snd_devdata);
-	bf5xx_board_snd_devdata.dev = &bf5xx_board_snd_device->dev;
+	platform_set_drvdata(bf5xx_board_snd_device, &bf5xx_board);
 	ret = platform_device_add(bf5xx_board_snd_device);
 
 	if (ret)

+ 8 - 14
sound/soc/blackfin/bf5xx-ad73311.c

@@ -47,7 +47,6 @@
 #include "../codecs/ad73311.h"
 #include "bf5xx-sport.h"
 #include "bf5xx-i2s-pcm.h"
-#include "bf5xx-i2s.h"
 
 #if CONFIG_SND_BF5XX_SPORT_NUM == 0
 #define bfin_write_SPORT_TCR1	bfin_write_SPORT0_TCR1
@@ -150,10 +149,10 @@ static int bf5xx_probe(struct platform_device *pdev)
 static int bf5xx_ad73311_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 
 	pr_debug("%s enter\n", __func__);
-	cpu_dai->private_data = sport_handle;
+	snd_soc_dai_set_drvdata(cpu_dai, sport_handle);
 	return 0;
 }
 
@@ -161,7 +160,7 @@ static int bf5xx_ad73311_hw_params(struct snd_pcm_substream *substream,
 	struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 	int ret = 0;
 
 	pr_debug("%s rate %d format %x\n", __func__, params_rate(params),
@@ -185,24 +184,20 @@ static struct snd_soc_ops bf5xx_ad73311_ops = {
 static struct snd_soc_dai_link bf5xx_ad73311_dai = {
 	.name = "ad73311",
 	.stream_name = "AD73311",
-	.cpu_dai = &bf5xx_i2s_dai,
-	.codec_dai = &ad73311_dai,
+	.cpu_dai_name = "bf5xx-i2s",
+	.codec_dai_name = "ad73311-hifi",
+	.platform_name = "bfin-pcm-audio",
+	.codec_name = "ad73311-codec",
 	.ops = &bf5xx_ad73311_ops,
 };
 
 static struct snd_soc_card bf5xx_ad73311 = {
 	.name = "bf5xx_ad73311",
-	.platform = &bf5xx_i2s_soc_platform,
 	.probe = bf5xx_probe,
 	.dai_link = &bf5xx_ad73311_dai,
 	.num_links = 1,
 };
 
-static struct snd_soc_device bf5xx_ad73311_snd_devdata = {
-	.card = &bf5xx_ad73311,
-	.codec_dev = &soc_codec_dev_ad73311,
-};
-
 static struct platform_device *bf5xx_ad73311_snd_device;
 
 static int __init bf5xx_ad73311_init(void)
@@ -214,8 +209,7 @@ static int __init bf5xx_ad73311_init(void)
 	if (!bf5xx_ad73311_snd_device)
 		return -ENOMEM;
 
-	platform_set_drvdata(bf5xx_ad73311_snd_device, &bf5xx_ad73311_snd_devdata);
-	bf5xx_ad73311_snd_devdata.dev = &bf5xx_ad73311_snd_device->dev;
+	platform_set_drvdata(bf5xx_ad73311_snd_device, &bf5xx_ad73311);
 	ret = platform_device_add(bf5xx_ad73311_snd_device);
 
 	if (ret)

+ 31 - 13
sound/soc/blackfin/bf5xx-i2s-pcm.c

@@ -40,7 +40,6 @@
 #include <asm/dma.h>
 
 #include "bf5xx-i2s-pcm.h"
-#include "bf5xx-i2s.h"
 #include "bf5xx-sport.h"
 
 static void bf5xx_dma_irq(void *data)
@@ -257,14 +256,14 @@ int bf5xx_pcm_i2s_new(struct snd_card *card, struct snd_soc_dai *dai,
 	if (!card->dev->coherent_dma_mask)
 		card->dev->coherent_dma_mask = DMA_BIT_MASK(32);
 
-	if (dai->playback.channels_min) {
+	if (dai->driver->playback.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_PLAYBACK);
 		if (ret)
 			goto out;
 	}
 
-	if (dai->capture.channels_min) {
+	if (dai->driver->capture.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_CAPTURE);
 		if (ret)
@@ -274,25 +273,44 @@ int bf5xx_pcm_i2s_new(struct snd_card *card, struct snd_soc_dai *dai,
 	return ret;
 }
 
-struct snd_soc_platform bf5xx_i2s_soc_platform = {
-	.name		= "bf5xx-audio",
-	.pcm_ops 	= &bf5xx_pcm_i2s_ops,
+static struct snd_soc_platform_driver bf5xx_i2s_soc_platform = {
+	.ops		= &bf5xx_pcm_i2s_ops,
 	.pcm_new	= bf5xx_pcm_i2s_new,
 	.pcm_free	= bf5xx_pcm_free_dma_buffers,
 };
-EXPORT_SYMBOL_GPL(bf5xx_i2s_soc_platform);
 
-static int __init bfin_i2s_init(void)
+static int __devinit bfin_i2s_soc_platform_probe(struct platform_device *pdev)
 {
-	return snd_soc_register_platform(&bf5xx_i2s_soc_platform);
+	return snd_soc_register_platform(&pdev->dev, &bf5xx_i2s_soc_platform);
 }
-module_init(bfin_i2s_init);
 
-static void __exit bfin_i2s_exit(void)
+static int __devexit bfin_i2s_soc_platform_remove(struct platform_device *pdev)
 {
-	snd_soc_unregister_platform(&bf5xx_i2s_soc_platform);
+	snd_soc_unregister_platform(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver bfin_i2s_pcm_driver = {
+	.driver = {
+			.name = "bfin-pcm-audio",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = bfin_i2s_soc_platform_probe,
+	.remove = __devexit_p(bfin_i2s_soc_platform_remove),
+};
+
+static int __init snd_bfin_i2s_pcm_init(void)
+{
+	return platform_driver_register(&bfin_i2s_pcm_driver);
+}
+module_init(snd_bfin_i2s_pcm_init);
+
+static void __exit snd_bfin_i2s_pcm_exit(void)
+{
+	platform_driver_unregister(&bfin_i2s_pcm_driver);
 }
-module_exit(bfin_i2s_exit);
+module_exit(snd_bfin_i2s_pcm_exit);
 
 MODULE_AUTHOR("Cliff Cai");
 MODULE_DESCRIPTION("ADI Blackfin I2S PCM DMA module");

+ 0 - 3
sound/soc/blackfin/bf5xx-i2s-pcm.h

@@ -23,7 +23,4 @@ struct bf5xx_gpio {
 	u32 frm;
 };
 
-/* platform data */
-extern struct snd_soc_platform bf5xx_i2s_soc_platform;
-
 #endif

+ 31 - 14
sound/soc/blackfin/bf5xx-i2s.c

@@ -42,7 +42,6 @@
 #include <linux/gpio.h>
 
 #include "bf5xx-sport.h"
-#include "bf5xx-i2s.h"
 
 struct bf5xx_i2s_port {
 	u16 tcr1;
@@ -195,8 +194,7 @@ static void bf5xx_i2s_shutdown(struct snd_pcm_substream *substream,
 		bf5xx_i2s.configured = 0;
 }
 
-static int bf5xx_i2s_probe(struct platform_device *pdev,
-			   struct snd_soc_dai *dai)
+static int bf5xx_i2s_probe(struct snd_soc_dai *dai)
 {
 	pr_debug("%s enter\n", __func__);
 	if (peripheral_request_list(&sport_req[sport_num][0], "soc-audio")) {
@@ -215,11 +213,11 @@ static int bf5xx_i2s_probe(struct platform_device *pdev,
 	return 0;
 }
 
-static void bf5xx_i2s_remove(struct platform_device *pdev,
-			struct snd_soc_dai *dai)
+static int bf5xx_i2s_remove(struct snd_soc_dai *dai)
 {
 	pr_debug("%s enter\n", __func__);
 	peripheral_free_list(&sport_req[sport_num][0]);
+	return 0;
 }
 
 #ifdef CONFIG_PM
@@ -228,9 +226,9 @@ static int bf5xx_i2s_suspend(struct snd_soc_dai *dai)
 
 	pr_debug("%s : sport %d\n", __func__, dai->id);
 
-	if (dai->capture.active)
+	if (dai->capture_active)
 		sport_rx_stop(sport_handle);
-	if (dai->playback.active)
+	if (dai->playback_active)
 		sport_tx_stop(sport_handle);
 	return 0;
 }
@@ -277,9 +275,7 @@ static struct snd_soc_dai_ops bf5xx_i2s_dai_ops = {
 	.set_fmt	= bf5xx_i2s_set_dai_fmt,
 };
 
-struct snd_soc_dai bf5xx_i2s_dai = {
-	.name = "bf5xx-i2s",
-	.id = 0,
+static struct snd_soc_dai_driver bf5xx_i2s_dai = {
 	.probe = bf5xx_i2s_probe,
 	.remove = bf5xx_i2s_remove,
 	.suspend = bf5xx_i2s_suspend,
@@ -296,18 +292,39 @@ struct snd_soc_dai bf5xx_i2s_dai = {
 		.formats = BF5XX_I2S_FORMATS,},
 	.ops = &bf5xx_i2s_dai_ops,
 };
-EXPORT_SYMBOL_GPL(bf5xx_i2s_dai);
+
+static int bfin_i2s_drv_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_dai(&pdev->dev, &bf5xx_i2s_dai);
+}
+
+static int __devexit bfin_i2s_drv_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_dai(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver bfin_i2s_driver = {
+	.probe = bfin_i2s_drv_probe,
+	.remove = __devexit_p(bfin_i2s_drv_remove),
+
+	.driver = {
+		.name = "bf5xx-i2s",
+		.owner = THIS_MODULE,
+	},
+};
 
 static int __init bfin_i2s_init(void)
 {
-	return snd_soc_register_dai(&bf5xx_i2s_dai);
+	return platform_driver_register(&bfin_i2s_driver);
 }
-module_init(bfin_i2s_init);
 
 static void __exit bfin_i2s_exit(void)
 {
-	snd_soc_unregister_dai(&bf5xx_i2s_dai);
+	platform_driver_unregister(&bfin_i2s_driver);
 }
+
+module_init(bfin_i2s_init);
 module_exit(bfin_i2s_exit);
 
 /* Module information */

+ 0 - 14
sound/soc/blackfin/bf5xx-i2s.h

@@ -1,14 +0,0 @@
-/*
- * sound/soc/blackfin/bf5xx-i2s.h
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- */
-
-#ifndef _BF5XX_I2S_H
-#define _BF5XX_I2S_H
-
-extern struct snd_soc_dai bf5xx_i2s_dai;
-
-#endif

+ 9 - 29
sound/soc/blackfin/bf5xx-ssm2602.c

@@ -42,17 +42,16 @@
 #include "../codecs/ssm2602.h"
 #include "bf5xx-sport.h"
 #include "bf5xx-i2s-pcm.h"
-#include "bf5xx-i2s.h"
 
 static struct snd_soc_card bf5xx_ssm2602;
 
 static int bf5xx_ssm2602_startup(struct snd_pcm_substream *substream)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 
 	pr_debug("%s enter\n", __func__);
-	cpu_dai->private_data = sport_handle;
+	snd_soc_dai_set_drvdata(cpu_dai, sport_handle);
 	return 0;
 }
 
@@ -60,8 +59,8 @@ static int bf5xx_ssm2602_hw_params(struct snd_pcm_substream *substream,
 	struct snd_pcm_hw_params *params)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
-	struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
+	struct snd_soc_dai *codec_dai = rtd->codec_dai;
+	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
 	unsigned int clk = 0;
 	int ret = 0;
 
@@ -118,36 +117,19 @@ static struct snd_soc_ops bf5xx_ssm2602_ops = {
 static struct snd_soc_dai_link bf5xx_ssm2602_dai = {
 	.name = "ssm2602",
 	.stream_name = "SSM2602",
-	.cpu_dai = &bf5xx_i2s_dai,
-	.codec_dai = &ssm2602_dai,
+	.cpu_dai_name = "bf5xx-i2s",
+	.codec_dai_name = "ssm2602-hifi",
+	.platform_name = "bf5xx-pcm-audio",
+	.codec_name = "ssm2602-codec.0-0x1b",
 	.ops = &bf5xx_ssm2602_ops,
 };
 
-/*
- * SSM2602 2 wire address is determined by CSB
- * state during powerup.
- *    low  = 0x1a
- *    high = 0x1b
- */
-
-static struct ssm2602_setup_data bf5xx_ssm2602_setup = {
-	.i2c_bus = 0,
-	.i2c_address = 0x1b,
-};
-
 static struct snd_soc_card bf5xx_ssm2602 = {
 	.name = "bf5xx_ssm2602",
-	.platform = &bf5xx_i2s_soc_platform,
 	.dai_link = &bf5xx_ssm2602_dai,
 	.num_links = 1,
 };
 
-static struct snd_soc_device bf5xx_ssm2602_snd_devdata = {
-	.card = &bf5xx_ssm2602,
-	.codec_dev = &soc_codec_dev_ssm2602,
-	.codec_data = &bf5xx_ssm2602_setup,
-};
-
 static struct platform_device *bf5xx_ssm2602_snd_device;
 
 static int __init bf5xx_ssm2602_init(void)
@@ -159,9 +141,7 @@ static int __init bf5xx_ssm2602_init(void)
 	if (!bf5xx_ssm2602_snd_device)
 		return -ENOMEM;
 
-	platform_set_drvdata(bf5xx_ssm2602_snd_device,
-				&bf5xx_ssm2602_snd_devdata);
-	bf5xx_ssm2602_snd_devdata.dev = &bf5xx_ssm2602_snd_device->dev;
+	platform_set_drvdata(bf5xx_ssm2602_snd_device, &bf5xx_ssm2602);
 	ret = platform_device_add(bf5xx_ssm2602_snd_device);
 
 	if (ret)

+ 31 - 12
sound/soc/blackfin/bf5xx-tdm-pcm.c

@@ -290,14 +290,14 @@ static int bf5xx_pcm_tdm_new(struct snd_card *card, struct snd_soc_dai *dai,
 	if (!card->dev->coherent_dma_mask)
 		card->dev->coherent_dma_mask = DMA_BIT_MASK(32);
 
-	if (dai->playback.channels_min) {
+	if (dai->driver->playback.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_PLAYBACK);
 		if (ret)
 			goto out;
 	}
 
-	if (dai->capture.channels_min) {
+	if (dai->driver->capture.channels_min) {
 		ret = bf5xx_pcm_preallocate_dma_buffer(pcm,
 			SNDRV_PCM_STREAM_CAPTURE);
 		if (ret)
@@ -307,25 +307,44 @@ out:
 	return ret;
 }
 
-struct snd_soc_platform bf5xx_tdm_soc_platform = {
-	.name           = "bf5xx-audio",
-	.pcm_ops        = &bf5xx_pcm_tdm_ops,
+static struct snd_soc_platform_driver bf5xx_tdm_soc_platform = {
+	.ops        = &bf5xx_pcm_tdm_ops,
 	.pcm_new        = bf5xx_pcm_tdm_new,
 	.pcm_free       = bf5xx_pcm_free_dma_buffers,
 };
-EXPORT_SYMBOL_GPL(bf5xx_tdm_soc_platform);
 
-static int __init bfin_pcm_tdm_init(void)
+static int __devinit bf5xx_soc_platform_probe(struct platform_device *pdev)
 {
-	return snd_soc_register_platform(&bf5xx_tdm_soc_platform);
+	return snd_soc_register_platform(&pdev->dev, &bf5xx_tdm_soc_platform);
 }
-module_init(bfin_pcm_tdm_init);
 
-static void __exit bfin_pcm_tdm_exit(void)
+static int __devexit bf5xx_soc_platform_remove(struct platform_device *pdev)
 {
-	snd_soc_unregister_platform(&bf5xx_tdm_soc_platform);
+	snd_soc_unregister_platform(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver bfin_tdm_driver = {
+	.driver = {
+			.name = "bf5xx-tdm-pcm-audio",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = bf5xx_soc_platform_probe,
+	.remove = __devexit_p(bf5xx_soc_platform_remove),
+};
+
+static int __init snd_bfin_tdm_init(void)
+{
+	return platform_driver_register(&bfin_tdm_driver);
+}
+module_init(snd_bfin_tdm_init);
+
+static void __exit snd_bfin_tdm_exit(void)
+{
+	platform_driver_unregister(&bfin_tdm_driver);
 }
-module_exit(bfin_pcm_tdm_exit);
+module_exit(snd_bfin_tdm_exit);
 
 MODULE_AUTHOR("Barry Song");
 MODULE_DESCRIPTION("ADI Blackfin TDM PCM DMA module");

+ 0 - 3
sound/soc/blackfin/bf5xx-tdm-pcm.h

@@ -15,7 +15,4 @@ struct bf5xx_pcm_dma_params {
 	char *name;                     /* stream identifier */
 };
 
-/* platform data */
-extern struct snd_soc_platform bf5xx_tdm_soc_platform;
-
 #endif

+ 6 - 9
sound/soc/blackfin/bf5xx-tdm.c

@@ -214,9 +214,9 @@ static int bf5xx_tdm_suspend(struct snd_soc_dai *dai)
 
 	if (!dai->active)
 		return 0;
-	if (dai->capture.active)
+	if (dai->capture_active)
 		sport_rx_stop(sport);
-	if (dai->playback.active)
+	if (dai->playback_active)
 		sport_tx_stop(sport);
 	return 0;
 }
@@ -224,7 +224,7 @@ static int bf5xx_tdm_suspend(struct snd_soc_dai *dai)
 static int bf5xx_tdm_resume(struct snd_soc_dai *dai)
 {
 	int ret;
-	struct sport_device *sport = dai->private_data;
+	struct sport_device *sport = snd_soc_dai_get_drvdata(dai);
 
 	if (!dai->active)
 		return 0;
@@ -262,9 +262,7 @@ static struct snd_soc_dai_ops bf5xx_tdm_dai_ops = {
 	.set_channel_map   = bf5xx_tdm_set_channel_map,
 };
 
-struct snd_soc_dai bf5xx_tdm_dai = {
-	.name = "bf5xx-tdm",
-	.id = 0,
+static struct snd_soc_dai_driver bf5xx_tdm_dai = {
 	.suspend = bf5xx_tdm_suspend,
 	.resume = bf5xx_tdm_resume,
 	.playback = {
@@ -279,7 +277,6 @@ struct snd_soc_dai bf5xx_tdm_dai = {
 		.formats = SNDRV_PCM_FMTBIT_S32_LE,},
 	.ops = &bf5xx_tdm_dai_ops,
 };
-EXPORT_SYMBOL_GPL(bf5xx_tdm_dai);
 
 static int __devinit bfin_tdm_probe(struct platform_device *pdev)
 {
@@ -320,7 +317,7 @@ static int __devinit bfin_tdm_probe(struct platform_device *pdev)
 		goto sport_config_err;
 	}
 
-	ret = snd_soc_register_dai(&bf5xx_tdm_dai);
+	ret = snd_soc_register_dai(&pdev->dev, &bf5xx_tdm_dai);
 	if (ret) {
 		pr_err("Failed to register DAI: %d\n", ret);
 		goto sport_config_err;
@@ -337,7 +334,7 @@ sport_config_err:
 static int __devexit bfin_tdm_remove(struct platform_device *pdev)
 {
 	peripheral_free_list(&sport_req[sport_num][0]);
-	snd_soc_unregister_dai(&bf5xx_tdm_dai);
+	snd_soc_unregister_dai(&pdev->dev);
 
 	return 0;
 }

+ 0 - 2
sound/soc/blackfin/bf5xx-tdm.h

@@ -20,6 +20,4 @@ struct bf5xx_tdm_port {
 	int configured;
 };
 
-extern struct snd_soc_dai bf5xx_tdm_dai;
-
 #endif

+ 55 - 69
sound/soc/codecs/ac97.c

@@ -21,7 +21,6 @@
 #include <sound/ac97_codec.h>
 #include <sound/initval.h>
 #include <sound/soc.h>
-#include "ac97.h"
 
 #define AC97_VERSION "0.6"
 
@@ -30,8 +29,7 @@ static int ac97_prepare(struct snd_pcm_substream *substream,
 {
 	struct snd_pcm_runtime *runtime = substream->runtime;
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 
 	int reg = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ?
 		  AC97_PCM_FRONT_DAC_RATE : AC97_PCM_LR_ADC_RATE;
@@ -46,8 +44,8 @@ static struct snd_soc_dai_ops ac97_dai_ops = {
 	.prepare	= ac97_prepare,
 };
 
-struct snd_soc_dai ac97_dai = {
-	.name = "AC97 HiFi",
+static struct snd_soc_dai_driver ac97_dai = {
+	.name = "ac97-hifi",
 	.ac97_control = 1,
 	.playback = {
 		.stream_name = "AC97 Playback",
@@ -63,7 +61,6 @@ struct snd_soc_dai ac97_dai = {
 		.formats = SND_SOC_STD_AC97_FMTS,},
 	.ops = &ac97_dai_ops,
 };
-EXPORT_SYMBOL_GPL(ac97_dai);
 
 static unsigned int ac97_read(struct snd_soc_codec *codec,
 	unsigned int reg)
@@ -78,95 +75,49 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg,
 	return 0;
 }
 
-static int ac97_soc_probe(struct platform_device *pdev)
+static int ac97_soc_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_card *card = socdev->card;
-	struct snd_soc_codec *codec;
 	struct snd_ac97_bus *ac97_bus;
 	struct snd_ac97_template ac97_template;
-	int i;
-	int ret = 0;
+	int ret;
 
 	printk(KERN_INFO "AC97 SoC Audio Codec %s\n", AC97_VERSION);
 
-	socdev->card->codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (!socdev->card->codec)
-		return -ENOMEM;
-	codec = socdev->card->codec;
-	mutex_init(&codec->mutex);
-
-	codec->name = "AC97";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ac97_dai;
-	codec->num_dai = 1;
-	codec->write = ac97_write;
-	codec->read = ac97_read;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0)
-		goto err;
+	ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0);
+	if (ret < 0) {
+		printk(KERN_ERR "ASoC: failed to init gen ac97 glue\n");
+		return ret;
+	}
 
 	/* add codec as bus device for standard ac97 */
-	ret = snd_ac97_bus(codec->card, 0, &soc_ac97_ops, NULL, &ac97_bus);
+	ret = snd_ac97_bus(codec->card->snd_card, 0, &soc_ac97_ops, NULL, &ac97_bus);
 	if (ret < 0)
-		goto bus_err;
+		return ret;
 
 	memset(&ac97_template, 0, sizeof(struct snd_ac97_template));
 	ret = snd_ac97_mixer(ac97_bus, &ac97_template, &codec->ac97);
 	if (ret < 0)
-		goto bus_err;
-
-	for (i = 0; i < card->num_links; i++) {
-		if (card->dai_link[i].codec_dai->ac97_control) {
-			snd_ac97_dev_add_pdata(codec->ac97,
-				card->dai_link[i].cpu_dai->ac97_pdata);
-		}
-	}
+		return ret;
 
 	return 0;
-
-bus_err:
-	snd_soc_free_pcms(socdev);
-
-err:
-	kfree(socdev->card->codec);
-	socdev->card->codec = NULL;
-	return ret;
 }
 
-static int ac97_soc_remove(struct platform_device *pdev)
+static int ac97_soc_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	if (!codec)
-		return 0;
-
-	snd_soc_free_pcms(socdev);
-	kfree(socdev->card->codec);
-
 	return 0;
 }
 
 #ifdef CONFIG_PM
-static int ac97_soc_suspend(struct platform_device *pdev, pm_message_t msg)
+static int ac97_soc_suspend(struct snd_soc_codec *codec, pm_message_t msg)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_ac97_suspend(socdev->card->codec->ac97);
+	snd_ac97_suspend(codec->ac97);
 
 	return 0;
 }
 
-static int ac97_soc_resume(struct platform_device *pdev)
+static int ac97_soc_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_ac97_resume(socdev->card->codec->ac97);
+	snd_ac97_resume(codec->ac97);
 
 	return 0;
 }
@@ -175,13 +126,48 @@ static int ac97_soc_resume(struct platform_device *pdev)
 #define ac97_soc_resume NULL
 #endif
 
-struct snd_soc_codec_device soc_codec_dev_ac97 = {
+static struct snd_soc_codec_driver soc_codec_dev_ac97 = {
+	.write = ac97_write,
+	.read = ac97_read,
 	.probe = 	ac97_soc_probe,
 	.remove = 	ac97_soc_remove,
 	.suspend =	ac97_soc_suspend,
 	.resume =	ac97_soc_resume,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ac97);
+
+static __devinit int ac97_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_ac97, &ac97_dai, 1);
+}
+
+static int __devexit ac97_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_codec(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver ac97_codec_driver = {
+	.driver = {
+			.name = "ac97-codec",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = ac97_probe,
+	.remove = __devexit_p(ac97_remove),
+};
+
+static int __init ac97_init(void)
+{
+	return platform_driver_register(&ac97_codec_driver);
+}
+module_init(ac97_init);
+
+static void __exit ac97_exit(void)
+{
+	platform_driver_unregister(&ac97_codec_driver);
+}
+module_exit(ac97_exit);
 
 MODULE_DESCRIPTION("Soc Generic AC97 driver");
 MODULE_AUTHOR("Liam Girdwood");

+ 0 - 19
sound/soc/codecs/ac97.h

@@ -1,19 +0,0 @@
-/*
- * linux/sound/codecs/ac97.h -- ALSA SoC Layer
- *
- * Author:		Liam Girdwood
- * Created:		Dec 1st 2005
- * Copyright:	Wolfson Microelectronics. PLC.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- */
-
-#ifndef __LINUX_SND_SOC_AC97_H
-#define __LINUX_SND_SOC_AC97_H
-
-extern struct snd_soc_codec_device soc_codec_dev_ac97;
-extern struct snd_soc_dai ac97_dai;
-
-#endif

+ 55 - 136
sound/soc/codecs/ad1836.c

@@ -33,15 +33,10 @@
 
 /* codec private data */
 struct ad1836_priv {
-	struct snd_soc_codec codec;
-	u16 reg_cache[AD1836_NUM_REGS];
+	enum snd_soc_control_type control_type;
+	void *control_data;
 };
 
-static struct snd_soc_codec *ad1836_codec;
-struct snd_soc_codec_device soc_codec_dev_ad1836;
-static int ad1836_register(struct ad1836_priv *ad1836);
-static void ad1836_unregister(struct ad1836_priv *ad1836);
-
 /*
  * AD1836 volume/mute/de-emphasis etc. controls
  */
@@ -146,8 +141,7 @@ static int ad1836_hw_params(struct snd_pcm_substream *substream,
 	int word_len = 0;
 
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 
 	/* bit size */
 	switch (params_format(params)) {
@@ -173,12 +167,9 @@ static int ad1836_hw_params(struct snd_pcm_substream *substream,
 }
 
 #ifdef CONFIG_PM
-static int ad1836_soc_suspend(struct platform_device *pdev,
+static int ad1836_soc_suspend(struct snd_soc_codec *codec,
 		pm_message_t state)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	/* reset clock control mode */
 	u16 adc_ctrl2 = snd_soc_read(codec, AD1836_ADC_CTRL2);
 	adc_ctrl2 &= ~AD1836_ADC_SERFMT_MASK;
@@ -186,11 +177,8 @@ static int ad1836_soc_suspend(struct platform_device *pdev,
 	return snd_soc_write(codec, AD1836_ADC_CTRL2, adc_ctrl2);
 }
 
-static int ad1836_soc_resume(struct platform_device *pdev)
+static int ad1836_soc_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	/* restore clock control mode */
 	u16 adc_ctrl2 = snd_soc_read(codec, AD1836_ADC_CTRL2);
 	adc_ctrl2 |= AD1836_ADC_AUX;
@@ -202,49 +190,14 @@ static int ad1836_soc_resume(struct platform_device *pdev)
 #define ad1836_soc_resume  NULL
 #endif
 
-static int __devinit ad1836_spi_probe(struct spi_device *spi)
-{
-	struct snd_soc_codec *codec;
-	struct ad1836_priv *ad1836;
-
-	ad1836 = kzalloc(sizeof(struct ad1836_priv), GFP_KERNEL);
-	if (ad1836 == NULL)
-		return -ENOMEM;
-
-	codec = &ad1836->codec;
-	codec->control_data = spi;
-	codec->dev = &spi->dev;
-
-	dev_set_drvdata(&spi->dev, ad1836);
-
-	return ad1836_register(ad1836);
-}
-
-static int __devexit ad1836_spi_remove(struct spi_device *spi)
-{
-	struct ad1836_priv *ad1836 = dev_get_drvdata(&spi->dev);
-
-	ad1836_unregister(ad1836);
-	return 0;
-}
-
-static struct spi_driver ad1836_spi_driver = {
-	.driver = {
-		.name	= "ad1836",
-		.owner	= THIS_MODULE,
-	},
-	.probe		= ad1836_spi_probe,
-	.remove		= __devexit_p(ad1836_spi_remove),
-};
-
 static struct snd_soc_dai_ops ad1836_dai_ops = {
 	.hw_params = ad1836_hw_params,
 	.set_fmt = ad1836_set_dai_fmt,
 };
 
 /* codec DAI instance */
-struct snd_soc_dai ad1836_dai = {
-	.name = "AD1836",
+static struct snd_soc_dai_driver ad1836_dai = {
+	.name = "ad1836-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 2,
@@ -263,35 +216,13 @@ struct snd_soc_dai ad1836_dai = {
 	},
 	.ops = &ad1836_dai_ops,
 };
-EXPORT_SYMBOL_GPL(ad1836_dai);
 
-static int ad1836_register(struct ad1836_priv *ad1836)
+static int ad1836_probe(struct snd_soc_codec *codec)
 {
-	int ret;
-	struct snd_soc_codec *codec = &ad1836->codec;
-
-	if (ad1836_codec) {
-		dev_err(codec->dev, "Another ad1836 is registered\n");
-		kfree(ad1836);
-		return -EINVAL;
-	}
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-	snd_soc_codec_set_drvdata(codec, ad1836);
-	codec->reg_cache = ad1836->reg_cache;
-	codec->reg_cache_size = AD1836_NUM_REGS;
-	codec->name = "AD1836";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ad1836_dai;
-	codec->num_dai = 1;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	ad1836_dai.dev = codec->dev;
-	ad1836_codec = codec;
+	struct ad1836_priv *ad1836 = snd_soc_codec_get_drvdata(codec);
+	int ret = 0;
 
+	codec->control_data = ad1836->control_data;
 	ret = snd_soc_codec_set_cache_io(codec, 4, 12, SND_SOC_SPI);
 	if (ret < 0) {
 		dev_err(codec->dev, "failed to set cache I/O: %d\n",
@@ -319,81 +250,69 @@ static int ad1836_register(struct ad1836_priv *ad1836)
 	snd_soc_write(codec, AD1836_DAC_L3_VOL, 0x3FF);
 	snd_soc_write(codec, AD1836_DAC_R3_VOL, 0x3FF);
 
-	ret = snd_soc_register_codec(codec);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		kfree(ad1836);
-		return ret;
-	}
-
-	ret = snd_soc_register_dai(&ad1836_dai);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		snd_soc_unregister_codec(codec);
-		kfree(ad1836);
-		return ret;
-	}
-
-	return 0;
-}
-
-static void ad1836_unregister(struct ad1836_priv *ad1836)
-{
-	snd_soc_unregister_dai(&ad1836_dai);
-	snd_soc_unregister_codec(&ad1836->codec);
-	kfree(ad1836);
-	ad1836_codec = NULL;
-}
-
-static int ad1836_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
-
-	if (ad1836_codec == NULL) {
-		dev_err(&pdev->dev, "Codec device not registered\n");
-		return -ENODEV;
-	}
-
-	socdev->card->codec = ad1836_codec;
-	codec = ad1836_codec;
-
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to create pcms: %d\n", ret);
-		goto pcm_err;
-	}
-
 	snd_soc_add_controls(codec, ad1836_snd_controls,
 			     ARRAY_SIZE(ad1836_snd_controls));
 	snd_soc_dapm_new_controls(codec, ad1836_dapm_widgets,
 				  ARRAY_SIZE(ad1836_dapm_widgets));
 	snd_soc_dapm_add_routes(codec, audio_paths, ARRAY_SIZE(audio_paths));
 
-pcm_err:
 	return ret;
 }
 
 /* power down chip */
-static int ad1836_remove(struct platform_device *pdev)
+static int ad1836_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
+	/* reset clock control mode */
+	u16 adc_ctrl2 = snd_soc_read(codec, AD1836_ADC_CTRL2);
+	adc_ctrl2 &= ~AD1836_ADC_SERFMT_MASK;
 
-	return 0;
+	return snd_soc_write(codec, AD1836_ADC_CTRL2, adc_ctrl2);
 }
 
-struct snd_soc_codec_device soc_codec_dev_ad1836 = {
+static struct snd_soc_codec_driver soc_codec_dev_ad1836 = {
 	.probe = 	ad1836_probe,
 	.remove = 	ad1836_remove,
 	.suspend =      ad1836_soc_suspend,
 	.resume =       ad1836_soc_resume,
+	.reg_cache_size = AD1836_NUM_REGS,
+	.reg_word_size = sizeof(u16),
+};
+
+static int __devinit ad1836_spi_probe(struct spi_device *spi)
+{
+	struct ad1836_priv *ad1836;
+	int ret;
+
+	ad1836 = kzalloc(sizeof(struct ad1836_priv), GFP_KERNEL);
+	if (ad1836 == NULL)
+		return -ENOMEM;
+
+	spi_set_drvdata(spi, ad1836);
+	ad1836->control_data = spi;
+	ad1836->control_type = SND_SOC_SPI;
+
+	ret = snd_soc_register_codec(&spi->dev,
+			&soc_codec_dev_ad1836, &ad1836_dai, 1);
+	if (ret < 0)
+		kfree(ad1836);
+	return ret;
+}
+
+static int __devexit ad1836_spi_remove(struct spi_device *spi)
+{
+	snd_soc_unregister_codec(&spi->dev);
+	kfree(spi_get_drvdata(spi));
+	return 0;
+}
+
+static struct spi_driver ad1836_spi_driver = {
+	.driver = {
+		.name	= "ad1836-codec",
+		.owner	= THIS_MODULE,
+	},
+	.probe		= ad1836_spi_probe,
+	.remove		= __devexit_p(ad1836_spi_remove),
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ad1836);
 
 static int __init ad1836_init(void)
 {

+ 0 - 2
sound/soc/codecs/ad1836.h

@@ -60,6 +60,4 @@
 
 #define AD1836_NUM_REGS                16
 
-extern struct snd_soc_dai ad1836_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ad1836;
 #endif

+ 77 - 140
sound/soc/codecs/ad193x.c

@@ -24,9 +24,10 @@
 
 /* codec private data */
 struct ad193x_priv {
-	unsigned int sysclk;
-	struct snd_soc_codec codec;
 	u8 reg_cache[AD193X_NUM_REGS];
+	enum snd_soc_control_type bus_type;
+	void *control_data;
+	int sysclk;
 };
 
 /* ad193x register cache & default register settings */
@@ -34,9 +35,6 @@ static const u8 ad193x_reg[AD193X_NUM_REGS] = {
 	0, 0, 0, 0, 0, 0, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0, 0, 0,
 };
 
-static struct snd_soc_codec *ad193x_codec;
-struct snd_soc_codec_device soc_codec_dev_ad193x;
-
 /*
  * AD193X volume/mute/de-emphasis etc. controls
  */
@@ -275,8 +273,7 @@ static int ad193x_hw_params(struct snd_pcm_substream *substream,
 	int word_len = 0, reg = 0, master_rate = 0;
 
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	struct ad193x_priv *ad193x = snd_soc_codec_get_drvdata(codec);
 
 	/* bit size */
@@ -323,100 +320,6 @@ static int ad193x_hw_params(struct snd_pcm_substream *substream,
 	return 0;
 }
 
-static int ad193x_bus_probe(struct device *dev, void *ctrl_data, int bus_type)
-{
-	struct snd_soc_codec *codec;
-	struct ad193x_priv *ad193x;
-	int ret;
-
-	if (ad193x_codec) {
-		dev_err(dev, "Another ad193x is registered\n");
-		return -EINVAL;
-	}
-
-	ad193x = kzalloc(sizeof(struct ad193x_priv), GFP_KERNEL);
-	if (ad193x == NULL)
-		return -ENOMEM;
-
-	dev_set_drvdata(dev, ad193x);
-
-	codec = &ad193x->codec;
-	mutex_init(&codec->mutex);
-	codec->control_data = ctrl_data;
-	codec->dev = dev;
-	snd_soc_codec_set_drvdata(codec, ad193x);
-	codec->reg_cache = ad193x->reg_cache;
-	codec->reg_cache_size = AD193X_NUM_REGS;
-	codec->name = "AD193X";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ad193x_dai;
-	codec->num_dai = 1;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	ad193x_dai.dev = codec->dev;
-	ad193x_codec = codec;
-
-	memcpy(codec->reg_cache, ad193x_reg, AD193X_NUM_REGS);
-
-	if (bus_type == SND_SOC_I2C)
-		ret = snd_soc_codec_set_cache_io(codec, 8, 8, bus_type);
-	else
-		ret = snd_soc_codec_set_cache_io(codec, 16, 8, bus_type);
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to set cache I/O: %d\n",
-				ret);
-		kfree(ad193x);
-		return ret;
-	}
-
-	/* default setting for ad193x */
-
-	/* unmute dac channels */
-	snd_soc_write(codec, AD193X_DAC_CHNL_MUTE, 0x0);
-	/* de-emphasis: 48kHz, powedown dac */
-	snd_soc_write(codec, AD193X_DAC_CTRL2, 0x1A);
-	/* powerdown dac, dac in tdm mode */
-	snd_soc_write(codec, AD193X_DAC_CTRL0, 0x41);
-	/* high-pass filter enable */
-	snd_soc_write(codec, AD193X_ADC_CTRL0, 0x3);
-	/* sata delay=1, adc aux mode */
-	snd_soc_write(codec, AD193X_ADC_CTRL1, 0x43);
-	/* pll input: mclki/xi */
-	snd_soc_write(codec, AD193X_PLL_CLK_CTRL0, 0x99); /* mclk=24.576Mhz: 0x9D; mclk=12.288Mhz: 0x99 */
-	snd_soc_write(codec, AD193X_PLL_CLK_CTRL1, 0x04);
-	ad193x->sysclk = 12288000;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		kfree(ad193x);
-		return ret;
-	}
-
-	ret = snd_soc_register_dai(&ad193x_dai);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		snd_soc_unregister_codec(codec);
-		kfree(ad193x);
-		return ret;
-	}
-
-	return 0;
-}
-
-static int ad193x_bus_remove(struct device *dev)
-{
-	struct ad193x_priv *ad193x = dev_get_drvdata(dev);
-
-	snd_soc_unregister_dai(&ad193x_dai);
-	snd_soc_unregister_codec(&ad193x->codec);
-	kfree(ad193x);
-	ad193x_codec = NULL;
-
-	return 0;
-}
-
 static struct snd_soc_dai_ops ad193x_dai_ops = {
 	.hw_params = ad193x_hw_params,
 	.digital_mute = ad193x_mute,
@@ -426,8 +329,8 @@ static struct snd_soc_dai_ops ad193x_dai_ops = {
 };
 
 /* codec DAI instance */
-struct snd_soc_dai ad193x_dai = {
-	.name = "AD193X",
+static struct snd_soc_dai_driver ad193x_dai = {
+	.name = "ad193x-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 2,
@@ -446,28 +349,39 @@ struct snd_soc_dai ad193x_dai = {
 	},
 	.ops = &ad193x_dai_ops,
 };
-EXPORT_SYMBOL_GPL(ad193x_dai);
 
-static int ad193x_probe(struct platform_device *pdev)
+static int ad193x_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
+	struct ad193x_priv *ad193x = snd_soc_codec_get_drvdata(codec);
+	int ret;
 
-	if (ad193x_codec == NULL) {
-		dev_err(&pdev->dev, "Codec device not registered\n");
-		return -ENODEV;
+	codec->control_data = ad193x->control_data;
+	if (ad193x->bus_type == SND_SOC_I2C)
+		ret = snd_soc_codec_set_cache_io(codec, 8, 8, ad193x->bus_type);
+	else
+		ret = snd_soc_codec_set_cache_io(codec, 16, 8, ad193x->bus_type);
+	if (ret < 0) {
+		dev_err(codec->dev, "failed to set cache I/O: %d\n",
+				ret);
+		kfree(ad193x);
+		return ret;
 	}
 
-	socdev->card->codec = ad193x_codec;
-	codec = ad193x_codec;
+	/* default setting for ad193x */
 
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to create pcms: %d\n", ret);
-		goto pcm_err;
-	}
+	/* unmute dac channels */
+	snd_soc_write(codec, AD193X_DAC_CHNL_MUTE, 0x0);
+	/* de-emphasis: 48kHz, powedown dac */
+	snd_soc_write(codec, AD193X_DAC_CTRL2, 0x1A);
+	/* powerdown dac, dac in tdm mode */
+	snd_soc_write(codec, AD193X_DAC_CTRL0, 0x41);
+	/* high-pass filter enable */
+	snd_soc_write(codec, AD193X_ADC_CTRL0, 0x3);
+	/* sata delay=1, adc aux mode */
+	snd_soc_write(codec, AD193X_ADC_CTRL1, 0x43);
+	/* pll input: mclki/xi */
+	snd_soc_write(codec, AD193X_PLL_CLK_CTRL0, 0x99); /* mclk=24.576Mhz: 0x9D; mclk=12.288Mhz: 0x99 */
+	snd_soc_write(codec, AD193X_PLL_CLK_CTRL1, 0x04);
 
 	snd_soc_add_controls(codec, ad193x_snd_controls,
 			     ARRAY_SIZE(ad193x_snd_controls));
@@ -475,41 +389,47 @@ static int ad193x_probe(struct platform_device *pdev)
 				  ARRAY_SIZE(ad193x_dapm_widgets));
 	snd_soc_dapm_add_routes(codec, audio_paths, ARRAY_SIZE(audio_paths));
 
-pcm_err:
 	return ret;
 }
 
-/* power down chip */
-static int ad193x_remove(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
-
-	return 0;
-}
-
-struct snd_soc_codec_device soc_codec_dev_ad193x = {
+static struct snd_soc_codec_driver soc_codec_dev_ad193x = {
 	.probe = 	ad193x_probe,
-	.remove = 	ad193x_remove,
+	.reg_cache_default = ad193x_reg,
+	.reg_cache_size = AD193X_NUM_REGS,
+	.reg_word_size = sizeof(u16),
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ad193x);
 
 #if defined(CONFIG_SPI_MASTER)
 static int __devinit ad193x_spi_probe(struct spi_device *spi)
 {
-	return ad193x_bus_probe(&spi->dev, spi, SND_SOC_SPI);
+	struct ad193x_priv *ad193x;
+	int ret;
+
+	ad193x = kzalloc(sizeof(struct ad193x_priv), GFP_KERNEL);
+	if (ad193x == NULL)
+		return -ENOMEM;
+
+	spi_set_drvdata(spi, ad193x);
+	ad193x->control_data = spi;
+	ad193x->bus_type = SND_SOC_SPI;
+
+	ret = snd_soc_register_codec(&spi->dev,
+			&soc_codec_dev_ad193x, &ad193x_dai, 1);
+	if (ret < 0)
+		kfree(ad193x);
+	return ret;
 }
 
 static int __devexit ad193x_spi_remove(struct spi_device *spi)
 {
-	return ad193x_bus_remove(&spi->dev);
+	snd_soc_unregister_codec(&spi->dev);
+	kfree(spi_get_drvdata(spi));
+	return 0;
 }
 
 static struct spi_driver ad193x_spi_driver = {
 	.driver = {
-		.name	= "ad193x",
+		.name	= "ad193x-codec",
 		.owner	= THIS_MODULE,
 	},
 	.probe		= ad193x_spi_probe,
@@ -528,17 +448,34 @@ MODULE_DEVICE_TABLE(i2c, ad193x_id);
 static int __devinit ad193x_i2c_probe(struct i2c_client *client,
 		const struct i2c_device_id *id)
 {
-	return ad193x_bus_probe(&client->dev, client, SND_SOC_I2C);
+	struct ad193x_priv *ad193x;
+	int ret;
+
+	ad193x = kzalloc(sizeof(struct ad193x_priv), GFP_KERNEL);
+	if (ad193x == NULL)
+		return -ENOMEM;
+
+	i2c_set_clientdata(client, ad193x);
+	ad193x->control_data = client;
+	ad193x->bus_type = SND_SOC_I2C;
+
+	ret =  snd_soc_register_codec(&client->dev,
+			&soc_codec_dev_ad193x, &ad193x_dai, 1);
+	if (ret < 0)
+		kfree(ad193x);
+	return ret;
 }
 
 static int __devexit ad193x_i2c_remove(struct i2c_client *client)
 {
-	return ad193x_bus_remove(&client->dev);
+	snd_soc_unregister_codec(&client->dev);
+	kfree(i2c_get_clientdata(client));
+	return 0;
 }
 
 static struct i2c_driver ad193x_i2c_driver = {
 	.driver = {
-		.name = "ad193x",
+		.name = "ad193x-codec",
 	},
 	.probe    = ad193x_i2c_probe,
 	.remove   = __devexit_p(ad193x_i2c_remove),

+ 0 - 3
sound/soc/codecs/ad193x.h

@@ -80,7 +80,4 @@
 
 #define AD193X_NUM_REGS          17
 
-extern struct snd_soc_dai ad193x_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ad193x;
-
 #endif

+ 46 - 61
sound/soc/codecs/ad1980.c

@@ -130,8 +130,8 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg,
 	return 0;
 }
 
-struct snd_soc_dai ad1980_dai = {
-	.name = "AC97",
+struct snd_soc_dai_driver ad1980_dai = {
+	.name = "ad1980-hifi",
 	.ac97_control = 1,
 	.playback = {
 		.stream_name = "Playback",
@@ -177,53 +177,20 @@ err:
 	return -EIO;
 }
 
-static int ad1980_soc_probe(struct platform_device *pdev)
+static int ad1980_soc_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
+	int ret;
 	u16 vendor_id2;
 	u16 ext_status;
 
 	printk(KERN_INFO "AD1980 SoC Audio Codec\n");
 
-	socdev->card->codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (socdev->card->codec == NULL)
-		return -ENOMEM;
-	codec = socdev->card->codec;
-	mutex_init(&codec->mutex);
-
-	codec->reg_cache =
-		kzalloc(sizeof(u16) * ARRAY_SIZE(ad1980_reg), GFP_KERNEL);
-	if (codec->reg_cache == NULL) {
-		ret = -ENOMEM;
-		goto cache_err;
-	}
-	memcpy(codec->reg_cache, ad1980_reg, sizeof(u16) * \
-			ARRAY_SIZE(ad1980_reg));
-	codec->reg_cache_size = sizeof(u16) * ARRAY_SIZE(ad1980_reg);
-	codec->reg_cache_step = 2;
-	codec->name = "AD1980";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ad1980_dai;
-	codec->num_dai = 1;
-	codec->write = ac97_write;
-	codec->read = ac97_read;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
 	ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0);
 	if (ret < 0) {
 		printk(KERN_ERR "ad1980: failed to register AC97 codec\n");
-		goto codec_err;
+		return ret;
 	}
 
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0)
-		goto pcm_err;
-
-
 	ret = ad1980_reset(codec, 0);
 	if (ret < 0) {
 		printk(KERN_ERR "Failed to reset AD1980: AC97 link error\n");
@@ -262,41 +229,59 @@ static int ad1980_soc_probe(struct platform_device *pdev)
 	return 0;
 
 reset_err:
-	snd_soc_free_pcms(socdev);
-
-pcm_err:
 	snd_soc_free_ac97_codec(codec);
-
-codec_err:
-	kfree(codec->reg_cache);
-
-cache_err:
-	kfree(socdev->card->codec);
-	socdev->card->codec = NULL;
 	return ret;
 }
 
-static int ad1980_soc_remove(struct platform_device *pdev)
+static int ad1980_soc_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	if (codec == NULL)
-		return 0;
-
-	snd_soc_dapm_free(socdev);
-	snd_soc_free_pcms(socdev);
 	snd_soc_free_ac97_codec(codec);
-	kfree(codec->reg_cache);
-	kfree(codec);
 	return 0;
 }
 
-struct snd_soc_codec_device soc_codec_dev_ad1980 = {
+static struct snd_soc_codec_driver soc_codec_dev_ad1980 = {
 	.probe = 	ad1980_soc_probe,
 	.remove = 	ad1980_soc_remove,
+	.reg_cache_size = ARRAY_SIZE(ad1980_reg),
+	.reg_word_size = sizeof(u16),
+	.reg_cache_step = 2,
+	.write = ac97_write,
+	.read = ac97_read,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ad1980);
+
+static __devinit int ad1980_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_ad1980, &ad1980_dai, 1);
+}
+
+static int __devexit ad1980_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_codec(&pdev->dev);
+	return 0;
+}
+
+static struct platform_driver ad1980_codec_driver = {
+	.driver = {
+			.name = "ad1980-codec",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = ad1980_probe,
+	.remove = __devexit_p(ad1980_remove),
+};
+
+static int __init ad1980_init(void)
+{
+	return platform_driver_register(&ad1980_codec_driver);
+}
+module_init(ad1980_init);
+
+static void __exit ad1980_exit(void)
+{
+	platform_driver_unregister(&ad1980_codec_driver);
+}
+module_exit(ad1980_exit);
 
 MODULE_DESCRIPTION("ASoC ad1980 driver");
 MODULE_AUTHOR("Roy Huang, Cliff Cai");

+ 0 - 3
sound/soc/codecs/ad1980.h

@@ -17,7 +17,4 @@
 #define PR5		0x2000
 #define PR6		0x4000
 
-extern struct snd_soc_dai ad1980_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ad1980;
-
 #endif

+ 19 - 47
sound/soc/codecs/ad73311.c

@@ -23,8 +23,8 @@
 
 #include "ad73311.h"
 
-struct snd_soc_dai ad73311_dai = {
-	.name = "AD73311",
+static struct snd_soc_dai_driver ad73311_dai = {
+	.name = "ad73311-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -38,68 +38,40 @@ struct snd_soc_dai ad73311_dai = {
 		.rates = SNDRV_PCM_RATE_8000,
 		.formats = SNDRV_PCM_FMTBIT_S16_LE, },
 };
-EXPORT_SYMBOL_GPL(ad73311_dai);
 
-static int ad73311_soc_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
-
-	codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (codec == NULL)
-		return -ENOMEM;
-	mutex_init(&codec->mutex);
-	codec->name = "AD73311";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ad73311_dai;
-	codec->num_dai = 1;
-	socdev->card->codec = codec;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		printk(KERN_ERR "ad73311: failed to create pcms\n");
-		goto pcm_err;
-	}
-
-	return ret;
+static struct snd_soc_codec_driver soc_codec_dev_ad73311;
 
-pcm_err:
-	kfree(socdev->card->codec);
-	socdev->card->codec = NULL;
-	return ret;
+static int ad73311_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_ad73311, &ad73311_dai, 1);
 }
 
-static int ad73311_soc_remove(struct platform_device *pdev)
+static int ad73311_remove(struct platform_device *pdev)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	if (codec == NULL)
-		return 0;
-	snd_soc_free_pcms(socdev);
-	kfree(codec);
+	snd_soc_unregister_codec(&pdev->dev);
 	return 0;
 }
 
-struct snd_soc_codec_device soc_codec_dev_ad73311 = {
-	.probe = 	ad73311_soc_probe,
-	.remove = 	ad73311_soc_remove,
+static struct platform_driver ad73311_codec_driver = {
+	.driver = {
+			.name = "ad73311-codec",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = ad73311_probe,
+	.remove = __devexit_p(ad73311_remove),
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ad73311);
 
 static int __init ad73311_init(void)
 {
-	return snd_soc_register_dai(&ad73311_dai);
+	return platform_driver_register(&ad73311_codec_driver);
 }
 module_init(ad73311_init);
 
 static void __exit ad73311_exit(void)
 {
-	snd_soc_unregister_dai(&ad73311_dai);
+	platform_driver_unregister(&ad73311_codec_driver);
 }
 module_exit(ad73311_exit);
 

+ 0 - 2
sound/soc/codecs/ad73311.h

@@ -85,6 +85,4 @@
 #define REGF_INV		(1 << 6)
 #define REGF_ALB		(1 << 7)
 
-extern struct snd_soc_dai ad73311_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ad73311;
 #endif

+ 11 - 61
sound/soc/codecs/ads117x.c

@@ -19,16 +19,12 @@
 #include <sound/initval.h>
 #include <sound/soc.h>
 
-#include "ads117x.h"
-
 #define ADS117X_RATES (SNDRV_PCM_RATE_8000_48000)
-
 #define ADS117X_FORMATS (SNDRV_PCM_FMTBIT_S16_LE)
 
-struct snd_soc_dai ads117x_dai = {
+static struct snd_soc_dai_driver ads117x_dai = {
 /* ADC */
-	.name = "ADS117X ADC",
-	.id = 1,
+	.name = "ads117x-hifi",
 	.capture = {
 		.stream_name = "Capture",
 		.channels_min = 1,
@@ -36,75 +32,29 @@ struct snd_soc_dai ads117x_dai = {
 		.rates = ADS117X_RATES,
 		.formats = ADS117X_FORMATS,},
 };
-EXPORT_SYMBOL_GPL(ads117x_dai);
-
-static int ads117x_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret;
-
-	codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (codec == NULL)
-		return -ENOMEM;
 
-	socdev->card->codec = codec;
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-	codec->name = "ADS117X";
-	codec->owner = THIS_MODULE;
-	codec->dai = &ads117x_dai;
-	codec->num_dai = 1;
-
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		printk(KERN_ERR "ads117x: failed to create pcms\n");
-		kfree(codec);
-		return ret;
-	}
-
-	return 0;
-}
-
-static int ads117x_remove(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	snd_soc_free_pcms(socdev);
-	kfree(codec);
-
-	return 0;
-}
-
-struct snd_soc_codec_device soc_codec_dev_ads117x = {
-	.probe =	ads117x_probe,
-	.remove =	ads117x_remove,
-};
-EXPORT_SYMBOL_GPL(soc_codec_dev_ads117x);
+static struct snd_soc_codec_driver soc_codec_dev_ads117x;
 
-static __devinit int ads117x_platform_probe(struct platform_device *pdev)
+static __devinit int ads117x_probe(struct platform_device *pdev)
 {
-	ads117x_dai.dev = &pdev->dev;
-	return snd_soc_register_dai(&ads117x_dai);
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_ads117x, &ads117x_dai, 1);
 }
 
-static int __devexit ads117x_platform_remove(struct platform_device *pdev)
+static int __devexit ads117x_remove(struct platform_device *pdev)
 {
-	snd_soc_unregister_dai(&ads117x_dai);
+	snd_soc_unregister_codec(&pdev->dev);
 	return 0;
 }
 
 static struct platform_driver ads117x_codec_driver = {
 	.driver = {
-			.name = "ads117x",
+			.name = "ads117x-codec",
 			.owner = THIS_MODULE,
 	},
 
-	.probe = ads117x_platform_probe,
-	.remove = __devexit_p(ads117x_platform_remove),
+	.probe = ads117x_probe,
+	.remove = __devexit_p(ads117x_remove),
 };
 
 static int __init ads117x_init(void)

+ 2 - 2
sound/soc/codecs/ads117x.h

@@ -9,5 +9,5 @@
  *  Free Software Foundation;  either version 2 of the  License, or (at your
  *  option) any later version.
  */
-extern struct snd_soc_dai ads117x_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ads117x;
+extern struct snd_soc_dai_driver ads117x_dai;
+extern struct snd_soc_codec_driver soc_codec_dev_ads117x;

+ 53 - 96
sound/soc/codecs/ak4104.c

@@ -17,8 +17,6 @@
 #include <linux/spi/spi.h>
 #include <sound/asoundef.h>
 
-#include "ak4104.h"
-
 /* AK4104 registers addresses */
 #define AK4104_REG_CONTROL1		0x00
 #define AK4104_REG_RESERVED		0x01
@@ -45,11 +43,11 @@
 #define AK4104_TX_TXE			(1 << 0)
 #define AK4104_TX_V			(1 << 1)
 
-#define DRV_NAME "ak4104"
+#define DRV_NAME "ak4104-codec"
 
 struct ak4104_private {
-	struct snd_soc_codec codec;
-	u8 reg_cache[AK4104_NUM_REGS];
+	enum snd_soc_control_type control_type;
+	void *control_data;
 };
 
 static int ak4104_fill_cache(struct snd_soc_codec *codec)
@@ -58,7 +56,7 @@ static int ak4104_fill_cache(struct snd_soc_codec *codec)
 	u8 *reg_cache = codec->reg_cache;
 	struct spi_device *spi = codec->control_data;
 
-	for (i = 0; i < codec->reg_cache_size; i++) {
+	for (i = 0; i < codec->driver->reg_cache_size; i++) {
 		int ret = spi_w8r8(spi, i | AK4104_READ);
 		if (ret < 0) {
 			dev_err(&spi->dev, "SPI write failure\n");
@@ -76,7 +74,7 @@ static unsigned int ak4104_read_reg_cache(struct snd_soc_codec *codec,
 {
 	u8 *reg_cache = codec->reg_cache;
 
-	if (reg >= codec->reg_cache_size)
+	if (reg >= codec->driver->reg_cache_size)
 		return -EINVAL;
 
 	return reg_cache[reg];
@@ -88,7 +86,7 @@ static int ak4104_spi_write(struct snd_soc_codec *codec, unsigned int reg,
 	u8 *cache = codec->reg_cache;
 	struct spi_device *spi = codec->control_data;
 
-	if (reg >= codec->reg_cache_size)
+	if (reg >= codec->driver->reg_cache_size)
 		return -EINVAL;
 
 	/* only write to the hardware if value has changed */
@@ -145,8 +143,7 @@ static int ak4104_hw_params(struct snd_pcm_substream *substream,
 			    struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	int val = 0;
 
 	/* set the IEC958 bits: consumer mode, no copyright bit */
@@ -178,8 +175,8 @@ static struct snd_soc_dai_ops ak4101_dai_ops = {
 	.set_fmt = ak4104_set_dai_fmt,
 };
 
-struct snd_soc_dai ak4104_dai = {
-	.name = DRV_NAME,
+static struct snd_soc_dai_driver ak4104_dai = {
+	.name = "ak4104-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 2,
@@ -192,45 +189,17 @@ struct snd_soc_dai ak4104_dai = {
 	.ops = &ak4101_dai_ops,
 };
 
-static struct snd_soc_codec *ak4104_codec;
-
-static int ak4104_spi_probe(struct spi_device *spi)
+static int ak4104_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_codec *codec;
-	struct ak4104_private *ak4104;
+	struct ak4104_private *ak4104 = snd_soc_codec_get_drvdata(codec);
 	int ret, val;
 
-	spi->bits_per_word = 8;
-	spi->mode = SPI_MODE_0;
-	ret = spi_setup(spi);
-	if (ret < 0)
-		return ret;
-
-	ak4104 = kzalloc(sizeof(struct ak4104_private), GFP_KERNEL);
-	if (!ak4104) {
-		dev_err(&spi->dev, "could not allocate codec\n");
-		return -ENOMEM;
-	}
-
-	codec = &ak4104->codec;
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	codec->dev = &spi->dev;
-	codec->name = DRV_NAME;
-	codec->owner = THIS_MODULE;
-	codec->dai = &ak4104_dai;
-	codec->num_dai = 1;
-	snd_soc_codec_set_drvdata(codec, ak4104);
-	codec->control_data = spi;
-	codec->reg_cache = ak4104->reg_cache;
-	codec->reg_cache_size = AK4104_NUM_REGS;
+	codec->control_data = ak4104->control_data;
 
 	/* read all regs and fill the cache */
 	ret = ak4104_fill_cache(codec);
 	if (ret < 0) {
-		dev_err(&spi->dev, "failed to fill register cache\n");
+		dev_err(codec->dev, "failed to fill register cache\n");
 		return ret;
 	}
 
@@ -238,93 +207,81 @@ static int ak4104_spi_probe(struct spi_device *spi)
 	 * should contain 0x5b. Not a good way to verify the presence of
 	 * the device, but there is no hardware ID register. */
 	if (ak4104_read_reg_cache(codec, AK4104_REG_RESERVED) !=
-					 AK4104_RESERVED_VAL) {
-		ret = -ENODEV;
-		goto error_free_codec;
-	}
+					 AK4104_RESERVED_VAL)
+		return -ENODEV;
 
 	/* set power-up and non-reset bits */
 	val = ak4104_read_reg_cache(codec, AK4104_REG_CONTROL1);
 	val |= AK4104_CONTROL1_PW | AK4104_CONTROL1_RSTN;
 	ret = ak4104_spi_write(codec, AK4104_REG_CONTROL1, val);
 	if (ret < 0)
-		goto error_free_codec;
+		return ret;
 
 	/* enable transmitter */
 	val = ak4104_read_reg_cache(codec, AK4104_REG_TX);
 	val |= AK4104_TX_TXE;
 	ret = ak4104_spi_write(codec, AK4104_REG_TX, val);
 	if (ret < 0)
-		goto error_free_codec;
-
-	ak4104_codec = codec;
-	ret = snd_soc_register_dai(&ak4104_dai);
-	if (ret < 0) {
-		dev_err(&spi->dev, "failed to register DAI\n");
-		goto error_free_codec;
-	}
+		return ret;
 
-	spi_set_drvdata(spi, ak4104);
-	dev_info(&spi->dev, "SPI device initialized\n");
+	dev_info(codec->dev, "SPI device initialized\n");
 	return 0;
-
-error_free_codec:
-	kfree(ak4104);
-	ak4104_dai.dev = NULL;
-	return ret;
 }
 
-static int __devexit ak4104_spi_remove(struct spi_device *spi)
+static int ak4104_remove(struct snd_soc_codec *codec)
 {
-	int ret, val;
-	struct ak4104_private *ak4104 = spi_get_drvdata(spi);
+	int val, ret;
 
-	val = ak4104_read_reg_cache(&ak4104->codec, AK4104_REG_CONTROL1);
+	val = ak4104_read_reg_cache(codec, AK4104_REG_CONTROL1);
 	if (val < 0)
 		return val;
 
 	/* clear power-up and non-reset bits */
 	val &= ~(AK4104_CONTROL1_PW | AK4104_CONTROL1_RSTN);
-	ret = ak4104_spi_write(&ak4104->codec, AK4104_REG_CONTROL1, val);
-	if (ret < 0)
-		return ret;
+	ret = ak4104_spi_write(codec, AK4104_REG_CONTROL1, val);
 
-	ak4104_codec = NULL;
-	kfree(ak4104);
-	return 0;
+	return ret;
 }
 
-static int ak4104_probe(struct platform_device *pdev)
+static struct snd_soc_codec_driver soc_codec_device_ak4104 = {
+	.probe =	ak4104_probe,
+	.remove =	ak4104_remove,
+	.reg_cache_size = AK4104_NUM_REGS,
+	.reg_word_size = sizeof(u16),
+};
+
+static int ak4104_spi_probe(struct spi_device *spi)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = ak4104_codec;
+	struct ak4104_private *ak4104;
 	int ret;
 
-	/* Connect the codec to the socdev.  snd_soc_new_pcms() needs this. */
-	socdev->card->codec = codec;
-
-	/* Register PCMs */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to create pcms\n");
+	spi->bits_per_word = 8;
+	spi->mode = SPI_MODE_0;
+	ret = spi_setup(spi);
+	if (ret < 0)
 		return ret;
-	}
 
-	return 0;
+	ak4104 = kzalloc(sizeof(struct ak4104_private), GFP_KERNEL);
+	if (ak4104 == NULL)
+		return -ENOMEM;
+
+	ak4104->control_data = spi;
+	ak4104->control_type = SND_SOC_SPI;
+	spi_set_drvdata(spi, ak4104);
+
+	ret = snd_soc_register_codec(&spi->dev,
+			&soc_codec_device_ak4104, &ak4104_dai, 1);
+	if (ret < 0)
+		kfree(ak4104);
+	return ret;
 }
 
-static int ak4104_remove(struct platform_device *pdev)
+static int __devexit ak4104_spi_remove(struct spi_device *spi)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	snd_soc_free_pcms(socdev);
+	snd_soc_unregister_codec(&spi->dev);
+	kfree(spi_get_drvdata(spi));
 	return 0;
-};
-
-struct snd_soc_codec_device soc_codec_device_ak4104 = {
-	.probe = 	ak4104_probe,
-	.remove = 	ak4104_remove
-};
-EXPORT_SYMBOL_GPL(soc_codec_device_ak4104);
+}
 
 static struct spi_driver ak4104_spi_driver = {
 	.driver  = {

+ 0 - 7
sound/soc/codecs/ak4104.h

@@ -1,7 +0,0 @@
-#ifndef _AK4104_H
-#define _AK4104_H
-
-extern struct snd_soc_dai ak4104_dai;
-extern struct snd_soc_codec_device soc_codec_device_ak4104;
-
-#endif

+ 61 - 175
sound/soc/codecs/ak4535.c

@@ -31,11 +31,11 @@
 
 #define AK4535_VERSION "0.3"
 
-struct snd_soc_codec_device soc_codec_dev_ak4535;
-
 /* codec private data */
 struct ak4535_priv {
 	unsigned int sysclk;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 };
 
 /*
@@ -313,8 +313,7 @@ static int ak4535_hw_params(struct snd_pcm_substream *substream,
 			    struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	struct ak4535_priv *ak4535 = snd_soc_codec_get_drvdata(codec);
 	u8 mode2 = ak4535_read_reg_cache(codec, AK4535_MODE2) & ~(0x3 << 5);
 	int rate = params_rate(params), fs = 256;
@@ -378,14 +377,16 @@ static int ak4535_mute(struct snd_soc_dai *dai, int mute)
 static int ak4535_set_bias_level(struct snd_soc_codec *codec,
 	enum snd_soc_bias_level level)
 {
-	u16 i;
+	u16 i, mute_reg;
 
 	switch (level) {
 	case SND_SOC_BIAS_ON:
-		ak4535_mute(codec->dai, 0);
+		mute_reg = ak4535_read_reg_cache(codec, AK4535_DAC) & 0xffdf;
+		ak4535_write(codec, AK4535_DAC, mute_reg);
 		break;
 	case SND_SOC_BIAS_PREPARE:
-		ak4535_mute(codec->dai, 1);
+		mute_reg = ak4535_read_reg_cache(codec, AK4535_DAC) & 0xffdf;
+		ak4535_write(codec, AK4535_DAC, mute_reg | 0x20);
 		break;
 	case SND_SOC_BIAS_STANDBY:
 		i = ak4535_read_reg_cache(codec, AK4535_PM1);
@@ -413,8 +414,8 @@ static struct snd_soc_dai_ops ak4535_dai_ops = {
 	.set_sysclk	= ak4535_set_dai_sysclk,
 };
 
-struct snd_soc_dai ak4535_dai = {
-	.name = "AK4535",
+static struct snd_soc_dai_driver ak4535_dai = {
+	.name = "ak4535-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -429,54 +430,27 @@ struct snd_soc_dai ak4535_dai = {
 		.formats = SNDRV_PCM_FMTBIT_S16_LE,},
 	.ops = &ak4535_dai_ops,
 };
-EXPORT_SYMBOL_GPL(ak4535_dai);
 
-static int ak4535_suspend(struct platform_device *pdev, pm_message_t state)
+static int ak4535_suspend(struct snd_soc_codec *codec, pm_message_t state)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	ak4535_set_bias_level(codec, SND_SOC_BIAS_OFF);
 	return 0;
 }
 
-static int ak4535_resume(struct platform_device *pdev)
+static int ak4535_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
 	ak4535_sync(codec);
 	ak4535_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
 	return 0;
 }
 
-/*
- * initialise the AK4535 driver
- * register the mixer and dsp interfaces with the kernel
- */
-static int ak4535_init(struct snd_soc_device *socdev)
+static int ak4535_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_codec *codec = socdev->card->codec;
-	int ret = 0;
+	struct ak4535_priv *ak4535 = snd_soc_codec_get_drvdata(codec);
 
-	codec->name = "AK4535";
-	codec->owner = THIS_MODULE;
-	codec->read = ak4535_read_reg_cache;
-	codec->write = ak4535_write;
-	codec->set_bias_level = ak4535_set_bias_level;
-	codec->dai = &ak4535_dai;
-	codec->num_dai = 1;
-	codec->reg_cache_size = ARRAY_SIZE(ak4535_reg);
-	codec->reg_cache = kmemdup(ak4535_reg, sizeof(ak4535_reg), GFP_KERNEL);
-
-	if (codec->reg_cache == NULL)
-		return -ENOMEM;
+	printk(KERN_INFO "AK4535 Audio Codec %s", AK4535_VERSION);
 
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		printk(KERN_ERR "ak4535: failed to create pcms\n");
-		goto pcm_err;
-	}
+	codec->control_data = ak4535->control_data;
 
 	/* power on device */
 	ak4535_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
@@ -485,39 +459,55 @@ static int ak4535_init(struct snd_soc_device *socdev)
 				ARRAY_SIZE(ak4535_snd_controls));
 	ak4535_add_widgets(codec);
 
-	return ret;
-
-pcm_err:
-	kfree(codec->reg_cache);
+	return 0;
+}
 
-	return ret;
+/* power down chip */
+static int ak4535_remove(struct snd_soc_codec *codec)
+{
+	ak4535_set_bias_level(codec, SND_SOC_BIAS_OFF);
+	return 0;
 }
 
-static struct snd_soc_device *ak4535_socdev;
+static struct snd_soc_codec_driver soc_codec_dev_ak4535 = {
+	.probe =	ak4535_probe,
+	.remove =	ak4535_remove,
+	.suspend =	ak4535_suspend,
+	.resume =	ak4535_resume,
+	.read = ak4535_read_reg_cache,
+	.write = ak4535_write,
+	.set_bias_level = ak4535_set_bias_level,
+	.reg_cache_size = ARRAY_SIZE(ak4535_reg),
+	.reg_word_size = sizeof(u8),
+	.reg_cache_default = ak4535_reg,
+};
 
 #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
-
-static int ak4535_i2c_probe(struct i2c_client *i2c,
-			    const struct i2c_device_id *id)
+static __devinit int ak4535_i2c_probe(struct i2c_client *i2c,
+				      const struct i2c_device_id *id)
 {
-	struct snd_soc_device *socdev = ak4535_socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct ak4535_priv *ak4535;
 	int ret;
 
-	i2c_set_clientdata(i2c, codec);
-	codec->control_data = i2c;
+	ak4535 = kzalloc(sizeof(struct ak4535_priv), GFP_KERNEL);
+	if (ak4535 == NULL)
+		return -ENOMEM;
 
-	ret = ak4535_init(socdev);
-	if (ret < 0)
-		printk(KERN_ERR "failed to initialise AK4535\n");
+	i2c_set_clientdata(i2c, ak4535);
+	ak4535->control_data = i2c;
+	ak4535->control_type = SND_SOC_I2C;
 
+	ret = snd_soc_register_codec(&i2c->dev,
+			&soc_codec_dev_ak4535, &ak4535_dai, 1);
+	if (ret < 0)
+		kfree(ak4535);
 	return ret;
 }
 
-static int ak4535_i2c_remove(struct i2c_client *client)
+static __devexit int ak4535_i2c_remove(struct i2c_client *client)
 {
-	struct snd_soc_codec *codec = i2c_get_clientdata(client);
-	kfree(codec->reg_cache);
+	snd_soc_unregister_codec(&client->dev);
+	kfree(i2c_get_clientdata(client));
 	return 0;
 }
 
@@ -529,138 +519,34 @@ MODULE_DEVICE_TABLE(i2c, ak4535_i2c_id);
 
 static struct i2c_driver ak4535_i2c_driver = {
 	.driver = {
-		.name = "AK4535 I2C Codec",
+		.name = "ak4535-codec",
 		.owner = THIS_MODULE,
 	},
 	.probe =    ak4535_i2c_probe,
-	.remove =   ak4535_i2c_remove,
+	.remove =   __devexit_p(ak4535_i2c_remove),
 	.id_table = ak4535_i2c_id,
 };
-
-static int ak4535_add_i2c_device(struct platform_device *pdev,
-				 const struct ak4535_setup_data *setup)
-{
-	struct i2c_board_info info;
-	struct i2c_adapter *adapter;
-	struct i2c_client *client;
-	int ret;
-
-	ret = i2c_add_driver(&ak4535_i2c_driver);
-	if (ret != 0) {
-		dev_err(&pdev->dev, "can't add i2c driver\n");
-		return ret;
-	}
-
-	memset(&info, 0, sizeof(struct i2c_board_info));
-	info.addr = setup->i2c_address;
-	strlcpy(info.type, "ak4535", I2C_NAME_SIZE);
-
-	adapter = i2c_get_adapter(setup->i2c_bus);
-	if (!adapter) {
-		dev_err(&pdev->dev, "can't get i2c adapter %d\n",
-			setup->i2c_bus);
-		goto err_driver;
-	}
-
-	client = i2c_new_device(adapter, &info);
-	i2c_put_adapter(adapter);
-	if (!client) {
-		dev_err(&pdev->dev, "can't add i2c device at 0x%x\n",
-			(unsigned int)info.addr);
-		goto err_driver;
-	}
-
-	return 0;
-
-err_driver:
-	i2c_del_driver(&ak4535_i2c_driver);
-	return -ENODEV;
-}
 #endif
 
-static int ak4535_probe(struct platform_device *pdev)
+static int __init ak4535_modinit(void)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct ak4535_setup_data *setup;
-	struct snd_soc_codec *codec;
-	struct ak4535_priv *ak4535;
-	int ret;
-
-	printk(KERN_INFO "AK4535 Audio Codec %s", AK4535_VERSION);
-
-	setup = socdev->codec_data;
-	codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (codec == NULL)
-		return -ENOMEM;
-
-	ak4535 = kzalloc(sizeof(struct ak4535_priv), GFP_KERNEL);
-	if (ak4535 == NULL) {
-		kfree(codec);
-		return -ENOMEM;
-	}
-
-	snd_soc_codec_set_drvdata(codec, ak4535);
-	socdev->card->codec = codec;
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	ak4535_socdev = socdev;
-	ret = -ENODEV;
-
+	int ret = 0;
 #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
-	if (setup->i2c_address) {
-		codec->hw_write = (hw_write_t)i2c_master_send;
-		ret = ak4535_add_i2c_device(pdev, setup);
-	}
-#endif
-
+	ret = i2c_add_driver(&ak4535_i2c_driver);
 	if (ret != 0) {
-		kfree(snd_soc_codec_get_drvdata(codec));
-		kfree(codec);
+		printk(KERN_ERR "Failed to register AK4535 I2C driver: %d\n",
+		       ret);
 	}
+#endif
 	return ret;
 }
+module_init(ak4535_modinit);
 
-/* power down chip */
-static int ak4535_remove(struct platform_device *pdev)
+static void __exit ak4535_exit(void)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	if (codec->control_data)
-		ak4535_set_bias_level(codec, SND_SOC_BIAS_OFF);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
 #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
-	if (codec->control_data)
-		i2c_unregister_device(codec->control_data);
 	i2c_del_driver(&ak4535_i2c_driver);
 #endif
-	kfree(snd_soc_codec_get_drvdata(codec));
-	kfree(codec);
-
-	return 0;
-}
-
-struct snd_soc_codec_device soc_codec_dev_ak4535 = {
-	.probe = 	ak4535_probe,
-	.remove = 	ak4535_remove,
-	.suspend = 	ak4535_suspend,
-	.resume =	ak4535_resume,
-};
-EXPORT_SYMBOL_GPL(soc_codec_dev_ak4535);
-
-static int __init ak4535_modinit(void)
-{
-	return snd_soc_register_dai(&ak4535_dai);
-}
-module_init(ak4535_modinit);
-
-static void __exit ak4535_exit(void)
-{
-	snd_soc_unregister_dai(&ak4535_dai);
 }
 module_exit(ak4535_exit);
 

+ 0 - 8
sound/soc/codecs/ak4535.h

@@ -36,12 +36,4 @@
 
 #define AK4535_CACHEREGNUM 	0x10
 
-struct ak4535_setup_data {
-	int            i2c_bus;
-	unsigned short i2c_address;
-};
-
-extern struct snd_soc_dai ak4535_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ak4535;
-
 #endif

+ 37 - 138
sound/soc/codecs/ak4642.c

@@ -30,8 +30,6 @@
 #include <sound/initval.h>
 #include <sound/tlv.h>
 
-#include "ak4642.h"
-
 #define AK4642_VERSION "0.0.1"
 
 #define PW_MGMT1	0x00
@@ -102,7 +100,6 @@
 #define FS3		(1 << 5)
 #define FS_MASK		(FS0 | FS1 | FS2 | FS3)
 
-struct snd_soc_codec_device soc_codec_dev_ak4642;
 
 /*
  * Playback Volume (table 39)
@@ -123,11 +120,11 @@ static const struct snd_kcontrol_new ak4642_snd_controls[] = {
 
 /* codec private data */
 struct ak4642_priv {
-	struct snd_soc_codec codec;
+	unsigned int sysclk;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 };
 
-static struct snd_soc_codec *ak4642_codec;
-
 /*
  * ak4642 register cache
  */
@@ -393,8 +390,8 @@ static struct snd_soc_dai_ops ak4642_dai_ops = {
 	.hw_params	= ak4642_dai_hw_params,
 };
 
-struct snd_soc_dai ak4642_dai = {
-	.name = "AK4642",
+static struct snd_soc_dai_driver ak4642_dai = {
+	.name = "ak4642-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -410,112 +407,63 @@ struct snd_soc_dai ak4642_dai = {
 	.ops = &ak4642_dai_ops,
 	.symmetric_rates = 1,
 };
-EXPORT_SYMBOL_GPL(ak4642_dai);
 
-static int ak4642_resume(struct platform_device *pdev)
+static int ak4642_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	ak4642_sync(codec);
 	return 0;
 }
 
-/*
- * initialise the AK4642 driver
- * register the mixer and dsp interfaces with the kernel
- */
-static int ak4642_init(struct ak4642_priv *ak4642)
+
+static int ak4642_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_codec *codec = &ak4642->codec;
-	int ret = 0;
+	struct ak4642_priv *ak4642 = snd_soc_codec_get_drvdata(codec);
 
-	if (ak4642_codec) {
-		dev_err(codec->dev, "Another ak4642 is registered\n");
-		return -EINVAL;
-	}
+	dev_info(codec->dev, "AK4642 Audio Codec %s", AK4642_VERSION);
 
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	snd_soc_codec_set_drvdata(codec, ak4642);
-	codec->name		= "AK4642";
-	codec->owner		= THIS_MODULE;
-	codec->read		= ak4642_read_reg_cache;
-	codec->write		= ak4642_write;
-	codec->dai		= &ak4642_dai;
-	codec->num_dai		= 1;
 	codec->hw_write		= (hw_write_t)i2c_master_send;
-	codec->reg_cache_size	= ARRAY_SIZE(ak4642_reg);
-	codec->reg_cache	= kmemdup(ak4642_reg,
-					  sizeof(ak4642_reg), GFP_KERNEL);
-
-	if (!codec->reg_cache)
-		return -ENOMEM;
-
-	ak4642_dai.dev = codec->dev;
-	ak4642_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		goto reg_cache_err;
-	}
+	codec->control_data = ak4642->control_data;
 
-	ret = snd_soc_register_dai(&ak4642_dai);
-	if (ret) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		snd_soc_unregister_codec(codec);
-		goto reg_cache_err;
-	}
-
-	return ret;
-
-reg_cache_err:
-	kfree(codec->reg_cache);
-	codec->reg_cache = NULL;
 
-	return ret;
+	return 0;
 }
 
+static struct snd_soc_codec_driver soc_codec_dev_ak4642 = {
+	.probe =	ak4642_probe,
+	.resume =	ak4642_resume,
+	.read		= ak4642_read_reg_cache,
+	.write		= ak4642_write,
+	.reg_cache_size	= ARRAY_SIZE(ak4642_reg),
+	.reg_word_size = sizeof(u8),
+	.reg_cache_default	= ak4642_reg,
+};
+
 #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
-static int ak4642_i2c_probe(struct i2c_client *i2c,
-			    const struct i2c_device_id *id)
+static __devinit int ak4642_i2c_probe(struct i2c_client *i2c,
+				      const struct i2c_device_id *id)
 {
 	struct ak4642_priv *ak4642;
-	struct snd_soc_codec *codec;
 	int ret;
 
 	ak4642 = kzalloc(sizeof(struct ak4642_priv), GFP_KERNEL);
-	if (!ak4642)
+	if (ak4642 == NULL)
 		return -ENOMEM;
 
-	codec = &ak4642->codec;
-	codec->dev = &i2c->dev;
-
 	i2c_set_clientdata(i2c, ak4642);
-	codec->control_data = i2c;
+	ak4642->control_data = i2c;
+	ak4642->control_type = SND_SOC_I2C;
 
-	ret = ak4642_init(ak4642);
-	if (ret < 0) {
-		printk(KERN_ERR "failed to initialise AK4642\n");
+	ret =  snd_soc_register_codec(&i2c->dev,
+			&soc_codec_dev_ak4642, &ak4642_dai, 1);
+	if (ret < 0)
 		kfree(ak4642);
-	}
-
 	return ret;
 }
 
-static int ak4642_i2c_remove(struct i2c_client *client)
+static __devexit int ak4642_i2c_remove(struct i2c_client *client)
 {
-	struct ak4642_priv *ak4642 = i2c_get_clientdata(client);
-
-	snd_soc_unregister_dai(&ak4642_dai);
-	snd_soc_unregister_codec(&ak4642->codec);
-	kfree(ak4642->codec.reg_cache);
-	kfree(ak4642);
-	ak4642_codec = NULL;
-
+	snd_soc_unregister_codec(&client->dev);
+	kfree(i2c_get_clientdata(client));
 	return 0;
 }
 
@@ -528,64 +476,15 @@ MODULE_DEVICE_TABLE(i2c, ak4642_i2c_id);
 
 static struct i2c_driver ak4642_i2c_driver = {
 	.driver = {
-		.name = "AK4642 I2C Codec",
+		.name = "ak4642-codec",
 		.owner = THIS_MODULE,
 	},
-	.probe		= ak4642_i2c_probe,
-	.remove		= ak4642_i2c_remove,
-	.id_table	= ak4642_i2c_id,
+	.probe =    ak4642_i2c_probe,
+	.remove =   __devexit_p(ak4642_i2c_remove),
+	.id_table = ak4642_i2c_id,
 };
-
 #endif
 
-static int ak4642_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	int ret;
-
-	if (!ak4642_codec) {
-		dev_err(&pdev->dev, "Codec device not registered\n");
-		return -ENODEV;
-	}
-
-	socdev->card->codec = ak4642_codec;
-
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		printk(KERN_ERR "ak4642: failed to create pcms\n");
-		goto pcm_err;
-	}
-
-	snd_soc_add_controls(ak4642_codec, ak4642_snd_controls,
-			     ARRAY_SIZE(ak4642_snd_controls));
-
-	dev_info(&pdev->dev, "AK4642 Audio Codec %s", AK4642_VERSION);
-	return ret;
-
-pcm_err:
-	return ret;
-
-}
-
-/* power down chip */
-static int ak4642_remove(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
-
-	return 0;
-}
-
-struct snd_soc_codec_device soc_codec_dev_ak4642 = {
-	.probe =	ak4642_probe,
-	.remove =	ak4642_remove,
-	.resume =	ak4642_resume,
-};
-EXPORT_SYMBOL_GPL(soc_codec_dev_ak4642);
-
 static int __init ak4642_modinit(void)
 {
 	int ret = 0;

+ 0 - 20
sound/soc/codecs/ak4642.h

@@ -1,20 +0,0 @@
-/*
- * ak4642.h  --  AK4642 Soc Audio driver
- *
- * Copyright (C) 2009 Renesas Solutions Corp.
- * Kuninori Morimoto <morimoto.kuninori@renesas.com>
- *
- * Based on ak4535.c
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- */
-
-#ifndef _AK4642_H
-#define _AK4642_H
-
-extern struct snd_soc_dai ak4642_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ak4642;
-
-#endif

+ 30 - 111
sound/soc/codecs/ak4671.c

@@ -23,11 +23,11 @@
 
 #include "ak4671.h"
 
-static struct snd_soc_codec *ak4671_codec;
 
 /* codec private data */
 struct ak4671_priv {
-	struct snd_soc_codec codec;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 	u8 reg_cache[AK4671_CACHEREGNUM];
 };
 
@@ -619,8 +619,8 @@ static struct snd_soc_dai_ops ak4671_dai_ops = {
 	.set_fmt	= ak4671_set_dai_fmt,
 };
 
-struct snd_soc_dai ak4671_dai = {
-	.name = "AK4671",
+static struct snd_soc_dai_driver ak4671_dai = {
+	.name = "ak4671-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -635,27 +635,19 @@ struct snd_soc_dai ak4671_dai = {
 		.formats = AK4671_FORMATS,},
 	.ops = &ak4671_dai_ops,
 };
-EXPORT_SYMBOL_GPL(ak4671_dai);
 
-static int ak4671_probe(struct platform_device *pdev)
+static int ak4671_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
-
-	if (ak4671_codec == NULL) {
-		dev_err(&pdev->dev, "Codec device not registered\n");
-		return -ENODEV;
-	}
+	struct ak4671_priv *ak4671 = snd_soc_codec_get_drvdata(codec);
+	int ret;
 
-	socdev->card->codec = ak4671_codec;
-	codec = ak4671_codec;
+	codec->hw_write = (hw_write_t)i2c_master_send;
+	codec->bias_level = SND_SOC_BIAS_OFF;
 
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
+	ret = snd_soc_codec_set_cache_io(codec, 8, 8, ak4671->control_type);
 	if (ret < 0) {
-		dev_err(codec->dev, "failed to create pcms: %d\n", ret);
-		goto pcm_err;
+		dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret);
+		return ret;
 	}
 
 	snd_soc_add_controls(codec, ak4671_snd_controls,
@@ -665,121 +657,48 @@ static int ak4671_probe(struct platform_device *pdev)
 	ak4671_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
 
 	return ret;
-
-pcm_err:
-	return ret;
 }
 
-static int ak4671_remove(struct platform_device *pdev)
+static int ak4671_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
-
+	ak4671_set_bias_level(codec, SND_SOC_BIAS_OFF);
 	return 0;
 }
 
-struct snd_soc_codec_device soc_codec_dev_ak4671 = {
+static struct snd_soc_codec_driver soc_codec_dev_ak4671 = {
 	.probe = ak4671_probe,
 	.remove = ak4671_remove,
+	.set_bias_level = ak4671_set_bias_level,
+	.reg_cache_size = AK4671_CACHEREGNUM,
+	.reg_word_size = sizeof(u8),
+	.reg_cache_default = ak4671_reg,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_ak4671);
-
-static int ak4671_register(struct ak4671_priv *ak4671,
-		enum snd_soc_control_type control)
-{
-	int ret;
-	struct snd_soc_codec *codec = &ak4671->codec;
-
-	if (ak4671_codec) {
-		dev_err(codec->dev, "Another AK4671 is registered\n");
-		ret = -EINVAL;
-		goto err;
-	}
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	snd_soc_codec_set_drvdata(codec,  ak4671);
-	codec->name = "AK4671";
-	codec->owner = THIS_MODULE;
-	codec->bias_level = SND_SOC_BIAS_OFF;
-	codec->set_bias_level = ak4671_set_bias_level;
-	codec->dai = &ak4671_dai;
-	codec->num_dai = 1;
-	codec->reg_cache_size = AK4671_CACHEREGNUM;
-	codec->reg_cache = &ak4671->reg_cache;
-
-	memcpy(codec->reg_cache, ak4671_reg, sizeof(ak4671_reg));
-
-	ret = snd_soc_codec_set_cache_io(codec, 8, 8, control);
-	if (ret < 0) {
-		dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret);
-		goto err;
-	}
-
-	ak4671_dai.dev = codec->dev;
-	ak4671_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		goto err;
-	}
-
-	ret = snd_soc_register_dai(&ak4671_dai);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		goto err_codec;
-	}
-
-	return 0;
-
-err_codec:
-	snd_soc_unregister_codec(codec);
-err:
-	kfree(ak4671);
-	return ret;
-}
-
-static void ak4671_unregister(struct ak4671_priv *ak4671)
-{
-	ak4671_set_bias_level(&ak4671->codec, SND_SOC_BIAS_OFF);
-	snd_soc_unregister_dai(&ak4671_dai);
-	snd_soc_unregister_codec(&ak4671->codec);
-	kfree(ak4671);
-	ak4671_codec = NULL;
-}
 
 static int __devinit ak4671_i2c_probe(struct i2c_client *client,
 		const struct i2c_device_id *id)
 {
 	struct ak4671_priv *ak4671;
-	struct snd_soc_codec *codec;
+	int ret;
 
 	ak4671 = kzalloc(sizeof(struct ak4671_priv), GFP_KERNEL);
 	if (ak4671 == NULL)
 		return -ENOMEM;
 
-	codec = &ak4671->codec;
-	codec->hw_write = (hw_write_t)i2c_master_send;
-
 	i2c_set_clientdata(client, ak4671);
-	codec->control_data = client;
-
-	codec->dev = &client->dev;
+	ak4671->control_data = client;
+	ak4671->control_type = SND_SOC_I2C;
 
-	return ak4671_register(ak4671, SND_SOC_I2C);
+	ret = snd_soc_register_codec(&client->dev,
+			&soc_codec_dev_ak4671, &ak4671_dai, 1);
+	if (ret < 0)
+		kfree(ak4671);
+	return ret;
 }
 
 static __devexit int ak4671_i2c_remove(struct i2c_client *client)
 {
-	struct ak4671_priv *ak4671 = i2c_get_clientdata(client);
-
-	ak4671_unregister(ak4671);
-
+	snd_soc_unregister_codec(&client->dev);
+	kfree(i2c_get_clientdata(client));
 	return 0;
 }
 
@@ -791,7 +710,7 @@ MODULE_DEVICE_TABLE(i2c, ak4671_i2c_id);
 
 static struct i2c_driver ak4671_i2c_driver = {
 	.driver = {
-		.name = "ak4671",
+		.name = "ak4671-codec",
 		.owner = THIS_MODULE,
 	},
 	.probe = ak4671_i2c_probe,

+ 0 - 3
sound/soc/codecs/ak4671.h

@@ -150,7 +150,4 @@
 /* AK4671_LOUT2_POWER_MANAGEMENT (0x10) Fields */
 #define AK4671_MUTEN				0x04
 
-extern struct snd_soc_dai ak4671_dai;
-extern struct snd_soc_codec_device soc_codec_dev_ak4671;
-
 #endif

+ 29 - 103
sound/soc/codecs/cq93vc.c

@@ -30,6 +30,7 @@
 #include <linux/slab.h>
 #include <linux/clk.h>
 #include <linux/mfd/davinci_voicecodec.h>
+#include <linux/spi/spi.h>
 
 #include <sound/core.h>
 #include <sound/pcm.h>
@@ -41,8 +42,6 @@
 
 #include <mach/dm365.h>
 
-#include "cq93vc.h"
-
 static inline unsigned int cq93vc_read(struct snd_soc_codec *codec,
 						unsigned int reg)
 {
@@ -130,8 +129,8 @@ static struct snd_soc_dai_ops cq93vc_dai_ops = {
 	.set_sysclk	= cq93vc_set_dai_sysclk,
 };
 
-struct snd_soc_dai cq93vc_dai = {
-	.name = "CQ93VC",
+static struct snd_soc_dai_driver cq93vc_dai = {
+	.name = "cq93vc-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -146,36 +145,20 @@ struct snd_soc_dai cq93vc_dai = {
 		.formats = CQ93VC_FORMATS,},
 	.ops = &cq93vc_dai_ops,
 };
-EXPORT_SYMBOL_GPL(cq93vc_dai);
 
-static int cq93vc_resume(struct platform_device *pdev)
+static int cq93vc_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	cq93vc_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
 
 	return 0;
 }
 
-static struct snd_soc_codec *cq93vc_codec;
-
-static int cq93vc_probe(struct platform_device *pdev)
+static int cq93vc_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct device *dev = &pdev->dev;
-	struct snd_soc_codec *codec;
-	int ret;
-
-	socdev->card->codec = cq93vc_codec;
-	codec = socdev->card->codec;
-
-	/* Register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(dev, "%s: failed to create pcms\n", pdev->name);
-		return ret;
-	}
+	struct davinci_vc *davinci_vc = codec->dev->platform_data;
+
+	davinci_vc->cq93vc.codec = codec;
+	codec->control_data = davinci_vc;
 
 	/* Set controls */
 	snd_soc_add_controls(codec, cq93vc_snd_controls,
@@ -187,108 +170,51 @@ static int cq93vc_probe(struct platform_device *pdev)
 	return 0;
 }
 
-static int cq93vc_remove(struct platform_device *pdev)
+static int cq93vc_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
+	cq93vc_set_bias_level(codec, SND_SOC_BIAS_OFF);
 
 	return 0;
 }
 
-struct snd_soc_codec_device soc_codec_dev_cq93vc = {
+static struct snd_soc_codec_driver soc_codec_dev_cq93vc = {
+	.read = cq93vc_read,
+	.write = cq93vc_write,
+	.set_bias_level = cq93vc_set_bias_level,
 	.probe = cq93vc_probe,
 	.remove = cq93vc_remove,
 	.resume = cq93vc_resume,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_cq93vc);
 
-static __init int cq93vc_codec_probe(struct platform_device *pdev)
+static int cq93vc_platform_probe(struct platform_device *pdev)
 {
-	struct davinci_vc *davinci_vc = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret;
-
-	codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (codec == NULL) {
-		dev_dbg(davinci_vc->dev,
-			"could not allocate memory for codec data\n");
-		return -ENOMEM;
-	}
-
-	davinci_vc->cq93vc.codec = codec;
-
-	cq93vc_dai.dev = &pdev->dev;
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-	codec->dev = &pdev->dev;
-	codec->name = "CQ93VC";
-	codec->owner = THIS_MODULE;
-	codec->read = cq93vc_read;
-	codec->write = cq93vc_write;
-	codec->set_bias_level = cq93vc_set_bias_level;
-	codec->dai = &cq93vc_dai;
-	codec->num_dai = 1;
-	codec->control_data = davinci_vc;
-
-	cq93vc_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret) {
-		dev_err(davinci_vc->dev, "failed to register codec\n");
-		goto fail1;
-	}
-
-	ret = snd_soc_register_dai(&cq93vc_dai);
-	if (ret) {
-		dev_err(davinci_vc->dev, "could register dai\n");
-		goto fail2;
-	}
-	return 0;
-
-fail2:
-	snd_soc_unregister_codec(codec);
-
-fail1:
-	kfree(codec);
-	cq93vc_codec = NULL;
-
-	return ret;
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_cq93vc, &cq93vc_dai, 1);
 }
 
-static int __devexit cq93vc_codec_remove(struct platform_device *pdev)
+static int cq93vc_platform_remove(struct platform_device *pdev)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
-	snd_soc_unregister_dai(&cq93vc_dai);
-	snd_soc_unregister_codec(&codec);
-
-	kfree(codec);
-	cq93vc_codec = NULL;
-
+	snd_soc_unregister_codec(&pdev->dev);
 	return 0;
 }
 
 static struct platform_driver cq93vc_codec_driver = {
 	.driver = {
-		   .name = "cq93vc",
-		   .owner = THIS_MODULE,
-		   },
-	.probe = cq93vc_codec_probe,
-	.remove = __devexit_p(cq93vc_codec_remove),
+			.name = "cq93vc-codec",
+			.owner = THIS_MODULE,
+	},
+
+	.probe = cq93vc_platform_probe,
+	.remove = __devexit_p(cq93vc_platform_remove),
 };
 
-static __init int cq93vc_init(void)
+static int __init cq93vc_init(void)
 {
-	return platform_driver_probe(&cq93vc_codec_driver, cq93vc_codec_probe);
+	return platform_driver_register(&cq93vc_codec_driver);
 }
 module_init(cq93vc_init);
 
-static __exit void cq93vc_exit(void)
+static void __exit cq93vc_exit(void)
 {
 	platform_driver_unregister(&cq93vc_codec_driver);
 }

+ 0 - 29
sound/soc/codecs/cq93vc.h

@@ -1,29 +0,0 @@
-/*
- * ALSA SoC CQ0093 Voice Codec Driver for DaVinci platforms
- *
- * Copyright (C) 2010 Texas Instruments, Inc
- *
- * Author: Miguel Aguilar <miguel.aguilar@ridgerun.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#ifndef _CQ93VC_H
-#define _CQ93VC_H
-
-extern struct snd_soc_dai cq93vc_dai;
-extern struct snd_soc_codec_device soc_codec_dev_cq93vc;
-
-#endif

+ 138 - 255
sound/soc/codecs/cs4270.c

@@ -31,8 +31,6 @@
 #include <linux/delay.h>
 #include <linux/regulator/consumer.h>
 
-#include "cs4270.h"
-
 /*
  * The codec isn't really big-endian or little-endian, since the I2S
  * interface requires data to be sent serially with the MSbit first.
@@ -114,7 +112,8 @@ static const char *supply_names[] = {
 
 /* Private data for the CS4270 */
 struct cs4270_private {
-	struct snd_soc_codec codec;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 	u8 reg_cache[CS4270_NUMREGS];
 	unsigned int mclk; /* Input frequency of the MCLK pin */
 	unsigned int mode; /* The mode (I2S or left-justified) */
@@ -212,44 +211,8 @@ static int cs4270_set_dai_sysclk(struct snd_soc_dai *codec_dai,
 {
 	struct snd_soc_codec *codec = codec_dai->codec;
 	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
-	unsigned int rates = 0;
-	unsigned int rate_min = -1;
-	unsigned int rate_max = 0;
-	unsigned int i;
 
 	cs4270->mclk = freq;
-
-	if (cs4270->mclk) {
-		for (i = 0; i < NUM_MCLK_RATIOS; i++) {
-			unsigned int rate = freq / cs4270_mode_ratios[i].ratio;
-			rates |= snd_pcm_rate_to_rate_bit(rate);
-			if (rate < rate_min)
-				rate_min = rate;
-			if (rate > rate_max)
-				rate_max = rate;
-		}
-		/* FIXME: soc should support a rate list */
-		rates &= ~SNDRV_PCM_RATE_KNOT;
-
-		if (!rates) {
-			dev_err(codec->dev, "could not find a valid sample rate\n");
-			return -EINVAL;
-		}
-	} else {
-		/* enable all possible rates */
-		rates = SNDRV_PCM_RATE_8000_192000;
-		rate_min = 8000;
-		rate_max = 192000;
-	}
-
-	codec_dai->playback.rates = rates;
-	codec_dai->playback.rate_min = rate_min;
-	codec_dai->playback.rate_max = rate_max;
-
-	codec_dai->capture.rates = rates;
-	codec_dai->capture.rate_min = rate_min;
-	codec_dai->capture.rate_max = rate_max;
-
 	return 0;
 }
 
@@ -410,8 +373,7 @@ static int cs4270_hw_params(struct snd_pcm_substream *substream,
 			    struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
 	int ret;
 	unsigned int i;
@@ -549,19 +511,6 @@ static const struct snd_kcontrol_new cs4270_snd_controls[] = {
 		snd_soc_get_volsw, cs4270_soc_put_mute),
 };
 
-/*
- * cs4270_codec - global variable to store codec for the ASoC probe function
- *
- * If struct i2c_driver had a private_data field, we wouldn't need to use
- * cs4270_codec.  This is the only way to pass the codec structure from
- * cs4270_i2c_probe() to cs4270_probe().  Unfortunately, there is no good
- * way to synchronize these two functions.  cs4270_i2c_probe() can be called
- * multiple times before cs4270_probe() is called even once.  So for now, we
- * also only allow cs4270_i2c_probe() to be run once.  That means that we do
- * not support more than one cs4270 device in the system, at least for now.
- */
-static struct snd_soc_codec *cs4270_codec;
-
 static struct snd_soc_dai_ops cs4270_dai_ops = {
 	.hw_params	= cs4270_hw_params,
 	.set_sysclk	= cs4270_set_dai_sysclk,
@@ -569,20 +518,24 @@ static struct snd_soc_dai_ops cs4270_dai_ops = {
 	.digital_mute	= cs4270_dai_mute,
 };
 
-struct snd_soc_dai cs4270_dai = {
-	.name = "cs4270",
+struct snd_soc_dai_driver cs4270_dai = {
+	.name = "cs4270-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
 		.channels_max = 2,
-		.rates = 0,
+		.rates = SNDRV_PCM_RATE_CONTINUOUS,
+		.rate_min = 4000,
+		.rate_max = 216000,
 		.formats = CS4270_FORMATS,
 	},
 	.capture = {
 		.stream_name = "Capture",
 		.channels_min = 1,
 		.channels_max = 2,
-		.rates = 0,
+		.rates = SNDRV_PCM_RATE_CONTINUOUS,
+		.rate_min = 4000,
+		.rate_max = 216000,
 		.formats = CS4270_FORMATS,
 	},
 	.ops = &cs4270_dai_ops,
@@ -596,153 +549,19 @@ EXPORT_SYMBOL_GPL(cs4270_dai);
  * This function is called when ASoC has all the pieces it needs to
  * instantiate a sound driver.
  */
-static int cs4270_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = cs4270_codec;
-	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
-	int i, ret;
-
-	/* Connect the codec to the socdev.  snd_soc_new_pcms() needs this. */
-	socdev->card->codec = codec;
-
-	/* Register PCMs */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to create pcms\n");
-		return ret;
-	}
-
-	/* Add the non-DAPM controls */
-	ret = snd_soc_add_controls(codec, cs4270_snd_controls,
-				ARRAY_SIZE(cs4270_snd_controls));
-	if (ret < 0) {
-		dev_err(codec->dev, "failed to add controls\n");
-		goto error_free_pcms;
-	}
-
-	/* get the power supply regulators */
-	for (i = 0; i < ARRAY_SIZE(supply_names); i++)
-		cs4270->supplies[i].supply = supply_names[i];
-
-	ret = regulator_bulk_get(codec->dev, ARRAY_SIZE(cs4270->supplies),
-				 cs4270->supplies);
-	if (ret < 0)
-		goto error_free_pcms;
-
-	ret = regulator_bulk_enable(ARRAY_SIZE(cs4270->supplies),
-				    cs4270->supplies);
-	if (ret < 0)
-		goto error_free_regulators;
-
-	return 0;
-
-error_free_regulators:
-	regulator_bulk_free(ARRAY_SIZE(cs4270->supplies),
-			    cs4270->supplies);
-
-error_free_pcms:
-	snd_soc_free_pcms(socdev);
-
-	return ret;
-}
-
-/**
- * cs4270_remove - ASoC remove function
- * @pdev: platform device
- *
- * This function is the counterpart to cs4270_probe().
- */
-static int cs4270_remove(struct platform_device *pdev)
+static int cs4270_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = cs4270_codec;
 	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
+	int i, ret, reg;
 
-	snd_soc_free_pcms(socdev);
-	regulator_bulk_disable(ARRAY_SIZE(cs4270->supplies), cs4270->supplies);
-	regulator_bulk_free(ARRAY_SIZE(cs4270->supplies), cs4270->supplies);
-
-	return 0;
-};
-
-/**
- * cs4270_i2c_probe - initialize the I2C interface of the CS4270
- * @i2c_client: the I2C client object
- * @id: the I2C device ID (ignored)
- *
- * This function is called whenever the I2C subsystem finds a device that
- * matches the device ID given via a prior call to i2c_add_driver().
- */
-static int cs4270_i2c_probe(struct i2c_client *i2c_client,
-	const struct i2c_device_id *id)
-{
-	struct snd_soc_codec *codec;
-	struct cs4270_private *cs4270;
-	unsigned int reg;
-	int ret;
-
-	/* For now, we only support one cs4270 device in the system.  See the
-	 * comment for cs4270_codec.
-	 */
-	if (cs4270_codec) {
-		dev_err(&i2c_client->dev, "ignoring CS4270 at addr %X\n",
-		       i2c_client->addr);
-		dev_err(&i2c_client->dev, "only one per board allowed\n");
-		/* Should we return something other than ENODEV here? */
-		return -ENODEV;
-	}
-
-	/* Verify that we have a CS4270 */
-
-	ret = i2c_smbus_read_byte_data(i2c_client, CS4270_CHIPID);
-	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to read i2c at addr %X\n",
-		       i2c_client->addr);
-		return ret;
-	}
-	/* The top four bits of the chip ID should be 1100. */
-	if ((ret & 0xF0) != 0xC0) {
-		dev_err(&i2c_client->dev, "device at addr %X is not a CS4270\n",
-		       i2c_client->addr);
-		return -ENODEV;
-	}
-
-	dev_info(&i2c_client->dev, "found device at i2c address %X\n",
-		i2c_client->addr);
-	dev_info(&i2c_client->dev, "hardware revision %X\n", ret & 0xF);
-
-	/* Allocate enough space for the snd_soc_codec structure
-	   and our private data together. */
-	cs4270 = kzalloc(sizeof(struct cs4270_private), GFP_KERNEL);
-	if (!cs4270) {
-		dev_err(&i2c_client->dev, "could not allocate codec\n");
-		return -ENOMEM;
-	}
-	codec = &cs4270->codec;
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	codec->dev = &i2c_client->dev;
-	codec->name = "CS4270";
-	codec->owner = THIS_MODULE;
-	codec->dai = &cs4270_dai;
-	codec->num_dai = 1;
-	snd_soc_codec_set_drvdata(codec, cs4270);
-	codec->control_data = i2c_client;
-	codec->read = cs4270_read_reg_cache;
-	codec->write = cs4270_i2c_write;
-	codec->reg_cache = cs4270->reg_cache;
-	codec->reg_cache_size = CS4270_NUMREGS;
+	codec->control_data = cs4270->control_data;
 
 	/* The I2C interface is set up, so pre-fill our register cache */
 
 	ret = cs4270_fill_cache(codec);
 	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to fill register cache\n");
-		goto error_free_codec;
+		dev_err(codec->dev, "failed to fill register cache\n");
+		return ret;
 	}
 
 	/* Disable auto-mute.  This feature appears to be buggy.  In some
@@ -755,7 +574,7 @@ static int cs4270_i2c_probe(struct i2c_client *i2c_client,
 	reg &= ~CS4270_MUTE_AUTO;
 	ret = cs4270_i2c_write(codec, CS4270_MUTE, reg);
 	if (ret < 0) {
-		dev_err(&i2c_client->dev, "i2c write failed\n");
+		dev_err(codec->dev, "i2c write failed\n");
 		return ret;
 	}
 
@@ -769,65 +588,56 @@ static int cs4270_i2c_probe(struct i2c_client *i2c_client,
 	reg &= ~(CS4270_TRANS_SOFT | CS4270_TRANS_ZERO);
 	ret = cs4270_i2c_write(codec, CS4270_TRANS, reg);
 	if (ret < 0) {
-		dev_err(&i2c_client->dev, "i2c write failed\n");
+		dev_err(codec->dev, "i2c write failed\n");
 		return ret;
 	}
 
-	/* Initialize the DAI. Normally, we'd prefer to have a kmalloc'd DAI
-	 * structure for each CS4270 device, but the machine driver needs to
-	 * have a pointer to the DAI structure, so for now it must be a global
-	 * variable.
-	 */
-	cs4270_dai.dev = &i2c_client->dev;
-
-	/* Register the DAI.  If all the other ASoC driver have already
-	 * registered, then this will call our probe function, so
-	 * cs4270_codec needs to be ready.
-	 */
-	cs4270_codec = codec;
-	ret = snd_soc_register_dai(&cs4270_dai);
+	/* Add the non-DAPM controls */
+	ret = snd_soc_add_controls(codec, cs4270_snd_controls,
+				ARRAY_SIZE(cs4270_snd_controls));
 	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to register DAIe\n");
-		goto error_free_codec;
+		dev_err(codec->dev, "failed to add controls\n");
+		return ret;
 	}
 
-	i2c_set_clientdata(i2c_client, cs4270);
+	/* get the power supply regulators */
+	for (i = 0; i < ARRAY_SIZE(supply_names); i++)
+		cs4270->supplies[i].supply = supply_names[i];
+
+	ret = regulator_bulk_get(codec->dev, ARRAY_SIZE(cs4270->supplies),
+				 cs4270->supplies);
+	if (ret < 0)
+		return ret;
+
+	ret = regulator_bulk_enable(ARRAY_SIZE(cs4270->supplies),
+				    cs4270->supplies);
+	if (ret < 0)
+		goto error_free_regulators;
 
 	return 0;
 
-error_free_codec:
-	kfree(cs4270);
-	cs4270_codec = NULL;
-	cs4270_dai.dev = NULL;
+error_free_regulators:
+	regulator_bulk_free(ARRAY_SIZE(cs4270->supplies),
+			    cs4270->supplies);
 
 	return ret;
 }
 
 /**
- * cs4270_i2c_remove - remove an I2C device
- * @i2c_client: the I2C client object
+ * cs4270_remove - ASoC remove function
+ * @pdev: platform device
  *
- * This function is the counterpart to cs4270_i2c_probe().
+ * This function is the counterpart to cs4270_probe().
  */
-static int cs4270_i2c_remove(struct i2c_client *i2c_client)
+static int cs4270_remove(struct snd_soc_codec *codec)
 {
-	struct cs4270_private *cs4270 = i2c_get_clientdata(i2c_client);
+	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
 
-	kfree(cs4270);
-	cs4270_codec = NULL;
-	cs4270_dai.dev = NULL;
+	regulator_bulk_disable(ARRAY_SIZE(cs4270->supplies), cs4270->supplies);
+	regulator_bulk_free(ARRAY_SIZE(cs4270->supplies), cs4270->supplies);
 
 	return 0;
-}
-
-/*
- * cs4270_id - I2C device IDs supported by this driver
- */
-static struct i2c_device_id cs4270_id[] = {
-	{"cs4270", 0},
-	{}
 };
-MODULE_DEVICE_TABLE(i2c, cs4270_id);
 
 #ifdef CONFIG_PM
 
@@ -840,9 +650,8 @@ MODULE_DEVICE_TABLE(i2c, cs4270_id);
  * and all registers are written back to the hardware when resuming.
  */
 
-static int cs4270_soc_suspend(struct platform_device *pdev, pm_message_t mesg)
+static int cs4270_soc_suspend(struct snd_soc_codec *codec, pm_message_t mesg)
 {
-	struct snd_soc_codec *codec = cs4270_codec;
 	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
 	int reg, ret;
 
@@ -860,9 +669,8 @@ static int cs4270_soc_suspend(struct platform_device *pdev, pm_message_t mesg)
 	return 0;
 }
 
-static int cs4270_soc_resume(struct platform_device *pdev)
+static int cs4270_soc_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_codec *codec = cs4270_codec;
 	struct cs4270_private *cs4270 = snd_soc_codec_get_drvdata(codec);
 	struct i2c_client *i2c_client = codec->control_data;
 	int reg;
@@ -895,6 +703,95 @@ static int cs4270_soc_resume(struct platform_device *pdev)
 #define cs4270_soc_resume	NULL
 #endif /* CONFIG_PM */
 
+/*
+ * ASoC codec device structure
+ *
+ * Assign this variable to the codec_dev field of the machine driver's
+ * snd_soc_device structure.
+ */
+static struct snd_soc_codec_driver soc_codec_device_cs4270 = {
+	.probe =	cs4270_probe,
+	.remove =	cs4270_remove,
+	.suspend =	cs4270_soc_suspend,
+	.resume =	cs4270_soc_resume,
+	.read = cs4270_read_reg_cache,
+	.write = cs4270_i2c_write,
+	.reg_cache_size = CS4270_NUMREGS,
+	.reg_word_size = sizeof(u8),
+};
+
+/**
+ * cs4270_i2c_probe - initialize the I2C interface of the CS4270
+ * @i2c_client: the I2C client object
+ * @id: the I2C device ID (ignored)
+ *
+ * This function is called whenever the I2C subsystem finds a device that
+ * matches the device ID given via a prior call to i2c_add_driver().
+ */
+static int cs4270_i2c_probe(struct i2c_client *i2c_client,
+	const struct i2c_device_id *id)
+{
+	struct cs4270_private *cs4270;
+	int ret;
+
+	/* Verify that we have a CS4270 */
+
+	ret = i2c_smbus_read_byte_data(i2c_client, CS4270_CHIPID);
+	if (ret < 0) {
+		dev_err(&i2c_client->dev, "failed to read i2c at addr %X\n",
+		       i2c_client->addr);
+		return ret;
+	}
+	/* The top four bits of the chip ID should be 1100. */
+	if ((ret & 0xF0) != 0xC0) {
+		dev_err(&i2c_client->dev, "device at addr %X is not a CS4270\n",
+		       i2c_client->addr);
+		return -ENODEV;
+	}
+
+	dev_info(&i2c_client->dev, "found device at i2c address %X\n",
+		i2c_client->addr);
+	dev_info(&i2c_client->dev, "hardware revision %X\n", ret & 0xF);
+
+	cs4270 = kzalloc(sizeof(struct cs4270_private), GFP_KERNEL);
+	if (!cs4270) {
+		dev_err(&i2c_client->dev, "could not allocate codec\n");
+		return -ENOMEM;
+	}
+
+	i2c_set_clientdata(i2c_client, cs4270);
+	cs4270->control_data = i2c_client;
+	cs4270->control_type = SND_SOC_I2C;
+
+	ret = snd_soc_register_codec(&i2c_client->dev,
+			&soc_codec_device_cs4270, &cs4270_dai, 1);
+	if (ret < 0)
+		kfree(cs4270);
+	return ret;
+}
+
+/**
+ * cs4270_i2c_remove - remove an I2C device
+ * @i2c_client: the I2C client object
+ *
+ * This function is the counterpart to cs4270_i2c_probe().
+ */
+static int cs4270_i2c_remove(struct i2c_client *i2c_client)
+{
+	snd_soc_unregister_codec(&i2c_client->dev);
+	kfree(i2c_get_clientdata(i2c_client));
+	return 0;
+}
+
+/*
+ * cs4270_id - I2C device IDs supported by this driver
+ */
+static struct i2c_device_id cs4270_id[] = {
+	{"cs4270", 0},
+	{}
+};
+MODULE_DEVICE_TABLE(i2c, cs4270_id);
+
 /*
  * cs4270_i2c_driver - I2C device identification
  *
@@ -903,7 +800,7 @@ static int cs4270_soc_resume(struct platform_device *pdev)
  */
 static struct i2c_driver cs4270_i2c_driver = {
 	.driver = {
-		.name = "cs4270",
+		.name = "cs4270-codec",
 		.owner = THIS_MODULE,
 	},
 	.id_table = cs4270_id,
@@ -911,20 +808,6 @@ static struct i2c_driver cs4270_i2c_driver = {
 	.remove = cs4270_i2c_remove,
 };
 
-/*
- * ASoC codec device structure
- *
- * Assign this variable to the codec_dev field of the machine driver's
- * snd_soc_device structure.
- */
-struct snd_soc_codec_device soc_codec_device_cs4270 = {
-	.probe = 	cs4270_probe,
-	.remove = 	cs4270_remove,
-	.suspend =	cs4270_soc_suspend,
-	.resume =	cs4270_soc_resume,
-};
-EXPORT_SYMBOL_GPL(soc_codec_device_cs4270);
-
 static int __init cs4270_init(void)
 {
 	pr_info("Cirrus Logic CS4270 ALSA SoC Codec Driver\n");

+ 0 - 28
sound/soc/codecs/cs4270.h

@@ -1,28 +0,0 @@
-/*
- * Cirrus Logic CS4270 ALSA SoC Codec Driver
- *
- * Author: Timur Tabi <timur@freescale.com>
- *
- * Copyright 2007 Freescale Semiconductor, Inc.  This file is licensed under
- * the terms of the GNU General Public License version 2.  This program
- * is licensed "as is" without any warranty of any kind, whether express
- * or implied.
- */
-
-#ifndef _CS4270_H
-#define _CS4270_H
-
-/*
- * The ASoC codec DAI structure for the CS4270.  Assign this structure to
- * the .codec_dai field of your machine driver's snd_soc_dai_link structure.
- */
-extern struct snd_soc_dai cs4270_dai;
-
-/*
- * The ASoC codec device structure for the CS4270.  Assign this structure
- * to the .codec_dev field of your machine driver's snd_soc_device
- * structure.
- */
-extern struct snd_soc_codec_device soc_codec_device_cs4270;
-
-#endif

+ 92 - 201
sound/soc/codecs/cs42l51.c

@@ -42,15 +42,14 @@ enum master_slave_mode {
 };
 
 struct cs42l51_private {
+	enum snd_soc_control_type control_type;
+	void *control_data;
 	unsigned int mclk;
 	unsigned int audio_mode;	/* The mode (I2S or left-justified) */
 	enum master_slave_mode func;
-	struct snd_soc_codec codec;
 	u8 reg_cache[CS42L51_NUMREGS];
 };
 
-static struct snd_soc_codec *cs42l51_codec;
-
 #define CS42L51_FORMATS ( \
 		SNDRV_PCM_FMTBIT_S16_LE  | SNDRV_PCM_FMTBIT_S16_BE  | \
 		SNDRV_PCM_FMTBIT_S18_3LE | SNDRV_PCM_FMTBIT_S18_3BE | \
@@ -75,134 +74,6 @@ static int cs42l51_fill_cache(struct snd_soc_codec *codec)
 	return 0;
 }
 
-static int cs42l51_i2c_probe(struct i2c_client *i2c_client,
-	const struct i2c_device_id *id)
-{
-	struct snd_soc_codec *codec;
-	struct cs42l51_private *cs42l51;
-	int ret = 0;
-	int reg;
-
-	if (cs42l51_codec)
-		return -EBUSY;
-
-	/* Verify that we have a CS42L51 */
-	ret = i2c_smbus_read_byte_data(i2c_client, CS42L51_CHIP_REV_ID);
-	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to read I2C\n");
-		goto error;
-	}
-
-	if ((ret != CS42L51_MK_CHIP_REV(CS42L51_CHIP_ID, CS42L51_CHIP_REV_A)) &&
-	    (ret != CS42L51_MK_CHIP_REV(CS42L51_CHIP_ID, CS42L51_CHIP_REV_B))) {
-		dev_err(&i2c_client->dev, "Invalid chip id\n");
-		ret = -ENODEV;
-		goto error;
-	}
-
-	dev_info(&i2c_client->dev, "found device cs42l51 rev %d\n",
-				ret & 7);
-
-	cs42l51 = kzalloc(sizeof(struct cs42l51_private), GFP_KERNEL);
-	if (!cs42l51) {
-		dev_err(&i2c_client->dev, "could not allocate codec\n");
-		return -ENOMEM;
-	}
-	codec = &cs42l51->codec;
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	codec->dev = &i2c_client->dev;
-	codec->name = "CS42L51";
-	codec->owner = THIS_MODULE;
-	codec->dai = &cs42l51_dai;
-	codec->num_dai = 1;
-	snd_soc_codec_set_drvdata(codec, cs42l51);
-
-	codec->control_data = i2c_client;
-	codec->reg_cache = cs42l51->reg_cache;
-	codec->reg_cache_size = CS42L51_NUMREGS;
-	i2c_set_clientdata(i2c_client, codec);
-
-	ret = cs42l51_fill_cache(codec);
-	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to fill register cache\n");
-		goto error_alloc;
-	}
-
-	ret = snd_soc_codec_set_cache_io(codec, 8, 8, SND_SOC_I2C);
-	if (ret < 0) {
-		dev_err(&i2c_client->dev, "Failed to set cache I/O: %d\n", ret);
-		goto error_alloc;
-	}
-
-	/*
-	 * DAC configuration
-	 * - Use signal processor
-	 * - auto mute
-	 * - vol changes immediate
-	 * - no de-emphasize
-	 */
-	reg = CS42L51_DAC_CTL_DATA_SEL(1)
-		| CS42L51_DAC_CTL_AMUTE | CS42L51_DAC_CTL_DACSZ(0);
-	ret = snd_soc_write(codec, CS42L51_DAC_CTL, reg);
-	if (ret < 0)
-		goto error_alloc;
-
-	cs42l51_dai.dev = codec->dev;
-	cs42l51_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		goto error_alloc;
-	}
-
-	ret = snd_soc_register_dai(&cs42l51_dai);
-	if (ret < 0) {
-		dev_err(&i2c_client->dev, "failed to register DAIe\n");
-		goto error_reg;
-	}
-
-	return 0;
-
-error_reg:
-	snd_soc_unregister_codec(codec);
-error_alloc:
-	kfree(cs42l51);
-error:
-	return ret;
-}
-
-static int cs42l51_i2c_remove(struct i2c_client *client)
-{
-	struct cs42l51_private *cs42l51 = i2c_get_clientdata(client);
-	snd_soc_unregister_dai(&cs42l51_dai);
-	snd_soc_unregister_codec(cs42l51_codec);
-	cs42l51_codec = NULL;
-	kfree(cs42l51);
-	return 0;
-}
-
-
-static const struct i2c_device_id cs42l51_id[] = {
-	{"cs42l51", 0},
-	{}
-};
-MODULE_DEVICE_TABLE(i2c, cs42l51_id);
-
-static struct i2c_driver cs42l51_i2c_driver = {
-	.driver = {
-		.name = "CS42L51 I2C",
-		.owner = THIS_MODULE,
-	},
-	.id_table = cs42l51_id,
-	.probe = cs42l51_i2c_probe,
-	.remove = cs42l51_i2c_remove,
-};
-
 static int cs42l51_get_chan_mix(struct snd_kcontrol *kcontrol,
 			struct snd_ctl_elem_value *ucontrol)
 {
@@ -484,51 +355,8 @@ static int cs42l51_set_dai_sysclk(struct snd_soc_dai *codec_dai,
 {
 	struct snd_soc_codec *codec = codec_dai->codec;
 	struct cs42l51_private *cs42l51 = snd_soc_codec_get_drvdata(codec);
-	struct cs42l51_ratios *ratios = NULL;
-	int nr_ratios = 0;
-	unsigned int rates = 0;
-	unsigned int rate_min = -1;
-	unsigned int rate_max = 0;
-	int i;
 
 	cs42l51->mclk = freq;
-
-	switch (cs42l51->func) {
-	case MODE_MASTER:
-		return -EINVAL;
-	case MODE_SLAVE:
-		ratios = slave_ratios;
-		nr_ratios = ARRAY_SIZE(slave_ratios);
-		break;
-	case MODE_SLAVE_AUTO:
-		ratios = slave_auto_ratios;
-		nr_ratios = ARRAY_SIZE(slave_auto_ratios);
-		break;
-	}
-
-	for (i = 0; i < nr_ratios; i++) {
-		unsigned int rate = freq / ratios[i].ratio;
-		rates |= snd_pcm_rate_to_rate_bit(rate);
-		if (rate < rate_min)
-			rate_min = rate;
-		if (rate > rate_max)
-			rate_max = rate;
-	}
-	rates &= ~SNDRV_PCM_RATE_KNOT;
-
-	if (!rates) {
-		dev_err(codec->dev, "could not find a valid sample rate\n");
-		return -EINVAL;
-	}
-
-	codec_dai->playback.rates = rates;
-	codec_dai->playback.rate_min = rate_min;
-	codec_dai->playback.rate_max = rate_max;
-
-	codec_dai->capture.rates = rates;
-	codec_dai->capture.rate_min = rate_min;
-	codec_dai->capture.rate_max = rate_max;
-
 	return 0;
 }
 
@@ -537,8 +365,7 @@ static int cs42l51_hw_params(struct snd_pcm_substream *substream,
 		struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	struct cs42l51_private *cs42l51 = snd_soc_codec_get_drvdata(codec);
 	int ret;
 	unsigned int i;
@@ -670,8 +497,8 @@ static struct snd_soc_dai_ops cs42l51_dai_ops = {
 	.digital_mute   = cs42l51_dai_mute,
 };
 
-struct snd_soc_dai cs42l51_dai = {
-	.name = "CS42L51 HiFi",
+static struct snd_soc_dai_driver cs42l51_dai = {
+	.name = "cs42l51-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -688,30 +515,39 @@ struct snd_soc_dai cs42l51_dai = {
 	},
 	.ops = &cs42l51_dai_ops,
 };
-EXPORT_SYMBOL_GPL(cs42l51_dai);
-
 
-static int cs42l51_probe(struct platform_device *pdev)
+static int cs42l51_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret = 0;
+	struct cs42l51_private *cs42l51 = snd_soc_codec_get_drvdata(codec);
+	int ret, reg;
 
-	if (!cs42l51_codec) {
-		dev_err(&pdev->dev, "CS42L51 codec not yet registered\n");
-		return -EINVAL;
-	}
+	codec->control_data = cs42l51->control_data;
 
-	socdev->card->codec = cs42l51_codec;
-	codec = socdev->card->codec;
+	ret = cs42l51_fill_cache(codec);
+	if (ret < 0) {
+		dev_err(codec->dev, "failed to fill register cache\n");
+		return ret;
+	}
 
-	/* Register PCMs */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
+	ret = snd_soc_codec_set_cache_io(codec, 8, 8, cs42l51->control_type);
 	if (ret < 0) {
-		dev_err(&pdev->dev, "failed to create PCMs\n");
+		dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret);
 		return ret;
 	}
 
+	/*
+	 * DAC configuration
+	 * - Use signal processor
+	 * - auto mute
+	 * - vol changes immediate
+	 * - no de-emphasize
+	 */
+	reg = CS42L51_DAC_CTL_DATA_SEL(1)
+		| CS42L51_DAC_CTL_AMUTE | CS42L51_DAC_CTL_DACSZ(0);
+	ret = snd_soc_write(codec, CS42L51_DAC_CTL, reg);
+	if (ret < 0)
+		return ret;
+
 	snd_soc_add_controls(codec, cs42l51_snd_controls,
 		ARRAY_SIZE(cs42l51_snd_controls));
 	snd_soc_dapm_new_controls(codec, cs42l51_dapm_widgets,
@@ -722,22 +558,77 @@ static int cs42l51_probe(struct platform_device *pdev)
 	return 0;
 }
 
+static struct snd_soc_codec_driver soc_codec_device_cs42l51 = {
+	.probe =	cs42l51_probe,
+	.reg_cache_size = CS42L51_NUMREGS,
+	.reg_word_size = sizeof(u8),
+};
 
-static int cs42l51_remove(struct platform_device *pdev)
+static int cs42l51_i2c_probe(struct i2c_client *i2c_client,
+	const struct i2c_device_id *id)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
+	struct cs42l51_private *cs42l51;
+	int ret;
 
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
+	/* Verify that we have a CS42L51 */
+	ret = i2c_smbus_read_byte_data(i2c_client, CS42L51_CHIP_REV_ID);
+	if (ret < 0) {
+		dev_err(&i2c_client->dev, "failed to read I2C\n");
+		goto error;
+	}
+
+	if ((ret != CS42L51_MK_CHIP_REV(CS42L51_CHIP_ID, CS42L51_CHIP_REV_A)) &&
+	    (ret != CS42L51_MK_CHIP_REV(CS42L51_CHIP_ID, CS42L51_CHIP_REV_B))) {
+		dev_err(&i2c_client->dev, "Invalid chip id\n");
+		ret = -ENODEV;
+		goto error;
+	}
+
+	dev_info(&i2c_client->dev, "found device cs42l51 rev %d\n",
+				ret & 7);
+
+	cs42l51 = kzalloc(sizeof(struct cs42l51_private), GFP_KERNEL);
+	if (!cs42l51) {
+		dev_err(&i2c_client->dev, "could not allocate codec\n");
+		return -ENOMEM;
+	}
+
+	i2c_set_clientdata(i2c_client, cs42l51);
+	cs42l51->control_data = i2c_client;
+	cs42l51->control_type = SND_SOC_I2C;
 
+	ret =  snd_soc_register_codec(&i2c_client->dev,
+			&soc_codec_device_cs42l51, &cs42l51_dai, 1);
+	if (ret < 0)
+		kfree(cs42l51);
+error:
+	return ret;
+}
+
+static int cs42l51_i2c_remove(struct i2c_client *client)
+{
+	struct cs42l51_private *cs42l51 = i2c_get_clientdata(client);
+
+	snd_soc_unregister_codec(&client->dev);
+	kfree(cs42l51);
 	return 0;
 }
 
-struct snd_soc_codec_device soc_codec_device_cs42l51 = {
-	.probe =	cs42l51_probe,
-	.remove =	cs42l51_remove
+static const struct i2c_device_id cs42l51_id[] = {
+	{"cs42l51", 0},
+	{}
+};
+MODULE_DEVICE_TABLE(i2c, cs42l51_id);
+
+static struct i2c_driver cs42l51_i2c_driver = {
+	.driver = {
+		.name = "cs42L51-codec",
+		.owner = THIS_MODULE,
+	},
+	.id_table = cs42l51_id,
+	.probe = cs42l51_i2c_probe,
+	.remove = cs42l51_i2c_remove,
 };
-EXPORT_SYMBOL_GPL(soc_codec_device_cs42l51);
 
 static int __init cs42l51_init(void)
 {

+ 0 - 2
sound/soc/codecs/cs42l51.h

@@ -158,6 +158,4 @@
 #define CS42L51_LASTREG		0x20
 #define CS42L51_NUMREGS		(CS42L51_LASTREG - CS42L51_FIRSTREG + 1)
 
-extern struct snd_soc_dai cs42l51_dai;
-extern struct snd_soc_codec_device soc_codec_device_cs42l51;
 #endif

+ 49 - 124
sound/soc/codecs/cx20442.c

@@ -24,7 +24,8 @@
 
 
 struct cx20442_priv {
-	struct snd_soc_codec codec;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 	u8 reg_cache[1];
 };
 
@@ -102,7 +103,7 @@ static unsigned int cx20442_read_reg_cache(struct snd_soc_codec *codec,
 {
 	u8 *reg_cache = codec->reg_cache;
 
-	if (reg >= codec->reg_cache_size)
+	if (reg >= codec->driver->reg_cache_size)
 		return -EINVAL;
 
 	return reg_cache[reg];
@@ -164,16 +165,17 @@ static int cx20442_pm_to_v253_vsp(u8 value)
 static int cx20442_write(struct snd_soc_codec *codec, unsigned int reg,
 							unsigned int value)
 {
+	struct cx20442_priv *cx20442 = snd_soc_codec_get_drvdata(codec);
 	u8 *reg_cache = codec->reg_cache;
 	int vls, vsp, old, len;
 	char buf[18];
 
-	if (reg >= codec->reg_cache_size)
+	if (reg >= codec->driver->reg_cache_size)
 		return -EINVAL;
 
 	/* hw_write and control_data pointers required for talking to the modem
 	 * are expected to be set by the line discipline initialization code */
-	if (!codec->hw_write || !codec->control_data)
+	if (!codec->hw_write || !cx20442->control_data)
 		return -EIO;
 
 	old = reg_cache[reg];
@@ -202,17 +204,13 @@ static int cx20442_write(struct snd_soc_codec *codec, unsigned int reg,
 		return -ENOMEM;
 
 	dev_dbg(codec->dev, "%s: %s\n", __func__, buf);
-	if (codec->hw_write(codec->control_data, buf, len) != len)
+	if (codec->hw_write(cx20442->control_data, buf, len) != len)
 		return -EIO;
 
 	return 0;
 }
 
 
-/* Moved up here as line discipline referres it during initialization */
-static struct snd_soc_codec *cx20442_codec;
-
-
 /*
  * Line discpline related code
  *
@@ -228,15 +226,15 @@ static const char *v253_init = "ate0m0q0+fclass=8\r";
 /* Line discipline .open() */
 static int v253_open(struct tty_struct *tty)
 {
-	struct snd_soc_codec *codec = cx20442_codec;
 	int ret, len = strlen(v253_init);
 
 	/* Doesn't make sense without write callback */
 	if (!tty->ops->write)
 		return -EINVAL;
 
-	/* Pass the codec structure address for use by other ldisc callbacks */
-	tty->disc_data = codec;
+	/* Won't work if no codec pointer has been passed by a card driver */
+	if (!tty->disc_data)
+		return -ENODEV;
 
 	if (tty->ops->write(tty, v253_init, len) != len) {
 		ret = -EIO;
@@ -253,15 +251,18 @@ err:
 static void v253_close(struct tty_struct *tty)
 {
 	struct snd_soc_codec *codec = tty->disc_data;
+	struct cx20442_priv *cx20442;
 
 	tty->disc_data = NULL;
 
 	if (!codec)
 		return;
 
+	cx20442 = snd_soc_codec_get_drvdata(codec);
+
 	/* Prevent the codec driver from further accessing the modem */
 	codec->hw_write = NULL;
-	codec->control_data = NULL;
+	cx20442->control_data = NULL;
 	codec->pop_time = 0;
 }
 
@@ -277,15 +278,18 @@ static void v253_receive(struct tty_struct *tty,
 				const unsigned char *cp, char *fp, int count)
 {
 	struct snd_soc_codec *codec = tty->disc_data;
+	struct cx20442_priv *cx20442;
 
 	if (!codec)
 		return;
 
-	if (!codec->control_data) {
+	cx20442 = snd_soc_codec_get_drvdata(codec);
+
+	if (!cx20442->control_data) {
 		/* First modem response, complete setup procedure */
 
 		/* Set up codec driver access to modem controls */
-		codec->control_data = tty;
+		cx20442->control_data = tty;
 		codec->hw_write = (hw_write_t)tty->ops->write;
 		codec->pop_time = 1;
 	}
@@ -313,8 +317,8 @@ EXPORT_SYMBOL_GPL(v253_ops);
  * Codec DAI
  */
 
-struct snd_soc_dai cx20442_dai = {
-	.name = "CX20442",
+static struct snd_soc_dai_driver cx20442_dai = {
+	.name = "cx20442-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 1,
@@ -330,142 +334,63 @@ struct snd_soc_dai cx20442_dai = {
 		.formats = SNDRV_PCM_FMTBIT_S16_LE,
 	},
 };
-EXPORT_SYMBOL_GPL(cx20442_dai);
 
-static int cx20442_codec_probe(struct platform_device *pdev)
+static int cx20442_codec_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret;
-
-	if (!cx20442_codec) {
-		dev_err(&pdev->dev, "cx20442 not yet discovered\n");
-		return -ENODEV;
-	}
-	codec = cx20442_codec;
-
-	socdev->card->codec = codec;
+	struct cx20442_priv *cx20442;
 
-	/* register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		dev_err(&pdev->dev, "failed to create pcms\n");
-		goto pcm_err;
-	}
+	cx20442 = kzalloc(sizeof(struct cx20442_priv), GFP_KERNEL);
+	if (cx20442 == NULL)
+		return -ENOMEM;
+	snd_soc_codec_set_drvdata(codec, cx20442);
 
 	cx20442_add_widgets(codec);
 
-pcm_err:
-	return ret;
+	cx20442->control_data = NULL;
+	codec->hw_write = NULL;
+	codec->pop_time = 0;
+
+	return 0;
 }
 
 /* power down chip */
-static int cx20442_codec_remove(struct platform_device *pdev)
+static int cx20442_codec_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
+	struct cx20442_priv *cx20442 = snd_soc_codec_get_drvdata(codec);
 
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
+	if (cx20442->control_data) {
+			struct tty_struct *tty = cx20442->control_data;
+			tty_hangup(tty);
+	}
 
+	kfree(cx20442);
 	return 0;
 }
 
-struct snd_soc_codec_device cx20442_codec_dev = {
+static struct snd_soc_codec_driver cx20442_codec_dev = {
 	.probe = 	cx20442_codec_probe,
 	.remove = 	cx20442_codec_remove,
+	.reg_cache_size = 1,
+	.reg_word_size = sizeof(u8),
+	.read = cx20442_read_reg_cache,
+	.write = cx20442_write,
 };
-EXPORT_SYMBOL_GPL(cx20442_codec_dev);
-
-static int cx20442_register(struct cx20442_priv *cx20442)
-{
-	struct snd_soc_codec *codec = &cx20442->codec;
-	int ret;
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	codec->name = "CX20442";
-	codec->owner = THIS_MODULE;
-	snd_soc_codec_set_drvdata(codec, cx20442);
-
-	codec->dai = &cx20442_dai;
-	codec->num_dai = 1;
-
-	codec->reg_cache = &cx20442->reg_cache;
-	codec->reg_cache_size = ARRAY_SIZE(cx20442->reg_cache);
-	codec->read = cx20442_read_reg_cache;
-	codec->write = cx20442_write;
-
-	codec->bias_level = SND_SOC_BIAS_OFF;
-
-	cx20442_dai.dev = codec->dev;
-
-	cx20442_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register codec: %d\n", ret);
-		goto err;
-	}
-
-	ret = snd_soc_register_dai(&cx20442_dai);
-	if (ret != 0) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		goto err_codec;
-	}
-
-	return 0;
-
-err_codec:
-	snd_soc_unregister_codec(codec);
-err:
-	cx20442_codec = NULL;
-	kfree(cx20442);
-	return ret;
-}
-
-static void cx20442_unregister(struct cx20442_priv *cx20442)
-{
-	snd_soc_unregister_dai(&cx20442_dai);
-	snd_soc_unregister_codec(&cx20442->codec);
-
-	cx20442_codec = NULL;
-	kfree(cx20442);
-}
 
 static int cx20442_platform_probe(struct platform_device *pdev)
 {
-	struct cx20442_priv *cx20442;
-	struct snd_soc_codec *codec;
-
-	cx20442 = kzalloc(sizeof(struct cx20442_priv), GFP_KERNEL);
-	if (cx20442 == NULL)
-		return -ENOMEM;
-
-	codec = &cx20442->codec;
-
-	codec->control_data = NULL;
-	codec->hw_write = NULL;
-	codec->pop_time = 0;
-
-	codec->dev = &pdev->dev;
-	platform_set_drvdata(pdev, cx20442);
-
-	return cx20442_register(cx20442);
+	return snd_soc_register_codec(&pdev->dev,
+			&cx20442_codec_dev, &cx20442_dai, 1);
 }
 
 static int __exit cx20442_platform_remove(struct platform_device *pdev)
 {
-	struct cx20442_priv *cx20442 = platform_get_drvdata(pdev);
-
-	cx20442_unregister(cx20442);
+	snd_soc_unregister_codec(&pdev->dev);
 	return 0;
 }
 
 static struct platform_driver cx20442_platform_driver = {
 	.driver = {
-		.name = "cx20442",
+		.name = "cx20442-codec",
 		.owner = THIS_MODULE,
 		},
 	.probe = cx20442_platform_probe,
@@ -487,4 +412,4 @@ module_exit(cx20442_exit);
 MODULE_DESCRIPTION("ASoC CX20442-11 voice modem codec driver");
 MODULE_AUTHOR("Janusz Krzysztofik");
 MODULE_LICENSE("GPL");
-MODULE_ALIAS("platform:cx20442");
+MODULE_ALIAS("platform:cx20442-codec");

+ 0 - 2
sound/soc/codecs/cx20442.h

@@ -13,8 +13,6 @@
 #ifndef _CX20442_CODEC_H
 #define _CX20442_CODEC_H
 
-extern struct snd_soc_dai cx20442_dai;
-extern struct snd_soc_codec_device cx20442_codec_dev;
 extern struct tty_ldisc_ops v253_ops;
 
 #endif

+ 32 - 125
sound/soc/codecs/da7210.c

@@ -25,8 +25,6 @@
 #include <sound/initval.h>
 #include <sound/tlv.h>
 
-#include "da7210.h"
-
 /* DA7210 register space */
 #define DA7210_STATUS			0x02
 #define DA7210_STARTUP1			0x03
@@ -162,11 +160,10 @@ static const struct snd_kcontrol_new da7210_snd_controls[] = {
 
 /* Codec private data */
 struct da7210_priv {
-	struct snd_soc_codec codec;
+	enum snd_soc_control_type control_type;
+	void *control_data;
 };
 
-static struct snd_soc_codec *da7210_codec;
-
 /*
  * Register cache
  */
@@ -209,12 +206,12 @@ static int da7210_write(struct snd_soc_codec *codec, u32 reg, u32 value)
 	u8 *cache = codec->reg_cache;
 	u8 data[2];
 
-	BUG_ON(codec->volatile_register);
+	BUG_ON(codec->driver->volatile_register);
 
 	data[0] = reg & 0xff;
 	data[1] = value & 0xff;
 
-	if (reg >= codec->reg_cache_size)
+	if (reg >= codec->driver->reg_cache_size)
 		return -EIO;
 
 	if (2 != codec->hw_write(codec->control_data, data, 2))
@@ -267,8 +264,7 @@ static int da7210_hw_params(struct snd_pcm_substream *substream,
 			    struct snd_soc_dai *dai)
 {
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec = rtd->codec;
 	u32 dai_cfg1;
 	u32 hpf_reg, hpf_mask, hpf_value;
 	u32 fs, bypass;
@@ -430,9 +426,8 @@ static struct snd_soc_dai_ops da7210_dai_ops = {
 	.set_fmt	= da7210_set_dai_fmt,
 };
 
-struct snd_soc_dai da7210_dai = {
-	.name = "DA7210 IIS",
-	.id = 0,
+static struct snd_soc_dai_driver da7210_dai = {
+	.name = "da7210-hifi",
 	/* playback capabilities */
 	.playback = {
 		.stream_name = "Playback",
@@ -452,55 +447,15 @@ struct snd_soc_dai da7210_dai = {
 	.ops = &da7210_dai_ops,
 	.symmetric_rates = 1,
 };
-EXPORT_SYMBOL_GPL(da7210_dai);
 
-/*
- * Initialize the DA7210 driver
- * register the mixer and dsp interfaces with the kernel
- */
-static int da7210_init(struct da7210_priv *da7210)
+static int da7210_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_codec *codec = &da7210->codec;
-	int ret = 0;
+	struct da7210_priv *da7210 = snd_soc_codec_get_drvdata(codec);
 
-	if (da7210_codec) {
-		dev_err(codec->dev, "Another da7210 is registered\n");
-		return -EINVAL;
-	}
+	dev_info(codec->dev, "DA7210 Audio Codec %s\n", DA7210_VERSION);
 
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	snd_soc_codec_set_drvdata(codec, da7210);
-	codec->name		= "DA7210";
-	codec->owner		= THIS_MODULE;
-	codec->read		= da7210_read;
-	codec->write		= da7210_write;
-	codec->dai		= &da7210_dai;
-	codec->num_dai		= 1;
+	codec->control_data = da7210->control_data;
 	codec->hw_write		= (hw_write_t)i2c_master_send;
-	codec->reg_cache_size	= ARRAY_SIZE(da7210_reg);
-	codec->reg_cache	= kmemdup(da7210_reg,
-					  sizeof(da7210_reg), GFP_KERNEL);
-
-	if (!codec->reg_cache)
-		return -ENOMEM;
-
-	da7210_dai.dev = codec->dev;
-	da7210_codec = codec;
-
-	ret = snd_soc_register_codec(codec);
-	if (ret) {
-		dev_err(codec->dev, "Failed to register CODEC: %d\n", ret);
-		goto init_err;
-	}
-
-	ret = snd_soc_register_dai(&da7210_dai);
-	if (ret) {
-		dev_err(codec->dev, "Failed to register DAI: %d\n", ret);
-		goto codec_err;
-	}
 
 	/* FIXME
 	 *
@@ -583,54 +538,50 @@ static int da7210_init(struct da7210_priv *da7210)
 	/* Activate all enabled subsystem */
 	da7210_write(codec, DA7210_STARTUP1, DA7210_SC_MST_EN);
 
-	return ret;
-
-codec_err:
-	snd_soc_unregister_codec(codec);
-init_err:
-	kfree(codec->reg_cache);
-	codec->reg_cache = NULL;
+	snd_soc_add_controls(codec, da7210_snd_controls,
+			     ARRAY_SIZE(da7210_snd_controls));
 
-	return ret;
+	dev_info(codec->dev, "DA7210 Audio Codec %s\n", DA7210_VERSION);
 
+	return 0;
 }
 
+static struct snd_soc_codec_driver soc_codec_dev_da7210 = {
+	.probe =	da7210_probe,
+	.read		= da7210_read,
+	.write		= da7210_write,
+	.reg_cache_size	= ARRAY_SIZE(da7210_reg),
+	.reg_word_size = sizeof(u8),
+	.reg_cache_default	= da7210_reg,
+};
+
 #if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
 static int __devinit da7210_i2c_probe(struct i2c_client *i2c,
 			   	      const struct i2c_device_id *id)
 {
 	struct da7210_priv *da7210;
-	struct snd_soc_codec *codec;
 	int ret;
 
 	da7210 = kzalloc(sizeof(struct da7210_priv), GFP_KERNEL);
 	if (!da7210)
 		return -ENOMEM;
 
-	codec = &da7210->codec;
-	codec->dev = &i2c->dev;
-
 	i2c_set_clientdata(i2c, da7210);
-	codec->control_data = i2c;
+	da7210->control_data = i2c;
+	da7210->control_type = SND_SOC_I2C;
 
-	ret = da7210_init(da7210);
-	if (ret < 0) {
-		pr_err("Failed to initialise da7210 audio codec\n");
+	ret =  snd_soc_register_codec(&i2c->dev,
+			&soc_codec_dev_da7210, &da7210_dai, 1);
+	if (ret < 0)
 		kfree(da7210);
-	}
 
 	return ret;
 }
 
 static int __devexit da7210_i2c_remove(struct i2c_client *client)
 {
-	struct da7210_priv *da7210 = i2c_get_clientdata(client);
-
-	snd_soc_unregister_dai(&da7210_dai);
-	kfree(da7210->codec.reg_cache);
-	kfree(da7210);
-	da7210_codec = NULL;
-
+	snd_soc_unregister_codec(&client->dev);
+	kfree(i2c_get_clientdata(client));
 	return 0;
 }
 
@@ -643,7 +594,7 @@ MODULE_DEVICE_TABLE(i2c, da7210_i2c_id);
 /* I2C codec control layer */
 static struct i2c_driver da7210_i2c_driver = {
 	.driver = {
-		.name = "DA7210 I2C Codec",
+		.name = "da7210-codec",
 		.owner = THIS_MODULE,
 	},
 	.probe = da7210_i2c_probe,
@@ -652,50 +603,6 @@ static struct i2c_driver da7210_i2c_driver = {
 };
 #endif
 
-static int da7210_probe(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	int ret;
-
-	if (!da7210_codec) {
-		dev_err(&pdev->dev, "Codec device not registered\n");
-		return -ENODEV;
-	}
-
-	socdev->card->codec = da7210_codec;
-	codec = da7210_codec;
-
-	/* Register pcms */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0)
-		goto pcm_err;
-
-	snd_soc_add_controls(da7210_codec, da7210_snd_controls,
-			     ARRAY_SIZE(da7210_snd_controls));
-
-	dev_info(&pdev->dev, "DA7210 Audio Codec %s\n", DA7210_VERSION);
-
-pcm_err:
-	return ret;
-}
-
-static int da7210_remove(struct platform_device *pdev)
-{
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
-
-	return 0;
-}
-
-struct snd_soc_codec_device soc_codec_dev_da7210 = {
-	.probe =	da7210_probe,
-	.remove =	da7210_remove,
-};
-EXPORT_SYMBOL_GPL(soc_codec_dev_da7210);
-
 static int __init da7210_modinit(void)
 {
 	int ret = 0;

+ 0 - 24
sound/soc/codecs/da7210.h

@@ -1,24 +0,0 @@
-/*
- * da7210.h  --  audio driver for da7210
- *
- * Copyright (c) 2009 Dialog Semiconductor
- * Written by David Chen <Dajun.chen@diasemi.com>
- *
- * Copyright (C) 2009 Renesas Solutions Corp.
- * Cleanups by Kuninori Morimoto <morimoto.kuninori@renesas.com>
- *
- * This program is free software; you can redistribute  it and/or modify it
- * under  the terms of  the GNU General  Public License as published by the
- * Free Software Foundation;  either version 2 of the  License, or (at your
- * option) any later version.
- *
- */
-
-#ifndef _DA7210_H
-#define _DA7210_H
-
-extern struct snd_soc_dai da7210_dai;
-extern struct snd_soc_codec_device soc_codec_dev_da7210;
-
-#endif
-

+ 26 - 90
sound/soc/codecs/jz4740.c

@@ -74,29 +74,22 @@ static const uint32_t jz4740_codec_regs[] = {
 struct jz4740_codec {
 	void __iomem *base;
 	struct resource *mem;
-
-	uint32_t reg_cache[2];
-	struct snd_soc_codec codec;
 };
 
-static inline struct jz4740_codec *codec_to_jz4740(struct snd_soc_codec *codec)
-{
-	return container_of(codec, struct jz4740_codec, codec);
-}
-
 static unsigned int jz4740_codec_read(struct snd_soc_codec *codec,
 	unsigned int reg)
 {
-	struct jz4740_codec *jz4740_codec = codec_to_jz4740(codec);
+	struct jz4740_codec *jz4740_codec = snd_soc_codec_get_drvdata(codec);
 	return readl(jz4740_codec->base + (reg << 2));
 }
 
 static int jz4740_codec_write(struct snd_soc_codec *codec, unsigned int reg,
 	unsigned int val)
 {
-	struct jz4740_codec *jz4740_codec = codec_to_jz4740(codec);
+	struct jz4740_codec *jz4740_codec = snd_soc_codec_get_drvdata(codec);
+	u32 *cache = codec->reg_cache;
 
-	jz4740_codec->reg_cache[reg] = val;
+	cache[reg] = val;
 	writel(val, jz4740_codec->base + (reg << 2));
 
 	return 0;
@@ -172,8 +165,7 @@ static int jz4740_codec_hw_params(struct snd_pcm_substream *substream,
 {
 	uint32_t val;
 	struct snd_soc_pcm_runtime *rtd = substream->private_data;
-	struct snd_soc_device *socdev = rtd->socdev;
-	struct snd_soc_codec *codec = socdev->card->codec;
+	struct snd_soc_codec *codec =rtd->codec;
 
 	switch (params_rate(params)) {
 	case 8000:
@@ -219,8 +211,8 @@ static struct snd_soc_dai_ops jz4740_codec_dai_ops = {
 	.hw_params = jz4740_codec_hw_params,
 };
 
-struct snd_soc_dai jz4740_codec_dai = {
-	.name = "jz4740",
+static struct snd_soc_dai_driver jz4740_codec_dai = {
+	.name = "jz4740-hifi",
 	.playback = {
 		.stream_name = "Playback",
 		.channels_min = 2,
@@ -238,7 +230,6 @@ struct snd_soc_dai jz4740_codec_dai = {
 	.ops = &jz4740_codec_dai_ops,
 	.symmetric_rates = 1,
 };
-EXPORT_SYMBOL_GPL(jz4740_codec_dai);
 
 static void jz4740_codec_wakeup(struct snd_soc_codec *codec)
 {
@@ -302,23 +293,10 @@ static int jz4740_codec_set_bias_level(struct snd_soc_codec *codec,
 	return 0;
 }
 
-static struct snd_soc_codec *jz4740_codec_codec;
-
-static int jz4740_codec_dev_probe(struct platform_device *pdev)
+static int jz4740_codec_dev_probe(struct snd_soc_codec *codec)
 {
-	int ret;
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = jz4740_codec_codec;
-
-	BUG_ON(!codec);
-
-	socdev->card->codec = codec;
-
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret) {
-		dev_err(&pdev->dev, "Failed to create pcms: %d\n", ret);
-		return ret;
-	}
+	snd_soc_update_bits(codec, JZ4740_REG_CODEC_1,
+			JZ4740_CODEC_1_SW2_ENABLE, JZ4740_CODEC_1_SW2_ENABLE);
 
 	snd_soc_add_controls(codec, jz4740_codec_controls,
 		ARRAY_SIZE(jz4740_codec_controls));
@@ -331,34 +309,27 @@ static int jz4740_codec_dev_probe(struct platform_device *pdev)
 
 	snd_soc_dapm_new_widgets(codec);
 
+	jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
+
 	return 0;
 }
 
-static int jz4740_codec_dev_remove(struct platform_device *pdev)
+static int jz4740_codec_dev_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-
-	snd_soc_free_pcms(socdev);
-	snd_soc_dapm_free(socdev);
+	jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_OFF);
 
 	return 0;
 }
 
 #ifdef CONFIG_PM_SLEEP
 
-static int jz4740_codec_suspend(struct platform_device *pdev, pm_message_t state)
+static int jz4740_codec_suspend(struct snd_soc_codec *codec, pm_message_t state)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	return jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_OFF);
 }
 
-static int jz4740_codec_resume(struct platform_device *pdev)
+static int jz4740_codec_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-
 	return jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
 }
 
@@ -367,19 +338,23 @@ static int jz4740_codec_resume(struct platform_device *pdev)
 #define jz4740_codec_resume NULL
 #endif
 
-struct snd_soc_codec_device soc_codec_dev_jz4740_codec = {
+static struct snd_soc_codec_driver soc_codec_dev_jz4740_codec = {
 	.probe = jz4740_codec_dev_probe,
 	.remove = jz4740_codec_dev_remove,
 	.suspend = jz4740_codec_suspend,
 	.resume = jz4740_codec_resume,
+	.read = jz4740_codec_read,
+	.write = jz4740_codec_write,
+	.set_bias_level = jz4740_codec_set_bias_level,
+	.reg_cache_default	= jz4740_codec_regs,
+	.reg_word_size = sizeof(u32),
+	.reg_cache_size	= 2,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_jz4740_codec);
 
 static int __devinit jz4740_codec_probe(struct platform_device *pdev)
 {
 	int ret;
 	struct jz4740_codec *jz4740_codec;
-	struct snd_soc_codec *codec;
 	struct resource *mem;
 
 	jz4740_codec = kzalloc(sizeof(*jz4740_codec), GFP_KERNEL);
@@ -408,55 +383,17 @@ static int __devinit jz4740_codec_probe(struct platform_device *pdev)
 	}
 	jz4740_codec->mem = mem;
 
-	jz4740_codec_dai.dev = &pdev->dev;
-
-	codec = &jz4740_codec->codec;
-
-	codec->dev		= &pdev->dev;
-	codec->name		= "jz4740";
-	codec->owner		= THIS_MODULE;
-
-	codec->read		= jz4740_codec_read;
-	codec->write		= jz4740_codec_write;
-	codec->set_bias_level	= jz4740_codec_set_bias_level;
-	codec->bias_level	= SND_SOC_BIAS_OFF;
-
-	codec->dai		= &jz4740_codec_dai;
-	codec->num_dai		= 1;
-
-	codec->reg_cache	= jz4740_codec->reg_cache;
-	codec->reg_cache_size	= 2;
-	memcpy(codec->reg_cache, jz4740_codec_regs, sizeof(jz4740_codec_regs));
-
-	mutex_init(&codec->mutex);
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	jz4740_codec_codec = codec;
-
-	snd_soc_update_bits(codec, JZ4740_REG_CODEC_1,
-			JZ4740_CODEC_1_SW2_ENABLE, JZ4740_CODEC_1_SW2_ENABLE);
-
 	platform_set_drvdata(pdev, jz4740_codec);
 
-	ret = snd_soc_register_codec(codec);
+	ret = snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_jz4740_codec, &jz4740_codec_dai, 1);
 	if (ret) {
 		dev_err(&pdev->dev, "Failed to register codec\n");
 		goto err_iounmap;
 	}
 
-	ret = snd_soc_register_dai(&jz4740_codec_dai);
-	if (ret) {
-		dev_err(&pdev->dev, "Failed to register codec dai\n");
-		goto err_unregister_codec;
-	}
-
-	jz4740_codec_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
-
 	return 0;
 
-err_unregister_codec:
-	snd_soc_unregister_codec(codec);
 err_iounmap:
 	iounmap(jz4740_codec->base);
 err_release_mem_region:
@@ -472,8 +409,7 @@ static int __devexit jz4740_codec_remove(struct platform_device *pdev)
 	struct jz4740_codec *jz4740_codec = platform_get_drvdata(pdev);
 	struct resource *mem = jz4740_codec->mem;
 
-	snd_soc_unregister_dai(&jz4740_codec_dai);
-	snd_soc_unregister_codec(&jz4740_codec->codec);
+	snd_soc_unregister_codec(&pdev->dev);
 
 	iounmap(jz4740_codec->base);
 	release_mem_region(mem->start, resource_size(mem));

+ 0 - 20
sound/soc/codecs/jz4740.h

@@ -1,20 +0,0 @@
-/*
- * Copyright (C) 2009, Lars-Peter Clausen <lars@metafoo.de>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- *
- *  You should have received a copy of the  GNU General Public License along
- *  with this program; if not, write  to the Free Software Foundation, Inc.,
- *  675 Mass Ave, Cambridge, MA 02139, USA.
- *
- */
-
-#ifndef __SND_SOC_CODECS_JZ4740_CODEC_H__
-#define __SND_SOC_CODECS_JZ4740_CODEC_H__
-
-extern struct snd_soc_dai jz4740_codec_dai;
-extern struct snd_soc_codec_device soc_codec_dev_jz4740_codec;
-
-#endif

+ 38 - 54
sound/soc/codecs/pcm3008.c

@@ -32,8 +32,8 @@
 #define PCM3008_RATES (SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_44100 |	\
 		       SNDRV_PCM_RATE_48000)
 
-struct snd_soc_dai pcm3008_dai = {
-	.name = "PCM3008 HiFi",
+static struct snd_soc_dai_driver pcm3008_dai = {
+	.name = "pcm3008-hifi",
 	.playback = {
 		.stream_name = "PCM3008 Playback",
 		.channels_min = 1,
@@ -49,7 +49,6 @@ struct snd_soc_dai pcm3008_dai = {
 		.formats = SNDRV_PCM_FMTBIT_S16_LE,
 	},
 };
-EXPORT_SYMBOL_GPL(pcm3008_dai);
 
 static void pcm3008_gpio_free(struct pcm3008_setup_data *setup)
 {
@@ -59,38 +58,13 @@ static void pcm3008_gpio_free(struct pcm3008_setup_data *setup)
 	gpio_free(setup->pdda_pin);
 }
 
-static int pcm3008_soc_probe(struct platform_device *pdev)
+static int pcm3008_soc_probe(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec;
-	struct pcm3008_setup_data *setup = socdev->codec_data;
+	struct pcm3008_setup_data *setup = codec->dev->platform_data;
 	int ret = 0;
 
 	printk(KERN_INFO "PCM3008 SoC Audio Codec %s\n", PCM3008_VERSION);
 
-	socdev->card->codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL);
-	if (!socdev->card->codec)
-		return -ENOMEM;
-
-	codec = socdev->card->codec;
-	mutex_init(&codec->mutex);
-
-	codec->name = "PCM3008";
-	codec->owner = THIS_MODULE;
-	codec->dai = &pcm3008_dai;
-	codec->num_dai = 1;
-	codec->write = NULL;
-	codec->read = NULL;
-	INIT_LIST_HEAD(&codec->dapm_widgets);
-	INIT_LIST_HEAD(&codec->dapm_paths);
-
-	/* Register PCMs. */
-	ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1);
-	if (ret < 0) {
-		printk(KERN_ERR "pcm3008: failed to create pcms\n");
-		goto pcm_err;
-	}
-
 	/* DEM1  DEM0  DE-EMPHASIS_MODE
 	 * Low   Low   De-emphasis 44.1 kHz ON
 	 * Low   High  De-emphasis OFF
@@ -130,33 +104,22 @@ static int pcm3008_soc_probe(struct platform_device *pdev)
 
 gpio_err:
 	pcm3008_gpio_free(setup);
-pcm_err:
-	kfree(socdev->card->codec);
 
 	return ret;
 }
 
-static int pcm3008_soc_remove(struct platform_device *pdev)
+static int pcm3008_soc_remove(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct snd_soc_codec *codec = socdev->card->codec;
-	struct pcm3008_setup_data *setup = socdev->codec_data;
-
-	if (!codec)
-		return 0;
+	struct pcm3008_setup_data *setup = codec->dev->platform_data;
 
 	pcm3008_gpio_free(setup);
-	snd_soc_free_pcms(socdev);
-	kfree(socdev->card->codec);
-
 	return 0;
 }
 
 #ifdef CONFIG_PM
-static int pcm3008_soc_suspend(struct platform_device *pdev, pm_message_t msg)
+static int pcm3008_soc_suspend(struct snd_soc_codec *codec, pm_message_t msg)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct pcm3008_setup_data *setup = socdev->codec_data;
+	struct pcm3008_setup_data *setup = codec->dev->platform_data;
 
 	gpio_set_value(setup->pdad_pin, 0);
 	gpio_set_value(setup->pdda_pin, 0);
@@ -164,10 +127,9 @@ static int pcm3008_soc_suspend(struct platform_device *pdev, pm_message_t msg)
 	return 0;
 }
 
-static int pcm3008_soc_resume(struct platform_device *pdev)
+static int pcm3008_soc_resume(struct snd_soc_codec *codec)
 {
-	struct snd_soc_device *socdev = platform_get_drvdata(pdev);
-	struct pcm3008_setup_data *setup = socdev->codec_data;
+	struct pcm3008_setup_data *setup = codec->dev->platform_data;
 
 	gpio_set_value(setup->pdad_pin, 1);
 	gpio_set_value(setup->pdda_pin, 1);
@@ -179,23 +141,45 @@ static int pcm3008_soc_resume(struct platform_device *pdev)
 #define pcm3008_soc_resume NULL
 #endif
 
-struct snd_soc_codec_device soc_codec_dev_pcm3008 = {
+static struct snd_soc_codec_driver soc_codec_dev_pcm3008 = {
 	.probe = 	pcm3008_soc_probe,
 	.remove = 	pcm3008_soc_remove,
 	.suspend =	pcm3008_soc_suspend,
 	.resume =	pcm3008_soc_resume,
 };
-EXPORT_SYMBOL_GPL(soc_codec_dev_pcm3008);
 
-static int __init pcm3008_init(void)
+static int __devinit pcm3008_codec_probe(struct platform_device *pdev)
+{
+	return snd_soc_register_codec(&pdev->dev,
+			&soc_codec_dev_pcm3008, &pcm3008_dai, 1);
+}
+
+static int __devexit pcm3008_codec_remove(struct platform_device *pdev)
+{
+	snd_soc_unregister_codec(&pdev->dev);
+	return 0;
+}
+
+MODULE_ALIAS("platform:pcm3008-codec");
+
+static struct platform_driver pcm3008_codec_driver = {
+	.probe		= pcm3008_codec_probe,
+	.remove		= __devexit_p(pcm3008_codec_remove),
+	.driver		= {
+		.name	= "pcm3008-codec",
+		.owner	= THIS_MODULE,
+	},
+};
+
+static int __init pcm3008_modinit(void)
 {
-	return snd_soc_register_dai(&pcm3008_dai);
+	return platform_driver_register(&pcm3008_codec_driver);
 }
-module_init(pcm3008_init);
+module_init(pcm3008_modinit);
 
 static void __exit pcm3008_exit(void)
 {
-	snd_soc_unregister_dai(&pcm3008_dai);
+	platform_driver_unregister(&pcm3008_codec_driver);
 }
 module_exit(pcm3008_exit);
 

+ 0 - 3
sound/soc/codecs/pcm3008.h

@@ -19,7 +19,4 @@ struct pcm3008_setup_data {
 	unsigned pdda_pin;
 };
 
-extern struct snd_soc_codec_device soc_codec_dev_pcm3008;
-extern struct snd_soc_dai pcm3008_dai;
-
 #endif

برخی فایل ها در این مقایسه diff نمایش داده نمی شوند زیرا تعداد فایل ها بسیار زیاد است