uboot/board/gateworks/gw_ventana/gw_ventana.c
<<
>>
Prefs
   1/*
   2 * Copyright (C) 2013 Gateworks Corporation
   3 *
   4 * Author: Tim Harvey <tharvey@gateworks.com>
   5 *
   6 * SPDX-License-Identifier: GPL-2.0+
   7 */
   8
   9#include <common.h>
  10#include <asm/arch/clock.h>
  11#include <asm/arch/crm_regs.h>
  12#include <asm/arch/iomux.h>
  13#include <asm/arch/mx6-pins.h>
  14#include <asm/arch/mxc_hdmi.h>
  15#include <asm/arch/sys_proto.h>
  16#include <asm/gpio.h>
  17#include <asm/imx-common/boot_mode.h>
  18#include <asm/imx-common/sata.h>
  19#include <asm/imx-common/spi.h>
  20#include <asm/imx-common/video.h>
  21#include <asm/io.h>
  22#include <dm.h>
  23#include <dm/platform_data/serial_mxc.h>
  24#include <i2c.h>
  25#include <fdt_support.h>
  26#include <fsl_esdhc.h>
  27#include <jffs2/load_kernel.h>
  28#include <linux/ctype.h>
  29#include <miiphy.h>
  30#include <mtd_node.h>
  31#include <netdev.h>
  32#include <pci.h>
  33#include <power/pmic.h>
  34#include <power/ltc3676_pmic.h>
  35#include <power/pfuze100_pmic.h>
  36#include <fdt_support.h>
  37#include <jffs2/load_kernel.h>
  38#include <spi_flash.h>
  39
  40#include "gsc.h"
  41#include "common.h"
  42
  43DECLARE_GLOBAL_DATA_PTR;
  44
  45
  46/*
  47 * EEPROM board info struct populated by read_eeprom so that we only have to
  48 * read it once.
  49 */
  50struct ventana_board_info ventana_info;
  51
  52static int board_type;
  53
  54/* MMC */
  55static iomux_v3_cfg_t const usdhc3_pads[] = {
  56        IOMUX_PADS(PAD_SD3_CLK__SD3_CLK    | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  57        IOMUX_PADS(PAD_SD3_CMD__SD3_CMD    | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  58        IOMUX_PADS(PAD_SD3_DAT0__SD3_DATA0 | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  59        IOMUX_PADS(PAD_SD3_DAT1__SD3_DATA1 | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  60        IOMUX_PADS(PAD_SD3_DAT2__SD3_DATA2 | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  61        IOMUX_PADS(PAD_SD3_DAT3__SD3_DATA3 | MUX_PAD_CTRL(USDHC_PAD_CTRL)),
  62        /* CD */
  63        IOMUX_PADS(PAD_SD3_DAT5__GPIO7_IO00  | MUX_PAD_CTRL(IRQ_PAD_CTRL)),
  64};
  65
  66/* ENET */
  67static iomux_v3_cfg_t const enet_pads[] = {
  68        IOMUX_PADS(PAD_ENET_MDIO__ENET_MDIO  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  69        IOMUX_PADS(PAD_ENET_MDC__ENET_MDC    | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  70        IOMUX_PADS(PAD_RGMII_TXC__RGMII_TXC  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  71        IOMUX_PADS(PAD_RGMII_TD0__RGMII_TD0  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  72        IOMUX_PADS(PAD_RGMII_TD1__RGMII_TD1  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  73        IOMUX_PADS(PAD_RGMII_TD2__RGMII_TD2  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  74        IOMUX_PADS(PAD_RGMII_TD3__RGMII_TD3  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  75        IOMUX_PADS(PAD_RGMII_TX_CTL__RGMII_TX_CTL |
  76                   MUX_PAD_CTRL(ENET_PAD_CTRL)),
  77        IOMUX_PADS(PAD_ENET_REF_CLK__ENET_TX_CLK |
  78                   MUX_PAD_CTRL(ENET_PAD_CTRL)),
  79        IOMUX_PADS(PAD_RGMII_RXC__RGMII_RXC  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  80        IOMUX_PADS(PAD_RGMII_RD0__RGMII_RD0  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  81        IOMUX_PADS(PAD_RGMII_RD1__RGMII_RD1  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  82        IOMUX_PADS(PAD_RGMII_RD2__RGMII_RD2  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  83        IOMUX_PADS(PAD_RGMII_RD3__RGMII_RD3  | MUX_PAD_CTRL(ENET_PAD_CTRL)),
  84        IOMUX_PADS(PAD_RGMII_RX_CTL__RGMII_RX_CTL |
  85                   MUX_PAD_CTRL(ENET_PAD_CTRL)),
  86        /* PHY nRST */
  87        IOMUX_PADS(PAD_ENET_TXD0__GPIO1_IO30 | DIO_PAD_CFG),
  88};
  89
  90/* NAND */
  91static iomux_v3_cfg_t const nfc_pads[] = {
  92        IOMUX_PADS(PAD_NANDF_CLE__NAND_CLE     | MUX_PAD_CTRL(NO_PAD_CTRL)),
  93        IOMUX_PADS(PAD_NANDF_ALE__NAND_ALE     | MUX_PAD_CTRL(NO_PAD_CTRL)),
  94        IOMUX_PADS(PAD_NANDF_WP_B__NAND_WP_B   | MUX_PAD_CTRL(NO_PAD_CTRL)),
  95        IOMUX_PADS(PAD_NANDF_RB0__NAND_READY_B | MUX_PAD_CTRL(NO_PAD_CTRL)),
  96        IOMUX_PADS(PAD_NANDF_CS0__NAND_CE0_B   | MUX_PAD_CTRL(NO_PAD_CTRL)),
  97        IOMUX_PADS(PAD_SD4_CMD__NAND_RE_B      | MUX_PAD_CTRL(NO_PAD_CTRL)),
  98        IOMUX_PADS(PAD_SD4_CLK__NAND_WE_B      | MUX_PAD_CTRL(NO_PAD_CTRL)),
  99        IOMUX_PADS(PAD_NANDF_D0__NAND_DATA00   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 100        IOMUX_PADS(PAD_NANDF_D1__NAND_DATA01   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 101        IOMUX_PADS(PAD_NANDF_D2__NAND_DATA02   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 102        IOMUX_PADS(PAD_NANDF_D3__NAND_DATA03   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 103        IOMUX_PADS(PAD_NANDF_D4__NAND_DATA04   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 104        IOMUX_PADS(PAD_NANDF_D5__NAND_DATA05   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 105        IOMUX_PADS(PAD_NANDF_D6__NAND_DATA06   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 106        IOMUX_PADS(PAD_NANDF_D7__NAND_DATA07   | MUX_PAD_CTRL(NO_PAD_CTRL)),
 107};
 108
 109#ifdef CONFIG_CMD_NAND
 110static void setup_gpmi_nand(void)
 111{
 112        struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
 113
 114        /* config gpmi nand iomux */
 115        SETUP_IOMUX_PADS(nfc_pads);
 116
 117        /* config gpmi and bch clock to 100 MHz */
 118        clrsetbits_le32(&mxc_ccm->cs2cdr,
 119                        MXC_CCM_CS2CDR_ENFC_CLK_PODF_MASK |
 120                        MXC_CCM_CS2CDR_ENFC_CLK_PRED_MASK |
 121                        MXC_CCM_CS2CDR_ENFC_CLK_SEL_MASK,
 122                        MXC_CCM_CS2CDR_ENFC_CLK_PODF(0) |
 123                        MXC_CCM_CS2CDR_ENFC_CLK_PRED(3) |
 124                        MXC_CCM_CS2CDR_ENFC_CLK_SEL(3));
 125
 126        /* enable gpmi and bch clock gating */
 127        setbits_le32(&mxc_ccm->CCGR4,
 128                     MXC_CCM_CCGR4_RAWNAND_U_BCH_INPUT_APB_MASK |
 129                     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_BCH_MASK |
 130                     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_GPMI_IO_MASK |
 131                     MXC_CCM_CCGR4_RAWNAND_U_GPMI_INPUT_APB_MASK |
 132                     MXC_CCM_CCGR4_PL301_MX6QPER1_BCH_OFFSET);
 133
 134        /* enable apbh clock gating */
 135        setbits_le32(&mxc_ccm->CCGR0, MXC_CCM_CCGR0_APBHDMA_MASK);
 136}
 137#endif
 138
 139static void setup_iomux_enet(int gpio)
 140{
 141        SETUP_IOMUX_PADS(enet_pads);
 142
 143        /* toggle PHY_RST# */
 144        gpio_request(gpio, "phy_rst#");
 145        gpio_direction_output(gpio, 0);
 146        mdelay(2);
 147        gpio_set_value(gpio, 1);
 148}
 149
 150#ifdef CONFIG_USB_EHCI_MX6
 151static iomux_v3_cfg_t const usb_pads[] = {
 152        IOMUX_PADS(PAD_GPIO_1__USB_OTG_ID   | DIO_PAD_CFG),
 153        IOMUX_PADS(PAD_KEY_COL4__USB_OTG_OC | DIO_PAD_CFG),
 154        /* OTG PWR */
 155        IOMUX_PADS(PAD_EIM_D22__GPIO3_IO22  | DIO_PAD_CFG),
 156};
 157
 158int board_ehci_hcd_init(int port)
 159{
 160        int gpio;
 161
 162        SETUP_IOMUX_PADS(usb_pads);
 163
 164        /* Reset USB HUB */
 165        switch (board_type) {
 166        case GW53xx:
 167        case GW552x:
 168                gpio = (IMX_GPIO_NR(1, 9));
 169                break;
 170        case GW54proto:
 171        case GW54xx:
 172                gpio = (IMX_GPIO_NR(1, 16));
 173                break;
 174        default:
 175                return 0;
 176        }
 177
 178        /* request and toggle hub rst */
 179        gpio_request(gpio, "usb_hub_rst#");
 180        gpio_direction_output(gpio, 0);
 181        mdelay(2);
 182        gpio_set_value(gpio, 1);
 183
 184        return 0;
 185}
 186
 187int board_ehci_power(int port, int on)
 188{
 189        if (port)
 190                return 0;
 191        gpio_set_value(GP_USB_OTG_PWR, on);
 192        return 0;
 193}
 194#endif /* CONFIG_USB_EHCI_MX6 */
 195
 196#ifdef CONFIG_FSL_ESDHC
 197static struct fsl_esdhc_cfg usdhc_cfg = { USDHC3_BASE_ADDR };
 198
 199int board_mmc_getcd(struct mmc *mmc)
 200{
 201        /* Card Detect */
 202        gpio_request(GP_SD3_CD, "sd_cd");
 203        gpio_direction_input(GP_SD3_CD);
 204        return !gpio_get_value(GP_SD3_CD);
 205}
 206
 207int board_mmc_init(bd_t *bis)
 208{
 209        /* Only one USDHC controller on Ventana */
 210        SETUP_IOMUX_PADS(usdhc3_pads);
 211        usdhc_cfg.sdhc_clk = mxc_get_clock(MXC_ESDHC3_CLK);
 212        usdhc_cfg.max_bus_width = 4;
 213
 214        return fsl_esdhc_initialize(bis, &usdhc_cfg);
 215}
 216#endif /* CONFIG_FSL_ESDHC */
 217
 218#ifdef CONFIG_MXC_SPI
 219iomux_v3_cfg_t const ecspi1_pads[] = {
 220        /* SS1 */
 221        IOMUX_PADS(PAD_EIM_D19__GPIO3_IO19  | MUX_PAD_CTRL(SPI_PAD_CTRL)),
 222        IOMUX_PADS(PAD_EIM_D17__ECSPI1_MISO | MUX_PAD_CTRL(SPI_PAD_CTRL)),
 223        IOMUX_PADS(PAD_EIM_D18__ECSPI1_MOSI | MUX_PAD_CTRL(SPI_PAD_CTRL)),
 224        IOMUX_PADS(PAD_EIM_D16__ECSPI1_SCLK | MUX_PAD_CTRL(SPI_PAD_CTRL)),
 225};
 226
 227int board_spi_cs_gpio(unsigned bus, unsigned cs)
 228{
 229        return (bus == 0 && cs == 0) ? (IMX_GPIO_NR(3, 19)) : -1;
 230}
 231
 232static void setup_spi(void)
 233{
 234        gpio_request(IMX_GPIO_NR(3, 19), "spi_cs");
 235        gpio_direction_output(IMX_GPIO_NR(3, 19), 1);
 236        SETUP_IOMUX_PADS(ecspi1_pads);
 237}
 238#endif
 239
 240/* configure eth0 PHY board-specific LED behavior */
 241int board_phy_config(struct phy_device *phydev)
 242{
 243        unsigned short val;
 244
 245        /* Marvel 88E1510 */
 246        if (phydev->phy_id == 0x1410dd1) {
 247                /*
 248                 * Page 3, Register 16: LED[2:0] Function Control Register
 249                 * LED[0] (SPD:Amber) R16_3.3:0 to 0111: on-GbE link
 250                 * LED[1] (LNK:Green) R16_3.7:4 to 0001: on-link, blink-activity
 251                 */
 252                phy_write(phydev, MDIO_DEVAD_NONE, 22, 3);
 253                val = phy_read(phydev, MDIO_DEVAD_NONE, 16);
 254                val &= 0xff00;
 255                val |= 0x0017;
 256                phy_write(phydev, MDIO_DEVAD_NONE, 16, val);
 257                phy_write(phydev, MDIO_DEVAD_NONE, 22, 0);
 258        }
 259
 260        if (phydev->drv->config)
 261                phydev->drv->config(phydev);
 262
 263        return 0;
 264}
 265
 266int board_eth_init(bd_t *bis)
 267{
 268#ifdef CONFIG_FEC_MXC
 269        if (board_type != GW551x && board_type != GW552x) {
 270                setup_iomux_enet(GP_PHY_RST);
 271                cpu_eth_init(bis);
 272        }
 273#endif
 274
 275#ifdef CONFIG_E1000
 276        e1000_initialize(bis);
 277#endif
 278
 279#ifdef CONFIG_CI_UDC
 280        /* For otg ethernet*/
 281        usb_eth_initialize(bis);
 282#endif
 283
 284        /* default to the first detected enet dev */
 285        if (!getenv("ethprime")) {
 286                struct eth_device *dev = eth_get_dev_by_index(0);
 287                if (dev) {
 288                        setenv("ethprime", dev->name);
 289                        printf("set ethprime to %s\n", getenv("ethprime"));
 290                }
 291        }
 292
 293        return 0;
 294}
 295
 296#if defined(CONFIG_VIDEO_IPUV3)
 297
 298static void enable_hdmi(struct display_info_t const *dev)
 299{
 300        imx_enable_hdmi_phy();
 301}
 302
 303static int detect_i2c(struct display_info_t const *dev)
 304{
 305        return i2c_set_bus_num(dev->bus) == 0 &&
 306                i2c_probe(dev->addr) == 0;
 307}
 308
 309static void enable_lvds(struct display_info_t const *dev)
 310{
 311        struct iomuxc *iomux = (struct iomuxc *)
 312                                IOMUXC_BASE_ADDR;
 313
 314        /* set CH0 data width to 24bit (IOMUXC_GPR2:5 0=18bit, 1=24bit) */
 315        u32 reg = readl(&iomux->gpr[2]);
 316        reg |= IOMUXC_GPR2_DATA_WIDTH_CH0_24BIT;
 317        writel(reg, &iomux->gpr[2]);
 318
 319        /* Enable Backlight */
 320        gpio_request(IMX_GPIO_NR(1, 18), "bklt_en");
 321        SETUP_IOMUX_PAD(PAD_SD1_CMD__GPIO1_IO18 | DIO_PAD_CFG);
 322        gpio_direction_output(IMX_GPIO_NR(1, 18), 1);
 323}
 324
 325struct display_info_t const displays[] = {{
 326        /* HDMI Output */
 327        .bus    = -1,
 328        .addr   = 0,
 329        .pixfmt = IPU_PIX_FMT_RGB24,
 330        .detect = detect_hdmi,
 331        .enable = enable_hdmi,
 332        .mode   = {
 333                .name           = "HDMI",
 334                .refresh        = 60,
 335                .xres           = 1024,
 336                .yres           = 768,
 337                .pixclock       = 15385,
 338                .left_margin    = 220,
 339                .right_margin   = 40,
 340                .upper_margin   = 21,
 341                .lower_margin   = 7,
 342                .hsync_len      = 60,
 343                .vsync_len      = 10,
 344                .sync           = FB_SYNC_EXT,
 345                .vmode          = FB_VMODE_NONINTERLACED
 346} }, {
 347        /* Freescale MXC-LVDS1: HannStar HSD100PXN1-A00 w/ egalx_ts cont */
 348        .bus    = 2,
 349        .addr   = 0x4,
 350        .pixfmt = IPU_PIX_FMT_LVDS666,
 351        .detect = detect_i2c,
 352        .enable = enable_lvds,
 353        .mode   = {
 354                .name           = "Hannstar-XGA",
 355                .refresh        = 60,
 356                .xres           = 1024,
 357                .yres           = 768,
 358                .pixclock       = 15385,
 359                .left_margin    = 220,
 360                .right_margin   = 40,
 361                .upper_margin   = 21,
 362                .lower_margin   = 7,
 363                .hsync_len      = 60,
 364                .vsync_len      = 10,
 365                .sync           = FB_SYNC_EXT,
 366                .vmode          = FB_VMODE_NONINTERLACED
 367} }, {
 368        /* DLC700JMG-T-4 */
 369        .bus    = 0,
 370        .addr   = 0,
 371        .detect = NULL,
 372        .enable = enable_lvds,
 373        .pixfmt = IPU_PIX_FMT_LVDS666,
 374        .mode   = {
 375                .name           = "DLC700JMGT4",
 376                .refresh        = 60,
 377                .xres           = 1024,         /* 1024x600active pixels */
 378                .yres           = 600,
 379                .pixclock       = 15385,        /* 64MHz */
 380                .left_margin    = 220,
 381                .right_margin   = 40,
 382                .upper_margin   = 21,
 383                .lower_margin   = 7,
 384                .hsync_len      = 60,
 385                .vsync_len      = 10,
 386                .sync           = FB_SYNC_EXT,
 387                .vmode          = FB_VMODE_NONINTERLACED
 388} }, {
 389        /* DLC800FIG-T-3 */
 390        .bus    = 0,
 391        .addr   = 0,
 392        .detect = NULL,
 393        .enable = enable_lvds,
 394        .pixfmt = IPU_PIX_FMT_LVDS666,
 395        .mode   = {
 396                .name           = "DLC800FIGT3",
 397                .refresh        = 60,
 398                .xres           = 1024,         /* 1024x768 active pixels */
 399                .yres           = 768,
 400                .pixclock       = 15385,        /* 64MHz */
 401                .left_margin    = 220,
 402                .right_margin   = 40,
 403                .upper_margin   = 21,
 404                .lower_margin   = 7,
 405                .hsync_len      = 60,
 406                .vsync_len      = 10,
 407                .sync           = FB_SYNC_EXT,
 408                .vmode          = FB_VMODE_NONINTERLACED
 409} } };
 410size_t display_count = ARRAY_SIZE(displays);
 411
 412static void setup_display(void)
 413{
 414        struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
 415        struct iomuxc *iomux = (struct iomuxc *)IOMUXC_BASE_ADDR;
 416        int reg;
 417
 418        enable_ipu_clock();
 419        imx_setup_hdmi();
 420        /* Turn on LDB0,IPU,IPU DI0 clocks */
 421        reg = __raw_readl(&mxc_ccm->CCGR3);
 422        reg |= MXC_CCM_CCGR3_LDB_DI0_MASK;
 423        writel(reg, &mxc_ccm->CCGR3);
 424
 425        /* set LDB0, LDB1 clk select to 011/011 */
 426        reg = readl(&mxc_ccm->cs2cdr);
 427        reg &= ~(MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_MASK
 428                 |MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_MASK);
 429        reg |= (3<<MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_OFFSET)
 430              |(3<<MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_OFFSET);
 431        writel(reg, &mxc_ccm->cs2cdr);
 432
 433        reg = readl(&mxc_ccm->cscmr2);
 434        reg |= MXC_CCM_CSCMR2_LDB_DI0_IPU_DIV;
 435        writel(reg, &mxc_ccm->cscmr2);
 436
 437        reg = readl(&mxc_ccm->chsccdr);
 438        reg |= (CHSCCDR_CLK_SEL_LDB_DI0
 439                <<MXC_CCM_CHSCCDR_IPU1_DI0_CLK_SEL_OFFSET);
 440        writel(reg, &mxc_ccm->chsccdr);
 441
 442        reg = IOMUXC_GPR2_BGREF_RRMODE_EXTERNAL_RES
 443             |IOMUXC_GPR2_DI1_VS_POLARITY_ACTIVE_HIGH
 444             |IOMUXC_GPR2_DI0_VS_POLARITY_ACTIVE_LOW
 445             |IOMUXC_GPR2_BIT_MAPPING_CH1_SPWG
 446             |IOMUXC_GPR2_DATA_WIDTH_CH1_18BIT
 447             |IOMUXC_GPR2_BIT_MAPPING_CH0_SPWG
 448             |IOMUXC_GPR2_DATA_WIDTH_CH0_18BIT
 449             |IOMUXC_GPR2_LVDS_CH1_MODE_DISABLED
 450             |IOMUXC_GPR2_LVDS_CH0_MODE_ENABLED_DI0;
 451        writel(reg, &iomux->gpr[2]);
 452
 453        reg = readl(&iomux->gpr[3]);
 454        reg = (reg & ~IOMUXC_GPR3_LVDS0_MUX_CTL_MASK)
 455            | (IOMUXC_GPR3_MUX_SRC_IPU1_DI0
 456               <<IOMUXC_GPR3_LVDS0_MUX_CTL_OFFSET);
 457        writel(reg, &iomux->gpr[3]);
 458
 459        /* Backlight CABEN on LVDS connector */
 460        gpio_request(IMX_GPIO_NR(1, 10), "bklt_gpio");
 461        SETUP_IOMUX_PAD(PAD_SD2_CLK__GPIO1_IO10 | DIO_PAD_CFG);
 462        gpio_direction_output(IMX_GPIO_NR(1, 10), 0);
 463}
 464#endif /* CONFIG_VIDEO_IPUV3 */
 465
 466/* setup board specific PMIC */
 467int power_init_board(void)
 468{
 469        setup_pmic();
 470        return 0;
 471}
 472
 473#if defined(CONFIG_CMD_PCI)
 474int imx6_pcie_toggle_reset(void)
 475{
 476        if (board_type < GW_UNKNOWN) {
 477                uint pin = gpio_cfg[board_type].pcie_rst;
 478                gpio_request(pin, "pci_rst#");
 479                gpio_direction_output(pin, 0);
 480                mdelay(50);
 481                gpio_direction_output(pin, 1);
 482        }
 483        return 0;
 484}
 485
 486/*
 487 * Most Ventana boards have a PLX PEX860x PCIe switch onboard and use its
 488 * GPIO's as PERST# signals for its downstream ports - configure the GPIO's
 489 * properly and assert reset for 100ms.
 490 */
 491void board_pci_fixup_dev(struct pci_controller *hose, pci_dev_t dev,
 492                         unsigned short vendor, unsigned short device,
 493                         unsigned short class)
 494{
 495        u32 dw;
 496
 497        debug("%s: %02d:%02d.%02d: %04x:%04x\n", __func__,
 498              PCI_BUS(dev), PCI_DEV(dev), PCI_FUNC(dev), vendor, device);
 499        if (vendor == PCI_VENDOR_ID_PLX &&
 500            (device & 0xfff0) == 0x8600 &&
 501            PCI_DEV(dev) == 0 && PCI_FUNC(dev) == 0) {
 502                debug("configuring PLX 860X downstream PERST#\n");
 503                pci_hose_read_config_dword(hose, dev, 0x62c, &dw);
 504                dw |= 0xaaa8; /* GPIO1-7 outputs */
 505                pci_hose_write_config_dword(hose, dev, 0x62c, dw);
 506
 507                pci_hose_read_config_dword(hose, dev, 0x644, &dw);
 508                dw |= 0xfe;   /* GPIO1-7 output high */
 509                pci_hose_write_config_dword(hose, dev, 0x644, dw);
 510
 511                mdelay(100);
 512        }
 513}
 514#endif /* CONFIG_CMD_PCI */
 515
 516#ifdef CONFIG_SERIAL_TAG
 517/*
 518 * called when setting up ATAGS before booting kernel
 519 * populate serialnum from the following (in order of priority):
 520 *   serial# env var
 521 *   eeprom
 522 */
 523void get_board_serial(struct tag_serialnr *serialnr)
 524{
 525        char *serial = getenv("serial#");
 526
 527        if (serial) {
 528                serialnr->high = 0;
 529                serialnr->low = simple_strtoul(serial, NULL, 10);
 530        } else if (ventana_info.model[0]) {
 531                serialnr->high = 0;
 532                serialnr->low = ventana_info.serial;
 533        } else {
 534                serialnr->high = 0;
 535                serialnr->low = 0;
 536        }
 537}
 538#endif
 539
 540/*
 541 * Board Support
 542 */
 543
 544int board_early_init_f(void)
 545{
 546        setup_iomux_uart();
 547
 548#if defined(CONFIG_VIDEO_IPUV3)
 549        setup_display();
 550#endif
 551        return 0;
 552}
 553
 554int dram_init(void)
 555{
 556        gd->ram_size = imx_ddr_size();
 557        return 0;
 558}
 559
 560int board_init(void)
 561{
 562        struct iomuxc *const iomuxc_regs = (struct iomuxc *)IOMUXC_BASE_ADDR;
 563
 564        clrsetbits_le32(&iomuxc_regs->gpr[1],
 565                        IOMUXC_GPR1_OTG_ID_MASK,
 566                        IOMUXC_GPR1_OTG_ID_GPIO1);
 567
 568        /* address of linux boot parameters */
 569        gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
 570
 571#ifdef CONFIG_CMD_NAND
 572        setup_gpmi_nand();
 573#endif
 574#ifdef CONFIG_MXC_SPI
 575        setup_spi();
 576#endif
 577        setup_ventana_i2c();
 578
 579#ifdef CONFIG_CMD_SATA
 580        setup_sata();
 581#endif
 582        /* read Gateworks EEPROM into global struct (used later) */
 583        board_type = read_eeprom(CONFIG_I2C_GSC, &ventana_info);
 584
 585        setup_iomux_gpio(board_type, &ventana_info);
 586
 587        return 0;
 588}
 589
 590#if defined(CONFIG_DISPLAY_BOARDINFO_LATE)
 591/*
 592 * called during late init (after relocation and after board_init())
 593 * by virtue of CONFIG_DISPLAY_BOARDINFO_LATE as we needed i2c initialized and
 594 * EEPROM read.
 595 */
 596int checkboard(void)
 597{
 598        struct ventana_board_info *info = &ventana_info;
 599        unsigned char buf[4];
 600        const char *p;
 601        int quiet; /* Quiet or minimal output mode */
 602
 603        quiet = 0;
 604        p = getenv("quiet");
 605        if (p)
 606                quiet = simple_strtol(p, NULL, 10);
 607        else
 608                setenv("quiet", "0");
 609
 610        puts("\nGateworks Corporation Copyright 2014\n");
 611        if (info->model[0]) {
 612                printf("Model: %s\n", info->model);
 613                printf("MFGDate: %02x-%02x-%02x%02x\n",
 614                       info->mfgdate[0], info->mfgdate[1],
 615                       info->mfgdate[2], info->mfgdate[3]);
 616                printf("Serial:%d\n", info->serial);
 617        } else {
 618                puts("Invalid EEPROM - board will not function fully\n");
 619        }
 620        if (quiet)
 621                return 0;
 622
 623        /* Display GSC firmware revision/CRC/status */
 624        gsc_info(0);
 625
 626        /* Display RTC */
 627        if (!gsc_i2c_read(GSC_RTC_ADDR, 0x00, 1, buf, 4)) {
 628                printf("RTC:   %d\n",
 629                       buf[0] | buf[1]<<8 | buf[2]<<16 | buf[3]<<24);
 630        }
 631
 632        return 0;
 633}
 634#endif
 635
 636#ifdef CONFIG_CMD_BMODE
 637/*
 638 * BOOT_CFG1, BOOT_CFG2, BOOT_CFG3, BOOT_CFG4
 639 * see Table 8-11 and Table 5-9
 640 *  BOOT_CFG1[7] = 1 (boot from NAND)
 641 *  BOOT_CFG1[5] = 0 - raw NAND
 642 *  BOOT_CFG1[4] = 0 - default pad settings
 643 *  BOOT_CFG1[3:2] = 00 - devices = 1
 644 *  BOOT_CFG1[1:0] = 00 - Row Address Cycles = 3
 645 *  BOOT_CFG2[4:3] = 00 - Boot Search Count = 2
 646 *  BOOT_CFG2[2:1] = 01 - Pages In Block = 64
 647 *  BOOT_CFG2[0] = 0 - Reset time 12ms
 648 */
 649static const struct boot_mode board_boot_modes[] = {
 650        /* NAND: 64pages per block, 3 row addr cycles, 2 copies of FCB/DBBT */
 651        { "nand", MAKE_CFGVAL(0x80, 0x02, 0x00, 0x00) },
 652        { NULL, 0 },
 653};
 654#endif
 655
 656/* late init */
 657int misc_init_r(void)
 658{
 659        struct ventana_board_info *info = &ventana_info;
 660
 661        /* set env vars based on EEPROM data */
 662        if (ventana_info.model[0]) {
 663                char str[16], fdt[36];
 664                char *p;
 665                const char *cputype = "";
 666                int i;
 667
 668                /*
 669                 * FDT name will be prefixed with CPU type.  Three versions
 670                 * will be created each increasingly generic and bootloader
 671                 * env scripts will try loading each from most specific to
 672                 * least.
 673                 */
 674                if (is_cpu_type(MXC_CPU_MX6Q) ||
 675                    is_cpu_type(MXC_CPU_MX6D))
 676                        cputype = "imx6q";
 677                else if (is_cpu_type(MXC_CPU_MX6DL) ||
 678                         is_cpu_type(MXC_CPU_MX6SOLO))
 679                        cputype = "imx6dl";
 680                setenv("soctype", cputype);
 681                if (8 << (ventana_info.nand_flash_size-1) >= 2048)
 682                        setenv("flash_layout", "large");
 683                else
 684                        setenv("flash_layout", "normal");
 685                memset(str, 0, sizeof(str));
 686                for (i = 0; i < (sizeof(str)-1) && info->model[i]; i++)
 687                        str[i] = tolower(info->model[i]);
 688                setenv("model", str);
 689                if (!getenv("fdt_file")) {
 690                        sprintf(fdt, "%s-%s.dtb", cputype, str);
 691                        setenv("fdt_file", fdt);
 692                }
 693                p = strchr(str, '-');
 694                if (p) {
 695                        *p++ = 0;
 696
 697                        setenv("model_base", str);
 698                        sprintf(fdt, "%s-%s.dtb", cputype, str);
 699                        setenv("fdt_file1", fdt);
 700                        if (board_type != GW551x && board_type != GW552x)
 701                                str[4] = 'x';
 702                        str[5] = 'x';
 703                        str[6] = 0;
 704                        sprintf(fdt, "%s-%s.dtb", cputype, str);
 705                        setenv("fdt_file2", fdt);
 706                }
 707
 708                /* initialize env from EEPROM */
 709                if (test_bit(EECONFIG_ETH0, info->config) &&
 710                    !getenv("ethaddr")) {
 711                        eth_setenv_enetaddr("ethaddr", info->mac0);
 712                }
 713                if (test_bit(EECONFIG_ETH1, info->config) &&
 714                    !getenv("eth1addr")) {
 715                        eth_setenv_enetaddr("eth1addr", info->mac1);
 716                }
 717
 718                /* board serial-number */
 719                sprintf(str, "%6d", info->serial);
 720                setenv("serial#", str);
 721
 722                /* memory MB */
 723                sprintf(str, "%d", (int) (gd->ram_size >> 20));
 724                setenv("mem_mb", str);
 725        }
 726
 727
 728        /* setup baseboard specific GPIO based on board and env */
 729        setup_board_gpio(board_type, info);
 730
 731#ifdef CONFIG_CMD_BMODE
 732        add_board_boot_modes(board_boot_modes);
 733#endif
 734
 735        /* disable boot watchdog */
 736        gsc_boot_wd_disable();
 737
 738        return 0;
 739}
 740
 741#if defined(CONFIG_OF_LIBFDT) && defined(CONFIG_OF_BOARD_SETUP)
 742
 743static int ft_sethdmiinfmt(void *blob, char *mode)
 744{
 745        int off;
 746
 747        if (!mode)
 748                return -EINVAL;
 749
 750        off = fdt_node_offset_by_compatible(blob, -1, "nxp,tda1997x");
 751        if (off < 0)
 752                return off;
 753
 754        if (0 == strcasecmp(mode, "yuv422bt656")) {
 755                u8 cfg[] = { 0x00, 0x00, 0x00, 0x82, 0x81, 0x00,
 756                             0x00, 0x00, 0x00 };
 757                mode = "422_ccir";
 758                fdt_setprop(blob, off, "vidout_fmt", mode, strlen(mode) + 1);
 759                fdt_setprop_u32(blob, off, "vidout_trc", 1);
 760                fdt_setprop_u32(blob, off, "vidout_blc", 1);
 761                fdt_setprop(blob, off, "vidout_portcfg", cfg, sizeof(cfg));
 762                printf("   set HDMI input mode to %s\n", mode);
 763        } else if (0 == strcasecmp(mode, "yuv422smp")) {
 764                u8 cfg[] = { 0x00, 0x00, 0x00, 0x88, 0x87, 0x00,
 765                             0x82, 0x81, 0x00 };
 766                mode = "422_smp";
 767                fdt_setprop(blob, off, "vidout_fmt", mode, strlen(mode) + 1);
 768                fdt_setprop_u32(blob, off, "vidout_trc", 0);
 769                fdt_setprop_u32(blob, off, "vidout_blc", 0);
 770                fdt_setprop(blob, off, "vidout_portcfg", cfg, sizeof(cfg));
 771                printf("   set HDMI input mode to %s\n", mode);
 772        } else {
 773                return -EINVAL;
 774        }
 775
 776        return 0;
 777}
 778
 779/*
 780 * called prior to booting kernel or by 'fdt boardsetup' command
 781 *
 782 * unless 'fdt_noauto' env var is set we will update the following in the DTB:
 783 *  - mtd partitions based on mtdparts/mtdids env
 784 *  - system-serial (board serial num from EEPROM)
 785 *  - board (full model from EEPROM)
 786 *  - peripherals removed from DTB if not loaded on board (per EEPROM config)
 787 */
 788int ft_board_setup(void *blob, bd_t *bd)
 789{
 790        struct ventana_board_info *info = &ventana_info;
 791        struct ventana_eeprom_config *cfg;
 792        struct node_info nodes[] = {
 793                { "sst,w25q256",          MTD_DEV_TYPE_NOR, },  /* SPI flash */
 794                { "fsl,imx6q-gpmi-nand",  MTD_DEV_TYPE_NAND, }, /* NAND flash */
 795        };
 796        const char *model = getenv("model");
 797        const char *display = getenv("display");
 798        int i;
 799        char rev = 0;
 800
 801        /* determine board revision */
 802        for (i = sizeof(ventana_info.model) - 1; i > 0; i--) {
 803                if (ventana_info.model[i] >= 'A') {
 804                        rev = ventana_info.model[i];
 805                        break;
 806                }
 807        }
 808
 809        if (getenv("fdt_noauto")) {
 810                puts("   Skiping ft_board_setup (fdt_noauto defined)\n");
 811                return 0;
 812        }
 813
 814        if (test_bit(EECONFIG_NAND, info->config)) {
 815                /* Update partition nodes using info from mtdparts env var */
 816                puts("   Updating MTD partitions...\n");
 817                fdt_fixup_mtdparts(blob, nodes, ARRAY_SIZE(nodes));
 818        }
 819
 820        /* Update display timings from display env var */
 821        if (display) {
 822                if (fdt_fixup_display(blob, fdt_get_alias(blob, "lvds0"),
 823                                      display) >= 0)
 824                        printf("   Set display timings for %s...\n", display);
 825        }
 826
 827        printf("   Adjusting FDT per EEPROM for %s...\n", model);
 828
 829        /* board serial number */
 830        fdt_setprop(blob, 0, "system-serial", getenv("serial#"),
 831                    strlen(getenv("serial#")) + 1);
 832
 833        /* board (model contains model from device-tree) */
 834        fdt_setprop(blob, 0, "board", info->model,
 835                    strlen((const char *)info->model) + 1);
 836
 837        /* set desired digital video capture format */
 838        ft_sethdmiinfmt(blob, getenv("hdmiinfmt"));
 839
 840        /*
 841         * disable serial2 node for GW54xx for compatibility with older
 842         * 3.10.x kernel that improperly had this node enabled in the DT
 843         */
 844        if (board_type == GW54xx) {
 845                i = fdt_path_offset(blob,
 846                                    "/soc/aips-bus@02100000/serial@021ec000");
 847                if (i)
 848                        fdt_del_node(blob, i);
 849        }
 850
 851        /*
 852         * disable wdog1/wdog2 nodes for GW51xx below revC to work around
 853         * errata causing wdog timer to be unreliable.
 854         */
 855        if (board_type == GW51xx && rev >= 'A' && rev < 'C') {
 856                i = fdt_path_offset(blob,
 857                                    "/soc/aips-bus@02000000/wdog@020bc000");
 858                if (i)
 859                        fdt_status_disabled(blob, i);
 860        }
 861
 862        /* GW522x Uses GPIO3_IO23 instead of GPIO1_IO29 */
 863        else if (board_type == GW52xx && info->model[4] == '2') {
 864                u32 handle = 0;
 865                u32 *range = NULL;
 866
 867                i = fdt_node_offset_by_compatible(blob, -1, "fsl,imx6q-pcie");
 868                if (i)
 869                        range = (u32 *)fdt_getprop(blob, i, "reset-gpio",
 870                                                   NULL);
 871
 872                if (range) {
 873                        i = fdt_path_offset(blob,
 874                                            "/soc/aips-bus@02000000/gpio@020a4000");
 875                        if (i)
 876                                handle = fdt_get_phandle(blob, i);
 877                        if (handle) {
 878                                range[0] = cpu_to_fdt32(handle);
 879                                range[1] = cpu_to_fdt32(23);
 880                        }
 881                }
 882        }
 883
 884        /*
 885         * isolate CSI0_DATA_EN for GW551x below revB to work around
 886         * errata causing non functional digital video in (it is not hooked up)
 887         */
 888        else if (board_type == GW551x && rev == 'A') {
 889                u32 *range = NULL;
 890                int len;
 891                const u32 *handle = NULL;
 892
 893                i = fdt_node_offset_by_compatible(blob, -1,
 894                                                  "fsl,imx-tda1997x-video");
 895                if (i)
 896                        handle = fdt_getprop(blob, i, "pinctrl-0", NULL);
 897                if (handle)
 898                        i = fdt_node_offset_by_phandle(blob,
 899                                                       fdt32_to_cpu(*handle));
 900                if (i)
 901                        range = (u32 *)fdt_getprop(blob, i, "fsl,pins", &len);
 902                if (range) {
 903                        len /= sizeof(u32);
 904                        for (i = 0; i < len; i += 6) {
 905                                u32 mux_reg = fdt32_to_cpu(range[i+0]);
 906                                u32 conf_reg = fdt32_to_cpu(range[i+1]);
 907                                /* mux PAD_CSI0_DATA_EN to GPIO */
 908                                if (is_cpu_type(MXC_CPU_MX6Q) &&
 909                                    mux_reg == 0x260 && conf_reg == 0x630)
 910                                        range[i+3] = cpu_to_fdt32(0x5);
 911                                else if (!is_cpu_type(MXC_CPU_MX6Q) &&
 912                                    mux_reg == 0x08c && conf_reg == 0x3a0)
 913                                        range[i+3] = cpu_to_fdt32(0x5);
 914                        }
 915                        fdt_setprop_inplace(blob, i, "fsl,pins", range, len);
 916                }
 917
 918                /* set BT656 video format */
 919                ft_sethdmiinfmt(blob, "yuv422bt656");
 920        }
 921
 922        /*
 923         * Peripheral Config:
 924         *  remove nodes by alias path if EEPROM config tells us the
 925         *  peripheral is not loaded on the board.
 926         */
 927        if (getenv("fdt_noconfig")) {
 928                puts("   Skiping periperhal config (fdt_noconfig defined)\n");
 929                return 0;
 930        }
 931        cfg = econfig;
 932        while (cfg->name) {
 933                if (!test_bit(cfg->bit, info->config)) {
 934                        fdt_del_node_and_alias(blob, cfg->dtalias ?
 935                                               cfg->dtalias : cfg->name);
 936                }
 937                cfg++;
 938        }
 939
 940        return 0;
 941}
 942#endif /* defined(CONFIG_OF_FLAT_TREE) && defined(CONFIG_OF_BOARD_SETUP) */
 943
 944static struct mxc_serial_platdata ventana_mxc_serial_plat = {
 945        .reg = (struct mxc_uart *)UART2_BASE,
 946};
 947
 948U_BOOT_DEVICE(ventana_serial) = {
 949        .name   = "serial_mxc",
 950        .platdata = &ventana_mxc_serial_plat,
 951};
 952