blob: bb983528b9a5905addc2a4947c683548ec2b272b [file] [log] [blame]
Fabio Estevame2d282a2013-03-15 10:43:48 +00001/*
2 * Copyright (C) 2013 Freescale Semiconductor, Inc.
3 *
4 * Author: Fabio Estevam <fabio.estevam@freescale.com>
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License as
8 * published by the Free Software Foundation; either version 2 of
9 * the License, or (at your option) any later version.
10 */
11
12#include <asm/arch/clock.h>
13#include <asm/arch/iomux.h>
14#include <asm/arch/imx-regs.h>
15#include <asm/arch/mx6-pins.h>
16#include <asm/arch/sys_proto.h>
17#include <asm/gpio.h>
18#include <asm/imx-common/iomux-v3.h>
Otavio Salvadoreaffaa22013-04-19 03:42:03 +000019#include <asm/imx-common/boot_mode.h>
Fabio Estevame2d282a2013-03-15 10:43:48 +000020#include <asm/io.h>
21#include <asm/sizes.h>
22#include <common.h>
23#include <fsl_esdhc.h>
24#include <mmc.h>
25#include <miiphy.h>
26#include <netdev.h>
27
28DECLARE_GLOBAL_DATA_PTR;
29
Benoît Thébaudeau7e2173c2013-04-26 01:34:47 +000030#define UART_PAD_CTRL (PAD_CTL_PUS_100K_UP | \
31 PAD_CTL_SPEED_MED | PAD_CTL_DSE_40ohm | \
32 PAD_CTL_SRE_FAST | PAD_CTL_HYS)
Fabio Estevame2d282a2013-03-15 10:43:48 +000033
Benoît Thébaudeau7e2173c2013-04-26 01:34:47 +000034#define USDHC_PAD_CTRL (PAD_CTL_PUS_47K_UP | \
35 PAD_CTL_SPEED_LOW | PAD_CTL_DSE_80ohm | \
36 PAD_CTL_SRE_FAST | PAD_CTL_HYS)
Fabio Estevame2d282a2013-03-15 10:43:48 +000037
Benoît Thébaudeau7e2173c2013-04-26 01:34:47 +000038#define ENET_PAD_CTRL (PAD_CTL_PUS_100K_UP | \
39 PAD_CTL_SPEED_MED | PAD_CTL_DSE_40ohm | PAD_CTL_HYS)
Fabio Estevame2d282a2013-03-15 10:43:48 +000040
Otavio Salvador5ed15732013-04-19 03:42:02 +000041#define USDHC1_CD_GPIO IMX_GPIO_NR(1, 2)
Otavio Salvador08f32f72013-04-19 03:42:01 +000042#define USDHC3_CD_GPIO IMX_GPIO_NR(3, 9)
Fabio Estevame2d282a2013-03-15 10:43:48 +000043#define ETH_PHY_RESET IMX_GPIO_NR(3, 29)
44
45int dram_init(void)
46{
47 gd->ram_size = CONFIG_DDR_MB * SZ_1M;
48
49 return 0;
50}
51
52static iomux_v3_cfg_t const uart1_pads[] = {
53 MX6_PAD_CSI0_DAT10__UART1_TXD | MUX_PAD_CTRL(UART_PAD_CTRL),
54 MX6_PAD_CSI0_DAT11__UART1_RXD | MUX_PAD_CTRL(UART_PAD_CTRL),
55};
56
Otavio Salvador5ed15732013-04-19 03:42:02 +000057iomux_v3_cfg_t const usdhc1_pads[] = {
58 MX6_PAD_SD1_CLK__USDHC1_CLK | MUX_PAD_CTRL(USDHC_PAD_CTRL),
59 MX6_PAD_SD1_CMD__USDHC1_CMD | MUX_PAD_CTRL(USDHC_PAD_CTRL),
60 MX6_PAD_SD1_DAT0__USDHC1_DAT0 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
61 MX6_PAD_SD1_DAT1__USDHC1_DAT1 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
62 MX6_PAD_SD1_DAT2__USDHC1_DAT2 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
63 MX6_PAD_SD1_DAT3__USDHC1_DAT3 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
64 /* Carrier MicroSD Card Detect */
65 MX6_PAD_GPIO_2__GPIO_1_2 | MUX_PAD_CTRL(NO_PAD_CTRL),
66};
67
Fabio Estevame2d282a2013-03-15 10:43:48 +000068static iomux_v3_cfg_t const usdhc3_pads[] = {
69 MX6_PAD_SD3_CLK__USDHC3_CLK | MUX_PAD_CTRL(USDHC_PAD_CTRL),
70 MX6_PAD_SD3_CMD__USDHC3_CMD | MUX_PAD_CTRL(USDHC_PAD_CTRL),
71 MX6_PAD_SD3_DAT0__USDHC3_DAT0 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
72 MX6_PAD_SD3_DAT1__USDHC3_DAT1 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
73 MX6_PAD_SD3_DAT2__USDHC3_DAT2 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
74 MX6_PAD_SD3_DAT3__USDHC3_DAT3 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
Otavio Salvador08f32f72013-04-19 03:42:01 +000075 /* SOM MicroSD Card Detect */
76 MX6_PAD_EIM_DA9__GPIO_3_9 | MUX_PAD_CTRL(NO_PAD_CTRL),
Fabio Estevame2d282a2013-03-15 10:43:48 +000077};
78
79static iomux_v3_cfg_t const enet_pads[] = {
80 MX6_PAD_ENET_MDIO__ENET_MDIO | MUX_PAD_CTRL(ENET_PAD_CTRL),
81 MX6_PAD_ENET_MDC__ENET_MDC | MUX_PAD_CTRL(ENET_PAD_CTRL),
82 MX6_PAD_RGMII_TXC__ENET_RGMII_TXC | MUX_PAD_CTRL(ENET_PAD_CTRL),
83 MX6_PAD_RGMII_TD0__ENET_RGMII_TD0 | MUX_PAD_CTRL(ENET_PAD_CTRL),
84 MX6_PAD_RGMII_TD1__ENET_RGMII_TD1 | MUX_PAD_CTRL(ENET_PAD_CTRL),
85 MX6_PAD_RGMII_TD2__ENET_RGMII_TD2 | MUX_PAD_CTRL(ENET_PAD_CTRL),
86 MX6_PAD_RGMII_TD3__ENET_RGMII_TD3 | MUX_PAD_CTRL(ENET_PAD_CTRL),
87 MX6_PAD_RGMII_TX_CTL__RGMII_TX_CTL | MUX_PAD_CTRL(ENET_PAD_CTRL),
88 MX6_PAD_ENET_REF_CLK__ENET_TX_CLK | MUX_PAD_CTRL(ENET_PAD_CTRL),
89 MX6_PAD_RGMII_RXC__ENET_RGMII_RXC | MUX_PAD_CTRL(ENET_PAD_CTRL),
90 MX6_PAD_RGMII_RD0__ENET_RGMII_RD0 | MUX_PAD_CTRL(ENET_PAD_CTRL),
91 MX6_PAD_RGMII_RD1__ENET_RGMII_RD1 | MUX_PAD_CTRL(ENET_PAD_CTRL),
92 MX6_PAD_RGMII_RD2__ENET_RGMII_RD2 | MUX_PAD_CTRL(ENET_PAD_CTRL),
93 MX6_PAD_RGMII_RD3__ENET_RGMII_RD3 | MUX_PAD_CTRL(ENET_PAD_CTRL),
94 MX6_PAD_RGMII_RX_CTL__RGMII_RX_CTL | MUX_PAD_CTRL(ENET_PAD_CTRL),
95 /* AR8031 PHY Reset */
96 MX6_PAD_EIM_D29__GPIO_3_29 | MUX_PAD_CTRL(NO_PAD_CTRL),
97};
98
99static void setup_iomux_uart(void)
100{
101 imx_iomux_v3_setup_multiple_pads(uart1_pads, ARRAY_SIZE(uart1_pads));
102}
103
104static void setup_iomux_enet(void)
105{
106 imx_iomux_v3_setup_multiple_pads(enet_pads, ARRAY_SIZE(enet_pads));
107
108 /* Reset AR8031 PHY */
109 gpio_direction_output(ETH_PHY_RESET, 0);
110 udelay(500);
111 gpio_set_value(ETH_PHY_RESET, 1);
112}
113
Otavio Salvador5ed15732013-04-19 03:42:02 +0000114static struct fsl_esdhc_cfg usdhc_cfg[2] = {
Fabio Estevame2d282a2013-03-15 10:43:48 +0000115 {USDHC3_BASE_ADDR},
Otavio Salvador5ed15732013-04-19 03:42:02 +0000116 {USDHC1_BASE_ADDR},
Fabio Estevame2d282a2013-03-15 10:43:48 +0000117};
118
Otavio Salvador08f32f72013-04-19 03:42:01 +0000119int board_mmc_getcd(struct mmc *mmc)
120{
121 struct fsl_esdhc_cfg *cfg = (struct fsl_esdhc_cfg *)mmc->priv;
122 int ret = 0;
123
124 switch (cfg->esdhc_base) {
Otavio Salvador5ed15732013-04-19 03:42:02 +0000125 case USDHC1_BASE_ADDR:
126 ret = !gpio_get_value(USDHC1_CD_GPIO);
127 break;
Otavio Salvador08f32f72013-04-19 03:42:01 +0000128 case USDHC3_BASE_ADDR:
129 ret = !gpio_get_value(USDHC3_CD_GPIO);
130 break;
131 }
132
133 return ret;
134}
135
Fabio Estevame2d282a2013-03-15 10:43:48 +0000136int board_mmc_init(bd_t *bis)
137{
Otavio Salvador5ed15732013-04-19 03:42:02 +0000138 s32 status = 0;
139 u32 index = 0;
Fabio Estevame2d282a2013-03-15 10:43:48 +0000140
Otavio Salvador5ed15732013-04-19 03:42:02 +0000141 /*
142 * Following map is done:
143 * (U-boot device node) (Physical Port)
144 * mmc0 SOM MicroSD
145 * mmc1 Carrier board MicroSD
146 */
147 for (index = 0; index < CONFIG_SYS_FSL_USDHC_NUM; ++index) {
148 switch (index) {
149 case 0:
150 imx_iomux_v3_setup_multiple_pads(
151 usdhc3_pads, ARRAY_SIZE(usdhc3_pads));
152 usdhc_cfg[0].sdhc_clk = mxc_get_clock(MXC_ESDHC3_CLK);
153 usdhc_cfg[0].max_bus_width = 4;
154 gpio_direction_input(USDHC3_CD_GPIO);
155 break;
156 case 1:
157 imx_iomux_v3_setup_multiple_pads(
158 usdhc1_pads, ARRAY_SIZE(usdhc1_pads));
159 usdhc_cfg[1].sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK);
160 usdhc_cfg[1].max_bus_width = 4;
161 gpio_direction_input(USDHC1_CD_GPIO);
162 break;
163 default:
164 printf("Warning: you configured more USDHC controllers"
165 "(%d) then supported by the board (%d)\n",
166 index + 1, CONFIG_SYS_FSL_USDHC_NUM);
167 return status;
168 }
Abbas Razaaad46592013-03-25 09:13:34 +0000169
Otavio Salvador5ed15732013-04-19 03:42:02 +0000170 status |= fsl_esdhc_initialize(bis, &usdhc_cfg[index]);
171 }
172
173 return status;
Fabio Estevame2d282a2013-03-15 10:43:48 +0000174}
175
176static int mx6_rgmii_rework(struct phy_device *phydev)
177{
178 unsigned short val;
179
180 /* To enable AR8031 ouput a 125MHz clk from CLK_25M */
181 phy_write(phydev, MDIO_DEVAD_NONE, 0xd, 0x7);
182 phy_write(phydev, MDIO_DEVAD_NONE, 0xe, 0x8016);
183 phy_write(phydev, MDIO_DEVAD_NONE, 0xd, 0x4007);
184
185 val = phy_read(phydev, MDIO_DEVAD_NONE, 0xe);
186 val &= 0xffe3;
187 val |= 0x18;
188 phy_write(phydev, MDIO_DEVAD_NONE, 0xe, val);
189
190 /* introduce tx clock delay */
191 phy_write(phydev, MDIO_DEVAD_NONE, 0x1d, 0x5);
192 val = phy_read(phydev, MDIO_DEVAD_NONE, 0x1e);
193 val |= 0x0100;
194 phy_write(phydev, MDIO_DEVAD_NONE, 0x1e, val);
195
196 return 0;
197}
198
199int board_phy_config(struct phy_device *phydev)
200{
201 mx6_rgmii_rework(phydev);
202
203 if (phydev->drv->config)
204 phydev->drv->config(phydev);
205
206 return 0;
207}
208
209int board_eth_init(bd_t *bis)
210{
211 int ret;
212
213 setup_iomux_enet();
214
215 ret = cpu_eth_init(bis);
216 if (ret)
217 printf("FEC MXC: %s:failed\n", __func__);
218
219 return 0;
220}
221
222int board_early_init_f(void)
223{
224 setup_iomux_uart();
225 return 0;
226}
227
Otavio Salvadoreaffaa22013-04-19 03:42:03 +0000228#ifdef CONFIG_CMD_BMODE
229static const struct boot_mode board_boot_modes[] = {
230 /* 4 bit bus width */
231 {"mmc0", MAKE_CFGVAL(0x40, 0x30, 0x00, 0x00)},
232 {"mmc1", MAKE_CFGVAL(0x40, 0x20, 0x00, 0x00)},
233 {NULL, 0},
234};
235#endif
236
237int board_late_init(void)
238{
239#ifdef CONFIG_CMD_BMODE
240 add_board_boot_modes(board_boot_modes);
241#endif
242
243 return 0;
244}
245
Fabio Estevame2d282a2013-03-15 10:43:48 +0000246int board_init(void)
247{
248 /* address of boot parameters */
249 gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
250
251 return 0;
252}
253
Fabio Estevame2d282a2013-03-15 10:43:48 +0000254int checkboard(void)
255{
256 puts("Board: Wandboard\n");
257
258 return 0;
259}