diff options
author | Sascha Hauer <s.hauer@pengutronix.de> | 2010-02-09 05:04:36 -0500 |
---|---|---|
committer | Sascha Hauer <s.hauer@pengutronix.de> | 2010-02-10 05:05:23 -0500 |
commit | d2831d1f543489ef97a20e6e65f625e195b521bf (patch) | |
tree | 707886f8f8b764d5fbed12f00a216d25a8831aad /arch/arm/mach-mx3/mach-pcm043.c | |
parent | c8a6885f2153087668b64d4ee25f78a7dda1dadb (diff) |
i.MX pcm043: Add AC97 sound support
Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
Diffstat (limited to 'arch/arm/mach-mx3/mach-pcm043.c')
-rw-r--r-- | arch/arm/mach-mx3/mach-pcm043.c | 101 |
1 files changed, 101 insertions, 0 deletions
diff --git a/arch/arm/mach-mx3/mach-pcm043.c b/arch/arm/mach-mx3/mach-pcm043.c index a9741c2b379f..1bf1ec2eef5e 100644 --- a/arch/arm/mach-mx3/mach-pcm043.c +++ b/arch/arm/mach-mx3/mach-pcm043.c | |||
@@ -26,6 +26,7 @@ | |||
26 | #include <linux/gpio.h> | 26 | #include <linux/gpio.h> |
27 | #include <linux/smc911x.h> | 27 | #include <linux/smc911x.h> |
28 | #include <linux/interrupt.h> | 28 | #include <linux/interrupt.h> |
29 | #include <linux/delay.h> | ||
29 | #include <linux/i2c.h> | 30 | #include <linux/i2c.h> |
30 | #include <linux/i2c/at24.h> | 31 | #include <linux/i2c/at24.h> |
31 | #include <linux/usb/otg.h> | 32 | #include <linux/usb/otg.h> |
@@ -49,6 +50,8 @@ | |||
49 | #include <mach/mxc_nand.h> | 50 | #include <mach/mxc_nand.h> |
50 | #include <mach/mxc_ehci.h> | 51 | #include <mach/mxc_ehci.h> |
51 | #include <mach/ulpi.h> | 52 | #include <mach/ulpi.h> |
53 | #include <mach/audmux.h> | ||
54 | #include <mach/ssi.h> | ||
52 | 55 | ||
53 | #include "devices.h" | 56 | #include "devices.h" |
54 | 57 | ||
@@ -213,6 +216,91 @@ static struct pad_desc pcm043_pads[] = { | |||
213 | /* USB host */ | 216 | /* USB host */ |
214 | MX35_PAD_I2C2_CLK__USB_TOP_USBH2_PWR, | 217 | MX35_PAD_I2C2_CLK__USB_TOP_USBH2_PWR, |
215 | MX35_PAD_I2C2_DAT__USB_TOP_USBH2_OC, | 218 | MX35_PAD_I2C2_DAT__USB_TOP_USBH2_OC, |
219 | /* SSI */ | ||
220 | MX35_PAD_STXFS4__AUDMUX_AUD4_TXFS, | ||
221 | MX35_PAD_STXD4__AUDMUX_AUD4_TXD, | ||
222 | MX35_PAD_SRXD4__AUDMUX_AUD4_RXD, | ||
223 | MX35_PAD_SCK4__AUDMUX_AUD4_TXC, | ||
224 | }; | ||
225 | |||
226 | #define AC97_GPIO_TXFS (1 * 32 + 31) | ||
227 | #define AC97_GPIO_TXD (1 * 32 + 28) | ||
228 | #define AC97_GPIO_RESET (1 * 32 + 0) | ||
229 | |||
230 | static void pcm043_ac97_warm_reset(struct snd_ac97 *ac97) | ||
231 | { | ||
232 | struct pad_desc txfs_gpio = MX35_PAD_STXFS4__GPIO2_31; | ||
233 | struct pad_desc txfs = MX35_PAD_STXFS4__AUDMUX_AUD4_TXFS; | ||
234 | int ret; | ||
235 | |||
236 | ret = gpio_request(AC97_GPIO_TXFS, "SSI"); | ||
237 | if (ret) { | ||
238 | printk("failed to get GPIO_TXFS: %d\n", ret); | ||
239 | return; | ||
240 | } | ||
241 | |||
242 | mxc_iomux_v3_setup_pad(&txfs_gpio); | ||
243 | |||
244 | /* warm reset */ | ||
245 | gpio_direction_output(AC97_GPIO_TXFS, 1); | ||
246 | udelay(2); | ||
247 | gpio_set_value(AC97_GPIO_TXFS, 0); | ||
248 | |||
249 | gpio_free(AC97_GPIO_TXFS); | ||
250 | mxc_iomux_v3_setup_pad(&txfs); | ||
251 | } | ||
252 | |||
253 | static void pcm043_ac97_cold_reset(struct snd_ac97 *ac97) | ||
254 | { | ||
255 | struct pad_desc txfs_gpio = MX35_PAD_STXFS4__GPIO2_31; | ||
256 | struct pad_desc txfs = MX35_PAD_STXFS4__AUDMUX_AUD4_TXFS; | ||
257 | struct pad_desc txd_gpio = MX35_PAD_STXD4__GPIO2_28; | ||
258 | struct pad_desc txd = MX35_PAD_STXD4__AUDMUX_AUD4_TXD; | ||
259 | struct pad_desc reset_gpio = MX35_PAD_SD2_CMD__GPIO2_0; | ||
260 | int ret; | ||
261 | |||
262 | ret = gpio_request(AC97_GPIO_TXFS, "SSI"); | ||
263 | if (ret) | ||
264 | goto err1; | ||
265 | |||
266 | ret = gpio_request(AC97_GPIO_TXD, "SSI"); | ||
267 | if (ret) | ||
268 | goto err2; | ||
269 | |||
270 | ret = gpio_request(AC97_GPIO_RESET, "SSI"); | ||
271 | if (ret) | ||
272 | goto err3; | ||
273 | |||
274 | mxc_iomux_v3_setup_pad(&txfs_gpio); | ||
275 | mxc_iomux_v3_setup_pad(&txd_gpio); | ||
276 | mxc_iomux_v3_setup_pad(&reset_gpio); | ||
277 | |||
278 | gpio_direction_output(AC97_GPIO_TXFS, 0); | ||
279 | gpio_direction_output(AC97_GPIO_TXD, 0); | ||
280 | |||
281 | /* cold reset */ | ||
282 | gpio_direction_output(AC97_GPIO_RESET, 0); | ||
283 | udelay(10); | ||
284 | gpio_direction_output(AC97_GPIO_RESET, 1); | ||
285 | |||
286 | mxc_iomux_v3_setup_pad(&txd); | ||
287 | mxc_iomux_v3_setup_pad(&txfs); | ||
288 | |||
289 | gpio_free(AC97_GPIO_RESET); | ||
290 | err3: | ||
291 | gpio_free(AC97_GPIO_TXD); | ||
292 | err2: | ||
293 | gpio_free(AC97_GPIO_TXFS); | ||
294 | err1: | ||
295 | if (ret) | ||
296 | printk("%s failed with %d\n", __func__, ret); | ||
297 | mdelay(1); | ||
298 | } | ||
299 | |||
300 | static struct imx_ssi_platform_data pcm043_ssi_pdata = { | ||
301 | .ac97_reset = pcm043_ac97_cold_reset, | ||
302 | .ac97_warm_reset = pcm043_ac97_warm_reset, | ||
303 | .flags = IMX_SSI_USE_AC97, | ||
216 | }; | 304 | }; |
217 | 305 | ||
218 | static struct mxc_nand_platform_data pcm037_nand_board_info = { | 306 | static struct mxc_nand_platform_data pcm037_nand_board_info = { |
@@ -258,10 +346,23 @@ static void __init mxc_board_init(void) | |||
258 | { | 346 | { |
259 | mxc_iomux_v3_setup_multiple_pads(pcm043_pads, ARRAY_SIZE(pcm043_pads)); | 347 | mxc_iomux_v3_setup_multiple_pads(pcm043_pads, ARRAY_SIZE(pcm043_pads)); |
260 | 348 | ||
349 | mxc_audmux_v2_configure_port(3, | ||
350 | MXC_AUDMUX_V2_PTCR_SYN | /* 4wire mode */ | ||
351 | MXC_AUDMUX_V2_PTCR_TFSEL(0) | | ||
352 | MXC_AUDMUX_V2_PTCR_TFSDIR, | ||
353 | MXC_AUDMUX_V2_PDCR_RXDSEL(0)); | ||
354 | |||
355 | mxc_audmux_v2_configure_port(0, | ||
356 | MXC_AUDMUX_V2_PTCR_SYN | /* 4wire mode */ | ||
357 | MXC_AUDMUX_V2_PTCR_TCSEL(3) | | ||
358 | MXC_AUDMUX_V2_PTCR_TCLKDIR, /* clock is output */ | ||
359 | MXC_AUDMUX_V2_PDCR_RXDSEL(3)); | ||
360 | |||
261 | platform_add_devices(devices, ARRAY_SIZE(devices)); | 361 | platform_add_devices(devices, ARRAY_SIZE(devices)); |
262 | 362 | ||
263 | mxc_register_device(&mxc_uart_device0, &uart_pdata); | 363 | mxc_register_device(&mxc_uart_device0, &uart_pdata); |
264 | mxc_register_device(&mxc_nand_device, &pcm037_nand_board_info); | 364 | mxc_register_device(&mxc_nand_device, &pcm037_nand_board_info); |
365 | mxc_register_device(&imx_ssi_device0, &pcm043_ssi_pdata); | ||
265 | 366 | ||
266 | mxc_register_device(&mxc_uart_device1, &uart_pdata); | 367 | mxc_register_device(&mxc_uart_device1, &uart_pdata); |
267 | 368 | ||