From 093b46eac2fb9496335db1fc0239665dfb72503b Mon Sep 17 00:00:00 2001 From: Marcel Ziswiler Date: Sat, 25 Jan 2014 23:17:53 +0100 Subject: apalis_imx6: fix ethernet Fix Ethernet by limiting Micrel KSZ9031 PHY to 10/100 Mbps for now. This has been ported from the following mainline commit for the uDoo board: 078813d21db0600d440625327a1728c32e9fcc90 While at it clean out some more irrelevant stuff. --- board/toradex/apalis_imx6/apalis_imx6.c | 243 ++++++-------------------------- include/micrel.h | 5 + 2 files changed, 50 insertions(+), 198 deletions(-) diff --git a/board/toradex/apalis_imx6/apalis_imx6.c b/board/toradex/apalis_imx6/apalis_imx6.c index f999f57a97..73738caad7 100644 --- a/board/toradex/apalis_imx6/apalis_imx6.c +++ b/board/toradex/apalis_imx6/apalis_imx6.c @@ -76,6 +76,7 @@ iomux_v3_cfg_t const uart1_pads[] = { MX6_PAD_CSI0_DAT10__UART1_TXD | MUX_PAD_CTRL(UART_PAD_CTRL), MX6_PAD_CSI0_DAT11__UART1_RXD | MUX_PAD_CTRL(UART_PAD_CTRL), }; + /* Apalis UART2 */ iomux_v3_cfg_t const uart2_pads[] = { MX6_PAD_SD4_DAT4__UART2_RXD | MUX_PAD_CTRL(UART_PAD_CTRL), @@ -96,6 +97,7 @@ struct i2c_pads_info i2c_pad_info1 = { .gp = IMX_GPIO_NR(5, 26) } }; + /* Apalis local, PMIC, SGTL5000, STMPE811*/ struct i2c_pads_info i2c_pad_info_loc = { .scl = { @@ -123,6 +125,7 @@ struct i2c_pads_info i2c_pad_info3 = { .gp = IMX_GPIO_NR(3, 18) } }; + /* Apalis I2C2 / DDC */ struct i2c_pads_info i2c_pad_info_ddc = { .scl = { @@ -151,6 +154,7 @@ iomux_v3_cfg_t const usdhc1_pads[] = { MX6_PAD_NANDF_D3__USDHC1_DAT7 | MUX_PAD_CTRL(USDHC_PAD_CTRL), MX6_PAD_DI0_PIN4__GPIO_4_20 | MUX_PAD_CTRL(NO_PAD_CTRL), /* CD */ }; + /* eMMC */ iomux_v3_cfg_t const usdhc3_pads[] = { MX6_PAD_SD3_CLK__USDHC3_CLK | MUX_PAD_CTRL(USDHC_PAD_CTRL), @@ -177,8 +181,36 @@ iomux_v3_cfg_t const usdhc4_pads[] = { MX6_PAD_NANDF_CS1__GPIO_6_14 | MUX_PAD_CTRL(NO_PAD_CTRL), /* CD */ }; -//TODO check all pins, do we need that GPIO->RD[0:3] transition (struct enet_pads2[]) -iomux_v3_cfg_t const enet_pads1[] = { +int mx6_rgmii_rework(struct phy_device *phydev) +{ + /* + * Bug: Apparently Apalis iMX6 does not works with Gigabit switches... + * Limiting speed to 10/100Mbps, and setting master mode, seems to + * be the only way to have a successfull PHY auto negotiation. + * How to fix: Understand why Linux kernel do not have this issue. + */ + phy_write(phydev, MDIO_DEVAD_NONE, MII_CTRL1000, 0x1c00); + + /* control data pad skew - devaddr = 0x02, register = 0x04 */ + ksz9031_phy_extended_write(phydev, 0x02, + MII_KSZ9031_EXT_RGMII_CTRL_SIG_SKEW, + MII_KSZ9031_MOD_DATA_NO_POST_INC, 0x0000); + /* rx data pad skew - devaddr = 0x02, register = 0x05 */ + ksz9031_phy_extended_write(phydev, 0x02, + MII_KSZ9031_EXT_RGMII_RX_DATA_SKEW, + MII_KSZ9031_MOD_DATA_NO_POST_INC, 0x0000); + /* tx data pad skew - devaddr = 0x02, register = 0x05 */ + ksz9031_phy_extended_write(phydev, 0x02, + MII_KSZ9031_EXT_RGMII_TX_DATA_SKEW, + MII_KSZ9031_MOD_DATA_NO_POST_INC, 0x0000); + /* gtx and rx clock pad skew - devaddr = 0x02, register = 0x08 */ + ksz9031_phy_extended_write(phydev, 0x02, + MII_KSZ9031_EXT_RGMII_CLOCK_SKEW, + MII_KSZ9031_MOD_DATA_NO_POST_INC, 0x03FF); + return 0; +} + +iomux_v3_cfg_t const enet_pads[] = { MX6_PAD_ENET_MDIO__ENET_MDIO | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_ENET_MDC__ENET_MDC | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_TXC__ENET_RGMII_TXC | MUX_PAD_CTRL(ENET_PAD_CTRL), @@ -188,79 +220,24 @@ iomux_v3_cfg_t const enet_pads1[] = { MX6_PAD_RGMII_TD3__ENET_RGMII_TD3 | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_TX_CTL__RGMII_TX_CTL | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_ENET_REF_CLK__ENET_TX_CLK | MUX_PAD_CTRL(ENET_PAD_CTRL), - /* pin 35 - 1 (PHY_AD2) on reset */ - MX6_PAD_RGMII_RXC__GPIO_6_30 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 32 - 1 - (MODE0) all */ - MX6_PAD_RGMII_RD0__GPIO_6_25 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 31 - 1 - (MODE1) all */ - MX6_PAD_RGMII_RD1__GPIO_6_27 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 28 - 1 - (MODE2) all */ - MX6_PAD_RGMII_RD2__GPIO_6_28 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 27 - 1 - (MODE3) all */ - MX6_PAD_RGMII_RD3__GPIO_6_29 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 33 - 1 - (CLK125_EN) 125Mhz clockout enabled */ - MX6_PAD_RGMII_RX_CTL__GPIO_6_24 | MUX_PAD_CTRL(NO_PAD_CTRL), - /* pin 42 PHY nRST */ - MX6_PAD_ENET_CRS_DV__GPIO_1_25 | MUX_PAD_CTRL(NO_PAD_CTRL), -}; - -iomux_v3_cfg_t const enet_pads2[] = { MX6_PAD_RGMII_RXC__ENET_RGMII_RXC | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_RD0__ENET_RGMII_RD0 | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_RD1__ENET_RGMII_RD1 | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_RD2__ENET_RGMII_RD2 | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_RD3__ENET_RGMII_RD3 | MUX_PAD_CTRL(ENET_PAD_CTRL), MX6_PAD_RGMII_RX_CTL__RGMII_RX_CTL | MUX_PAD_CTRL(ENET_PAD_CTRL), + /* KSZ9031 PHY Reset */ + MX6_PAD_ENET_CRS_DV__GPIO_1_25 | MUX_PAD_CTRL(NO_PAD_CTRL), }; -#if 0 -/* wl1271 pads on nitrogen6x */ -iomux_v3_cfg_t const wl12xx_pads[] = { - (MX6_PAD_NANDF_CS1__GPIO_6_14 & ~MUX_PAD_CTRL_MASK) - | MUX_PAD_CTRL(WEAK_PULLDOWN), - (MX6_PAD_NANDF_CS2__GPIO_6_15 & ~MUX_PAD_CTRL_MASK) - | MUX_PAD_CTRL(OUTPUT_40OHM), - (MX6_PAD_NANDF_CS3__GPIO_6_16 & ~MUX_PAD_CTRL_MASK) - | MUX_PAD_CTRL(OUTPUT_40OHM), -}; -#define WL12XX_WL_IRQ_GP IMX_GPIO_NR(6, 14) -#define WL12XX_WL_ENABLE_GP IMX_GPIO_NR(6, 15) -#define WL12XX_BT_ENABLE_GP IMX_GPIO_NR(6, 16) - -/* Button assignments for J14 */ -static iomux_v3_cfg_t const button_pads[] = { - /* Menu */ - MX6_PAD_NANDF_D1__GPIO_2_1 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), - /* Back */ - MX6_PAD_NANDF_D2__GPIO_2_2 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), - /* Labelled Search (mapped to Power under Android) */ - MX6_PAD_NANDF_D3__GPIO_2_3 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), - /* Home */ - MX6_PAD_NANDF_D4__GPIO_2_4 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), - /* Volume Down */ - MX6_PAD_GPIO_19__GPIO_4_5 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), - /* Volume Up */ - MX6_PAD_GPIO_18__GPIO_7_13 | MUX_PAD_CTRL(BUTTON_PAD_CTRL), -}; -#endif - static void setup_iomux_enet(void) { - gpio_direction_output(IMX_GPIO_NR(1, 25), 0); /* Apalis iMX6 PHY rst */ - gpio_direction_output(IMX_GPIO_NR(6, 30), 1); - gpio_direction_output(IMX_GPIO_NR(6, 25), 1); - gpio_direction_output(IMX_GPIO_NR(6, 27), 1); - gpio_direction_output(IMX_GPIO_NR(6, 28), 1); - gpio_direction_output(IMX_GPIO_NR(6, 29), 1); - imx_iomux_v3_setup_multiple_pads(enet_pads1, ARRAY_SIZE(enet_pads1)); - gpio_direction_output(IMX_GPIO_NR(6, 24), 1); - - /* Need delay 10ms according to KSZ9031 spec */ - udelay(1000 * 10); - gpio_set_value(IMX_GPIO_NR(1, 25), 1); /* Apalis iMX6 PHY reset */ - udelay(1); /* strapping hold time > 5ns */ - imx_iomux_v3_setup_multiple_pads(enet_pads2, ARRAY_SIZE(enet_pads2)); - udelay(1); + imx_iomux_v3_setup_multiple_pads(enet_pads, ARRAY_SIZE(enet_pads)); + + /* Reset KSZ9031 PHY */ + gpio_direction_output(IMX_GPIO_NR(1, 25) , 0); + mdelay(10); + gpio_set_value(IMX_GPIO_NR(1, 25), 1); } iomux_v3_cfg_t const usb_pads[] = { @@ -358,36 +335,13 @@ int board_mmc_init(bd_t *bis) return status; } #endif -#ifdef CONFIG_MXC_SPI -iomux_v3_cfg_t const ecspi1_pads[] = { - /* SS1 */ - MX6_PAD_EIM_D19__GPIO_3_19 | MUX_PAD_CTRL(SPI_PAD_CTRL), - MX6_PAD_EIM_D17__ECSPI1_MISO | MUX_PAD_CTRL(SPI_PAD_CTRL), - MX6_PAD_EIM_D18__ECSPI1_MOSI | MUX_PAD_CTRL(SPI_PAD_CTRL), - MX6_PAD_EIM_D16__ECSPI1_SCLK | MUX_PAD_CTRL(SPI_PAD_CTRL), -}; -void setup_spi(void) -{ - imx_iomux_v3_setup_multiple_pads(ecspi1_pads, - ARRAY_SIZE(ecspi1_pads)); -} -#endif int board_phy_config(struct phy_device *phydev) { -#ifdef TODO - /* min rx data delay */ - ksz9021_phy_extended_write(phydev, - MII_KSZ9021_EXT_RGMII_RX_DATA_SKEW, 0x0); - /* min tx data delay */ - ksz9021_phy_extended_write(phydev, - MII_KSZ9021_EXT_RGMII_TX_DATA_SKEW, 0x0); - /* max rx/tx clock delay, min rx/tx control */ - ksz9021_phy_extended_write(phydev, - MII_KSZ9021_EXT_RGMII_CLOCK_SKEW, 0xf0f0); + mx6_rgmii_rework(phydev); if (phydev->drv->config) phydev->drv->config(phydev); -#endif + return 0; } @@ -421,15 +375,8 @@ int board_eth_init(bd_t *bis) #endif return 0; } -#if TODO -static void setup_buttons(void) -{ - imx_iomux_v3_setup_multiple_pads(button_pads, - ARRAY_SIZE(button_pads)); -} -#endif -#ifdef CONFIG_CMD_SATA +#ifdef CONFIG_CMD_SATA int setup_sata(void) { struct iomuxc_base_regs *const iomuxc_regs @@ -791,15 +738,6 @@ int board_early_init_f(void) { setup_iomux_uart(); -#if 0 - /* Disable wl1271 For Nitrogen6w */ - gpio_direction_input(WL12XX_WL_IRQ_GP); - gpio_direction_output(WL12XX_WL_ENABLE_GP, 0); - gpio_direction_output(WL12XX_BT_ENABLE_GP, 0); - imx_iomux_v3_setup_multiple_pads(wl12xx_pads, ARRAY_SIZE(wl12xx_pads)); - setup_buttons(); -#endif - #if defined(CONFIG_VIDEO_IPUV3) setup_display(); #endif @@ -820,10 +758,6 @@ int board_init(void) /* address of boot parameters */ gd->bd->bi_boot_params = PHYS_SDRAM + 0x100; -#ifdef CONFIG_MXC_SPI - setup_spi(); -#endif -# setup_i2c(0, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info1); setup_i2c(1, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info_loc); setup_i2c(2, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info3); @@ -842,89 +776,6 @@ int checkboard(void) puts("Board: Toradex Apalis iMX6\n"); return 0; } -#if TODO -struct button_key { - char const *name; - unsigned gpnum; - char ident; -}; - -static struct button_key const buttons[] = { - {"back", IMX_GPIO_NR(2, 2), 'B'}, - {"home", IMX_GPIO_NR(2, 4), 'H'}, - {"menu", IMX_GPIO_NR(2, 1), 'M'}, - {"search", IMX_GPIO_NR(2, 3), 'S'}, - {"volup", IMX_GPIO_NR(7, 13), 'V'}, - {"voldown", IMX_GPIO_NR(4, 5), 'v'}, -}; - -/* - * generate a null-terminated string containing the buttons pressed - * returns number of keys pressed - */ -static int read_keys(char *buf) -{ - int i, numpressed = 0; - for (i = 0; i < ARRAY_SIZE(buttons); i++) { - if (!gpio_get_value(buttons[i].gpnum)) - buf[numpressed++] = buttons[i].ident; - } - buf[numpressed] = '\0'; - return numpressed; -} - -static int do_kbd(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) -{ - char envvalue[ARRAY_SIZE(buttons)+1]; - int numpressed = read_keys(envvalue); - setenv("keybd", envvalue); - return numpressed == 0; -} - -U_BOOT_CMD( - kbd, 1, 1, do_kbd, - "Tests for keypresses, sets 'keybd' environment variable", - "Returns 0 (true) to shell if key is pressed." -); -#endif -#ifdef CONFIG_PREBOOT -static char const kbd_magic_prefix[] = "key_magic"; -static char const kbd_command_prefix[] = "key_cmd"; - -static void preboot_keys(void) -{ - int numpressed; - char keypress[ARRAY_SIZE(buttons)+1]; - numpressed = read_keys(keypress); - if (numpressed) { - char *kbd_magic_keys = getenv("magic_keys"); - char *suffix; - /* - * loop over all magic keys - */ - for (suffix = kbd_magic_keys; *suffix; ++suffix) { - char *keys; - char magic[sizeof(kbd_magic_prefix) + 1]; - sprintf(magic, "%s%c", kbd_magic_prefix, *suffix); - keys = getenv(magic); - if (keys) { - if (!strcmp(keys, keypress)) - break; - } - } - if (*suffix) { - char cmd_name[sizeof(kbd_command_prefix) + 1]; - char *cmd; - sprintf(cmd_name, "%s%c", kbd_command_prefix, *suffix); - cmd = getenv(cmd_name); - if (cmd) { - setenv("preboot", cmd); - return; - } - } - } -} -#endif #ifdef CONFIG_CMD_BMODE static const struct boot_mode board_boot_modes[] = { @@ -937,10 +788,6 @@ static const struct boot_mode board_boot_modes[] = { int misc_init_r(void) { -#ifdef CONFIG_PREBOOT - preboot_keys(); -#endif - #ifdef CONFIG_CMD_BMODE add_board_boot_modes(board_boot_modes); #endif diff --git a/include/micrel.h b/include/micrel.h index e1c62d83cb..04c9ecf3bf 100644 --- a/include/micrel.h +++ b/include/micrel.h @@ -15,6 +15,11 @@ #define MII_KSZ9031_MOD_DATA_POST_INC_RW 0x8000 #define MII_KSZ9031_MOD_DATA_POST_INC_W 0xC000 +#define MII_KSZ9031_EXT_RGMII_CTRL_SIG_SKEW 0x4 +#define MII_KSZ9031_EXT_RGMII_RX_DATA_SKEW 0x5 +#define MII_KSZ9031_EXT_RGMII_TX_DATA_SKEW 0x6 +#define MII_KSZ9031_EXT_RGMII_CLOCK_SKEW 0x8 + struct phy_device; int ksz9021_phy_extended_write(struct phy_device *phydev, int regnum, u16 val); int ksz9021_phy_extended_read(struct phy_device *phydev, int regnum); -- cgit v1.2.3