diff options
author | Alan Tull <alan.tull@freescale.com> | 2011-06-28 11:18:05 -0500 |
---|---|---|
committer | Alan Tull <alan.tull@freescale.com> | 2011-10-25 11:51:23 -0500 |
commit | 1d7009281420135963017043998e42acd7f36d75 (patch) | |
tree | a1054a2f5b511a788cc327b48a1bf08507ead7b0 /arch | |
parent | b90d615d217b0ee564a3fce3ff050aabbfe2f90c (diff) |
ENGR00139265-4 mxc alsa soc spdif driver
* Add support for S/PDIF on i.Mx6
Signed-off-by: Alan Tull <alan.tull@freescale.com>
Diffstat (limited to 'arch')
-rw-r--r-- | arch/arm/configs/imx6_defconfig | 5 | ||||
-rw-r--r-- | arch/arm/mach-mx6/Kconfig | 2 | ||||
-rw-r--r-- | arch/arm/mach-mx6/board-mx6q_sabreauto.c | 39 | ||||
-rw-r--r-- | arch/arm/mach-mx6/clock.c | 5 | ||||
-rw-r--r-- | arch/arm/mach-mx6/devices-imx6q.h | 11 | ||||
-rw-r--r-- | arch/arm/plat-mxc/devices/platform-imx-spdif-dai.c | 5 | ||||
-rw-r--r-- | arch/arm/plat-mxc/devices/platform-imx-spdif.c | 5 | ||||
-rw-r--r-- | arch/arm/plat-mxc/include/mach/iomux-mx6q.h | 4 | ||||
-rw-r--r-- | arch/arm/plat-mxc/include/mach/mx6.h | 4 |
9 files changed, 75 insertions, 5 deletions
diff --git a/arch/arm/configs/imx6_defconfig b/arch/arm/configs/imx6_defconfig index 891e0c1d184..a24c80355c3 100644 --- a/arch/arm/configs/imx6_defconfig +++ b/arch/arm/configs/imx6_defconfig @@ -275,6 +275,7 @@ CONFIG_IMX_HAVE_PLATFORM_AHCI=y CONFIG_IMX_HAVE_PLATFORM_IMX_OCOTP=y CONFIG_IMX_HAVE_PLATFORM_IMX_VIIM=y CONFIG_IMX_HAVE_PLATFORM_LDB=y +CONFIG_IMX_HAVE_PLATFORM_IMX_SPDIF=y CONFIG_IMX_HAVE_PLATFORM_VIV_GPU=y CONFIG_IMX_HAVE_PLATFORM_MXC_HDMI=y CONFIG_IMX_HAVE_PLATFORM_IMX_ANATOP_THERMAL=y @@ -1450,10 +1451,12 @@ CONFIG_SND_SOC=y CONFIG_SND_SOC_AC97_BUS=y CONFIG_SND_IMX_SOC=y CONFIG_SND_MXC_SOC_MX2=y +CONFIG_SND_MXC_SOC_SPDIF_DAI=y CONFIG_SND_SOC_IMX_CS42888=y -# CONFIG_SND_SOC_IMX_SPDIF is not set +CONFIG_SND_SOC_IMX_SPDIF=y CONFIG_SND_SOC_I2C_AND_SPI=y # CONFIG_SND_SOC_ALL_CODECS is not set +CONFIG_SND_SOC_MXC_SPDIF=y CONFIG_SND_SOC_CS42888=y # CONFIG_SOUND_PRIME is not set CONFIG_AC97_BUS=y diff --git a/arch/arm/mach-mx6/Kconfig b/arch/arm/mach-mx6/Kconfig index 9fddbdf2190..d9f68946888 100644 --- a/arch/arm/mach-mx6/Kconfig +++ b/arch/arm/mach-mx6/Kconfig @@ -12,6 +12,7 @@ config ARCH_MX6Q select IMX_HAVE_PLATFORM_IMX_IPUV3 select IMX_HAVE_PLATFORM_MXC_PWM select IMX_HAVE_PLATFORM_LDB + select IMX_HAVE_PLATFORM_IMX_SPDIF config FORCE_MAX_ZONEORDER int "MAX_ORDER" @@ -48,6 +49,7 @@ config MACH_MX6Q_SABREAUTO select IMX_HAVE_PLATFORM_IMX_PM select IMX_HAVE_PLATFORM_MXC_HDMI select IMX_HAVE_PLATFORM_IMX_ASRC + select IMX_HAVE_PLATFORM_IMX_SPDIF help Include support for i.MX 6Quad SABRE Automotive Infotainment platform. This includes specific configurations for the board and its peripherals. diff --git a/arch/arm/mach-mx6/board-mx6q_sabreauto.c b/arch/arm/mach-mx6/board-mx6q_sabreauto.c index 4a71738f1ee..9149cb68e97 100644 --- a/arch/arm/mach-mx6/board-mx6q_sabreauto.c +++ b/arch/arm/mach-mx6/board-mx6q_sabreauto.c @@ -264,6 +264,10 @@ static iomux_v3_cfg_t mx6q_sabreauto_pads[] = { /* USBOTG ID pin */ MX6Q_PAD_GPIO_1__USBOTG_ID, + + /* SPDIF */ + MX6Q_PAD_GPIO_16__SPDIF_IN1, + MX6Q_PAD_GPIO_17__SPDIF_OUT1, }; static iomux_v3_cfg_t mx6q_sabreauto_esai_record_pads[] = { @@ -869,6 +873,35 @@ static inline void __init mx6q_csi0_io_init(void) gpio_set_value(MX6Q_SMD_CSI0_PWN, 0); mxc_iomux_set_gpr_register(1, 19, 1, 1); } + +static int spdif_clk_set_rate(struct clk *clk, unsigned long rate) +{ + unsigned long rate_actual; + rate_actual = clk_round_rate(clk, rate); + clk_set_rate(clk, rate_actual); + return 0; +} + +static struct mxc_spdif_platform_data mxc_spdif_data = { + .spdif_tx = 1, /* enable tx */ + .spdif_rx = 1, /* enable rx */ + /* + * spdif0_clk will be 454.7MHz divided by ccm dividers. + * + * 44.1KHz: 454.7MHz / 7 (ccm) / 23 (spdif) = 44,128 Hz ~ 0.06% error + * 48KHz: 454.7MHz / 4 (ccm) / 37 (spdif) = 48,004 Hz ~ 0.01% error + * 32KHz: 454.7MHz / 6 (ccm) / 37 (spdif) = 32,003 Hz ~ 0.01% error + */ + .spdif_clk_44100 = 1, /* tx clk from spdif0_clk_root */ + .spdif_clk_48000 = 1, /* tx clk from spdif0_clk_root */ + .spdif_div_44100 = 23, + .spdif_div_48000 = 37, + .spdif_div_32000 = 37, + .spdif_rx_clk = 0, /* rx clk from spdif stream */ + .spdif_clk_set_rate = spdif_clk_set_rate, + .spdif_clk = NULL, /* spdif bus clk */ +}; + /*! * Board specific initialization. */ @@ -954,6 +987,12 @@ static void __init mx6_board_init(void) imx6q_add_gpmi(&mx6q_gpmi_nfc_platform_data); imx6q_add_dvfs_core(&sabreauto_dvfscore_data); + + mxc_spdif_data.spdif_core_clk = clk_get_sys("mxc_spdif.0", NULL); + clk_put(mxc_spdif_data.spdif_core_clk); + imx6q_add_spdif(&mxc_spdif_data); + imx6q_add_spdif_dai(); + imx6q_add_spdif_audio_device(); } extern void __iomem *twd_base; diff --git a/arch/arm/mach-mx6/clock.c b/arch/arm/mach-mx6/clock.c index 007fd7b17a9..fe9dba23cc9 100644 --- a/arch/arm/mach-mx6/clock.c +++ b/arch/arm/mach-mx6/clock.c @@ -4483,7 +4483,7 @@ static struct clk_lookup lookups[] = { _REGISTER_CLOCK("FlexCAN.1", "can_clk", can2_clk[0]), _REGISTER_CLOCK(NULL, "ldb_di0_clk", ldb_di0_clk), _REGISTER_CLOCK(NULL, "ldb_di1_clk", ldb_di1_clk), - _REGISTER_CLOCK(NULL, "mxc_alsa_spdif.0", spdif0_clk[0]), + _REGISTER_CLOCK("mxc_spdif.0", NULL, spdif0_clk[0]), _REGISTER_CLOCK(NULL, "esai_clk", esai_clk), _REGISTER_CLOCK("mxc_spi.0", NULL, ecspi_clk[0]), _REGISTER_CLOCK("mxc_spi.1", NULL, ecspi_clk[1]), @@ -4653,6 +4653,9 @@ int __init mx6_clocks_init(unsigned long ckil, unsigned long osc, /* Lower the ipg_perclk frequency to 8.25MHz. */ clk_set_rate(&ipg_perclk, 8250000); + /* S/PDIF */ + clk_set_parent(&spdif0_clk[0], &pll3_pfd_454M); + base = ioremap(GPT_BASE_ADDR, SZ_4K); mxc_timer_init(&gpt_clk[0], base, MXC_INT_GPT); diff --git a/arch/arm/mach-mx6/devices-imx6q.h b/arch/arm/mach-mx6/devices-imx6q.h index b607758074c..98c94cbabf1 100644 --- a/arch/arm/mach-mx6/devices-imx6q.h +++ b/arch/arm/mach-mx6/devices-imx6q.h @@ -143,3 +143,14 @@ extern const struct imx_dvfs_core_data imx6q_dvfs_core_data __initconst; #define imx6q_add_dvfs_core(pdata) \ imx_add_dvfs_core(&imx6q_dvfs_core_data, pdata) +extern const struct imx_viv_gpu_data imx6_gc2000_data __initconst; +extern const struct imx_viv_gpu_data imx6_gc320_data __initconst; +extern const struct imx_viv_gpu_data imx6_gc355_data __initconst; + +extern const struct imx_spdif_data imx6q_imx_spdif_data __initconst; +#define imx6q_add_spdif(pdata) imx_add_spdif(&imx6q_imx_spdif_data, pdata) + +extern const struct imx_spdif_dai_data imx6q_spdif_dai_data __initconst; +#define imx6q_add_spdif_dai() imx_add_spdif_dai(&imx6q_spdif_dai_data) + +#define imx6q_add_spdif_audio_device(pdata) imx_add_spdif_audio_device() diff --git a/arch/arm/plat-mxc/devices/platform-imx-spdif-dai.c b/arch/arm/plat-mxc/devices/platform-imx-spdif-dai.c index 516ebc52467..7e0a97b14c3 100644 --- a/arch/arm/plat-mxc/devices/platform-imx-spdif-dai.c +++ b/arch/arm/plat-mxc/devices/platform-imx-spdif-dai.c @@ -33,6 +33,11 @@ const struct imx_spdif_dai_data imx53_spdif_dai_data __initconst = imx_spdif_dai_data_entry(MX53); #endif /* ifdef CONFIG_SOC_IMX53 */ +#ifdef CONFIG_SOC_IMX6Q +const struct imx_spdif_dai_data imx6q_spdif_dai_data __initconst = + imx_spdif_dai_data_entry(MX6Q); +#endif /* #ifdef CONFIG_SOC_IMX6Q */ + struct platform_device *__init imx_add_spdif_dai( const struct imx_spdif_dai_data *data) { diff --git a/arch/arm/plat-mxc/devices/platform-imx-spdif.c b/arch/arm/plat-mxc/devices/platform-imx-spdif.c index 80a5e782067..90a58899f92 100644 --- a/arch/arm/plat-mxc/devices/platform-imx-spdif.c +++ b/arch/arm/plat-mxc/devices/platform-imx-spdif.c @@ -42,6 +42,11 @@ const struct imx_spdif_data imx53_imx_spdif_data __initconst = imx5_spdif_data_entry_single(MX53); #endif /* ifdef CONFIG_SOC_IMX53 */ +#ifdef CONFIG_SOC_IMX6Q +const struct imx_spdif_data imx6q_imx_spdif_data __initconst = + imx5_spdif_data_entry_single(MX6Q); +#endif /* ifdef CONFIG_SOC_IMX6Q */ + struct platform_device *__init imx_add_spdif( const struct imx_spdif_data *data, const struct mxc_spdif_platform_data *pdata) diff --git a/arch/arm/plat-mxc/include/mach/iomux-mx6q.h b/arch/arm/plat-mxc/include/mach/iomux-mx6q.h index c48fe755cac..8927779bbb0 100644 --- a/arch/arm/plat-mxc/include/mach/iomux-mx6q.h +++ b/arch/arm/plat-mxc/include/mach/iomux-mx6q.h @@ -78,6 +78,8 @@ typedef enum iomux_config { #define MX6Q_GPMI_PAD_CTRL1 (PAD_CTL_DSE_40ohm | PAD_CTL_SPEED_MED | PAD_CTL_SRE_FAST) #define MX6Q_GPMI_PAD_CTRL2 (MX6Q_GPMI_PAD_CTRL0 | MX6Q_GPMI_PAD_CTRL1) +#define MX6Q_SPDIF_OUT_PAD_CTRL (PAD_CTL_DSE_120ohm | PAD_CTL_SRE_FAST) + #define _MX6Q_PAD_SD2_DAT1__USDHC2_DAT1 \ IOMUX_PAD(0x0360, 0x004C, 0, 0x0000, 0, 0) #define _MX6Q_PAD_SD2_DAT1__ECSPI5_SS0 \ @@ -6029,7 +6031,7 @@ typedef enum iomux_config { #define MX6Q_PAD_GPIO_17__SDMA_SDMA_EXT_EVENT_0 \ (_MX6Q_PAD_GPIO_17__SDMA_SDMA_EXT_EVENT_0 | MUX_PAD_CTRL(NO_PAD_CTRL)) #define MX6Q_PAD_GPIO_17__SPDIF_OUT1 \ - (_MX6Q_PAD_GPIO_17__SPDIF_OUT1 | MUX_PAD_CTRL(NO_PAD_CTRL)) + (_MX6Q_PAD_GPIO_17__SPDIF_OUT1 | MUX_PAD_CTRL(MX6Q_SPDIF_OUT_PAD_CTRL)) #define MX6Q_PAD_GPIO_17__GPIO_7_12 \ (_MX6Q_PAD_GPIO_17__GPIO_7_12 | MUX_PAD_CTRL(NO_PAD_CTRL)) #define MX6Q_PAD_GPIO_17__SJC_JTAG_ACT \ diff --git a/arch/arm/plat-mxc/include/mach/mx6.h b/arch/arm/plat-mxc/include/mach/mx6.h index cead192fc94..9103e9d13ff 100644 --- a/arch/arm/plat-mxc/include/mach/mx6.h +++ b/arch/arm/plat-mxc/include/mach/mx6.h @@ -130,7 +130,7 @@ #define ATZ2_BASE_ADDR AIPS2_ARB_BASE_ADDR /* slots 0,7 of SDMA reserved, therefore left unused in IPMUX3 */ -#define SPDIF_BASE_ADDR (ATZ1_BASE_ADDR + 0x04000) /* slot 1 */ +#define MX6Q_SPDIF_BASE_ADDR (ATZ1_BASE_ADDR + 0x04000) /* slot 1 */ #define MX6Q_ECSPI1_BASE_ADDR (ATZ1_BASE_ADDR + 0x08000) /* slot 2 */ #define MX6Q_ECSPI2_BASE_ADDR (ATZ1_BASE_ADDR + 0x0C000) /* slot 3 */ #define MX6Q_ECSPI3_BASE_ADDR (ATZ1_BASE_ADDR + 0x10000) /* slot 4 */ @@ -330,7 +330,7 @@ #define MXC_INT_ANATOP_TEMPSNSR 81 #define MX6Q_INT_ASRC 82 #define MXC_INT_ESAI 83 -#define MXC_INT_SPDIF 84 +#define MX6Q_INT_SPDIF 84 #define MXC_INT_MLB 85 #define MXC_INT_ANATOP_ANA1 86 #define MXC_INT_GPT 87 |