Efika MX platform support
[efikamx:linux-kernel.git] / arch / arm / mach-mx5 / mx51_efikamx_audio.c
1 /*
2  * Copyright 2009 Pegatron Corporation. All Rights Reserved.
3  * Copyright 2009-2010 Genesi USA, Inc. All Rights Reserved.
4  */
5
6 /*
7  * The code contained herein is licensed under the GNU General Public
8  * License. You may obtain a copy of the GNU General Public License
9  * Version 2 or later at the following locations:
10  *
11  * http://www.opensource.org/licenses/gpl-license.html
12  * http://www.gnu.org/copyleft/gpl.html
13  */
14
15 #include <linux/errno.h>
16 #include <linux/module.h>
17 #include <linux/platform_device.h>
18 #include <linux/delay.h>
19 #include <linux/clk.h>
20 #include <mach/hardware.h>
21 #include <mach/gpio.h>
22 #include <mach/mxc.h>
23 #include <mach/common.h>
24 #include <mach/irqs.h>
25
26 #include "devices.h"
27 #include "mx51_pins.h"
28 #include "iomux.h"
29
30 #include "mx51_efikamx.h"
31
32 #define EFIKAMX_AMP_ENABLE MX51_PIN_EIM_A23
33 #define EFIKAMX_HP_DETECT  MX51_PIN_DISPB2_SER_RS
34
35
36 static struct mxc_iomux_pin_cfg __initdata mx51_efikamx_audio_iomux_pins[] = {
37         {
38          MX51_PIN_AUD3_BB_TXD, IOMUX_CONFIG_ALT0,
39          (PAD_CTL_SRE_FAST | PAD_CTL_DRV_HIGH | PAD_CTL_ODE_OPENDRAIN_NONE |
40           PAD_CTL_100K_PU | PAD_CTL_HYS_NONE | PAD_CTL_DDR_INPUT_CMOS |
41           PAD_CTL_DRV_VOT_LOW),
42          },
43         {
44          MX51_PIN_AUD3_BB_RXD, IOMUX_CONFIG_ALT0,
45          (PAD_CTL_SRE_FAST | PAD_CTL_DRV_HIGH | PAD_CTL_ODE_OPENDRAIN_NONE |
46           PAD_CTL_100K_PU | PAD_CTL_HYS_NONE | PAD_CTL_DDR_INPUT_CMOS |
47           PAD_CTL_DRV_VOT_LOW),
48          },
49         {
50          MX51_PIN_AUD3_BB_CK, IOMUX_CONFIG_ALT0,
51          (PAD_CTL_SRE_FAST | PAD_CTL_DRV_HIGH | PAD_CTL_ODE_OPENDRAIN_NONE |
52           PAD_CTL_100K_PU | PAD_CTL_HYS_NONE | PAD_CTL_DDR_INPUT_CMOS |
53           PAD_CTL_DRV_VOT_LOW),
54          },
55         {
56          MX51_PIN_AUD3_BB_FS, IOMUX_CONFIG_ALT0,
57          (PAD_CTL_SRE_FAST | PAD_CTL_DRV_HIGH | PAD_CTL_ODE_OPENDRAIN_NONE |
58           PAD_CTL_100K_PU | PAD_CTL_HYS_NONE | PAD_CTL_DDR_INPUT_CMOS |
59           PAD_CTL_DRV_VOT_LOW),
60          },
61 };
62
63 static int mx51_efikamx_audio_amp_enable(int enable)
64 {
65         gpio_set_value(IOMUX_TO_GPIO(EFIKAMX_AMP_ENABLE), enable ? 1 : 0);
66         return 0;
67 }
68
69 static int mx51_efikamx_headphone_det_status(void)
70 {
71         return gpio_get_value(IOMUX_TO_GPIO(EFIKAMX_HP_DETECT));
72 }
73
74 static struct mxc_audio_platform_data mx51_efikamx_audio_data = {
75         .ssi_num = 1,
76         .src_port = 2,
77         .ext_port = 3,
78         .hp_irq = IOMUX_TO_IRQ(EFIKAMX_HP_DETECT),
79         .hp_status = mx51_efikamx_headphone_det_status,
80         .amp_enable = mx51_efikamx_audio_amp_enable,
81         .sysclk = 12288000,
82 };
83
84 static struct platform_device mx51_efikamx_audio_device = {
85         .name = "imx-3stack-sgtl5000",
86 };
87
88 static struct mxc_spdif_platform_data mx51_efikamx_spdif_data = {
89         .spdif_tx = 1,
90         .spdif_rx = 0,
91         .spdif_clk_44100 = 0,   /* spdif_ext_clk source for 44.1KHz */
92         .spdif_clk_48000 = 7,   /* audio osc source */
93         .spdif_clkid = 0,
94         .spdif_clk = NULL,      /* spdif bus clk */
95 };
96
97
98
99 void mx51_efikamx_init_audio(void)
100 {
101         CONFIG_IOMUX(mx51_efikamx_audio_iomux_pins);
102
103         /* TODO: move these two to the  IOMUX stuff above */
104         /* hphone_det_b */
105         mxc_request_iomux(EFIKAMX_HP_DETECT, IOMUX_CONFIG_ALT4);
106         mxc_iomux_set_pad(EFIKAMX_HP_DETECT, PAD_CTL_100K_PU);
107         gpio_request(IOMUX_TO_GPIO(EFIKAMX_HP_DETECT), "hphone_det_b");
108         gpio_direction_input(IOMUX_TO_GPIO(EFIKAMX_HP_DETECT));
109
110         /* audio_clk_en_b */
111         mxc_request_iomux(MX51_PIN_CSPI1_RDY, IOMUX_CONFIG_ALT3);
112         mxc_iomux_set_pad(MX51_PIN_CSPI1_RDY, PAD_CTL_DRV_HIGH |
113                           PAD_CTL_HYS_NONE | PAD_CTL_PUE_KEEPER |
114                           PAD_CTL_100K_PU | PAD_CTL_ODE_OPENDRAIN_NONE |
115                           PAD_CTL_PKE_ENABLE | PAD_CTL_SRE_FAST);
116         gpio_request(IOMUX_TO_GPIO(MX51_PIN_CSPI1_RDY), "audio_clk_en_b");
117         gpio_direction_output(IOMUX_TO_GPIO(MX51_PIN_CSPI1_RDY), 0);
118
119         mxc_register_device(&mxc_ssi1_device, NULL);
120         mxc_register_device(&mxc_ssi2_device, NULL);
121
122         if (cpu_is_mx51_rev(CHIP_REV_1_1) == 2) {
123                 mx51_efikamx_audio_data.sysclk = 26000000;
124         }
125
126         gpio_request(IOMUX_TO_GPIO(EFIKAMX_AMP_ENABLE), "audio_amp_enable");
127         gpio_direction_output(IOMUX_TO_GPIO(EFIKAMX_AMP_ENABLE), 0);
128
129         mxc_register_device(&mx51_efikamx_audio_device, &mx51_efikamx_audio_data);
130
131         mx51_efikamx_spdif_data.spdif_core_clk = clk_get(NULL, "spdif_xtal_clk");
132         clk_put(mx51_efikamx_spdif_data.spdif_core_clk);
133
134         /* this is in no way hooked in..???  */
135         mxc_register_device(&mxc_alsa_spdif_device, &mx51_efikamx_spdif_data);
136 };