uboot/board/grinn/liteboard/board.c
<<
>>
Prefs
   1/*
   2 * Copyright (C) 2015-2016 Freescale Semiconductor, Inc.
   3 * Copyright (C) 2016 Grinn
   4 *
   5 * SPDX-License-Identifier:     GPL-2.0+
   6 */
   7
   8#include <asm/arch/clock.h>
   9#include <asm/arch/iomux.h>
  10#include <asm/arch/imx-regs.h>
  11#include <asm/arch/crm_regs.h>
  12#include <asm/arch/litesom.h>
  13#include <asm/arch/mx6ul_pins.h>
  14#include <asm/arch/mx6-pins.h>
  15#include <asm/arch/sys_proto.h>
  16#include <asm/gpio.h>
  17#include <asm/mach-imx/iomux-v3.h>
  18#include <asm/mach-imx/boot_mode.h>
  19#include <asm/io.h>
  20#include <common.h>
  21#include <fsl_esdhc.h>
  22#include <linux/sizes.h>
  23#include <linux/fb.h>
  24#include <miiphy.h>
  25#include <mmc.h>
  26#include <netdev.h>
  27#include <spl.h>
  28#include <usb.h>
  29#include <usb/ehci-ci.h>
  30
  31DECLARE_GLOBAL_DATA_PTR;
  32
  33#define UART_PAD_CTRL  (PAD_CTL_PKE | PAD_CTL_PUE |             \
  34        PAD_CTL_PUS_100K_UP | PAD_CTL_SPEED_MED |               \
  35        PAD_CTL_DSE_40ohm   | PAD_CTL_SRE_FAST  | PAD_CTL_HYS)
  36
  37#define USDHC_PAD_CTRL (PAD_CTL_PKE | PAD_CTL_PUE |             \
  38        PAD_CTL_PUS_22K_UP  | PAD_CTL_SPEED_LOW |               \
  39        PAD_CTL_DSE_80ohm   | PAD_CTL_SRE_FAST  | PAD_CTL_HYS)
  40
  41#define ENET_PAD_CTRL  (PAD_CTL_PUS_100K_UP | PAD_CTL_PUE |     \
  42        PAD_CTL_SPEED_HIGH   |                                   \
  43        PAD_CTL_DSE_48ohm   | PAD_CTL_SRE_FAST)
  44
  45#define MDIO_PAD_CTRL  (PAD_CTL_PUS_100K_UP | PAD_CTL_PUE |     \
  46        PAD_CTL_DSE_48ohm   | PAD_CTL_SRE_FAST | PAD_CTL_ODE)
  47
  48#define ENET_CLK_PAD_CTRL  (PAD_CTL_DSE_40ohm   | PAD_CTL_SRE_FAST)
  49
  50static iomux_v3_cfg_t const uart1_pads[] = {
  51        MX6_PAD_UART1_TX_DATA__UART1_DCE_TX | MUX_PAD_CTRL(UART_PAD_CTRL),
  52        MX6_PAD_UART1_RX_DATA__UART1_DCE_RX | MUX_PAD_CTRL(UART_PAD_CTRL),
  53};
  54
  55static iomux_v3_cfg_t const sd_pads[] = {
  56        MX6_PAD_SD1_CLK__USDHC1_CLK | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  57        MX6_PAD_SD1_CMD__USDHC1_CMD | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  58        MX6_PAD_SD1_DATA0__USDHC1_DATA0 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  59        MX6_PAD_SD1_DATA1__USDHC1_DATA1 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  60        MX6_PAD_SD1_DATA2__USDHC1_DATA2 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  61        MX6_PAD_SD1_DATA3__USDHC1_DATA3 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
  62
  63        /* CD */
  64        MX6_PAD_UART1_RTS_B__GPIO1_IO19 | MUX_PAD_CTRL(NO_PAD_CTRL),
  65};
  66
  67#ifdef CONFIG_FEC_MXC
  68static iomux_v3_cfg_t const fec1_pads[] = {
  69        MX6_PAD_GPIO1_IO06__ENET1_MDIO | MUX_PAD_CTRL(MDIO_PAD_CTRL),
  70        MX6_PAD_GPIO1_IO07__ENET1_MDC | MUX_PAD_CTRL(ENET_PAD_CTRL),
  71        MX6_PAD_ENET1_TX_DATA0__ENET1_TDATA00 | MUX_PAD_CTRL(ENET_PAD_CTRL),
  72        MX6_PAD_ENET1_TX_DATA1__ENET1_TDATA01 | MUX_PAD_CTRL(ENET_PAD_CTRL),
  73        MX6_PAD_ENET1_TX_EN__ENET1_TX_EN | MUX_PAD_CTRL(ENET_PAD_CTRL),
  74        MX6_PAD_ENET1_TX_CLK__ENET1_REF_CLK1 | MUX_PAD_CTRL(ENET_CLK_PAD_CTRL),
  75        MX6_PAD_ENET1_RX_DATA0__ENET1_RDATA00 | MUX_PAD_CTRL(ENET_PAD_CTRL),
  76        MX6_PAD_ENET1_RX_DATA1__ENET1_RDATA01 | MUX_PAD_CTRL(ENET_PAD_CTRL),
  77        MX6_PAD_ENET1_RX_ER__ENET1_RX_ER | MUX_PAD_CTRL(ENET_PAD_CTRL),
  78        MX6_PAD_ENET1_RX_EN__ENET1_RX_EN | MUX_PAD_CTRL(ENET_PAD_CTRL),
  79};
  80
  81static void setup_iomux_fec(void)
  82{
  83        imx_iomux_v3_setup_multiple_pads(fec1_pads, ARRAY_SIZE(fec1_pads));
  84}
  85#endif
  86
  87static void setup_iomux_uart(void)
  88{
  89        imx_iomux_v3_setup_multiple_pads(uart1_pads, ARRAY_SIZE(uart1_pads));
  90}
  91
  92#ifdef CONFIG_FSL_ESDHC
  93static struct fsl_esdhc_cfg sd_cfg = {USDHC1_BASE_ADDR, 0, 4};
  94
  95#define SD_CD_GPIO      IMX_GPIO_NR(1, 19)
  96
  97static int mmc_get_env_devno(void)
  98{
  99        u32 soc_sbmr = readl(SRC_BASE_ADDR + 0x4);
 100        int dev_no;
 101        u32 bootsel;
 102
 103        bootsel = (soc_sbmr & 0x000000FF) >> 6;
 104
 105        /* If not boot from sd/mmc, use default value */
 106        if (bootsel != 1)
 107                return CONFIG_SYS_MMC_ENV_DEV;
 108
 109        /* BOOT_CFG2[3] and BOOT_CFG2[4] */
 110        dev_no = (soc_sbmr & 0x00001800) >> 11;
 111
 112        return dev_no;
 113}
 114
 115int board_mmc_getcd(struct mmc *mmc)
 116{
 117        struct fsl_esdhc_cfg *cfg = (struct fsl_esdhc_cfg *)mmc->priv;
 118        int ret = 0;
 119
 120        switch (cfg->esdhc_base) {
 121        case USDHC1_BASE_ADDR:
 122                ret = !gpio_get_value(SD_CD_GPIO);
 123                break;
 124        case USDHC2_BASE_ADDR:
 125                ret = 1;
 126                break;
 127        }
 128
 129        return ret;
 130}
 131
 132int board_mmc_init(bd_t *bis)
 133{
 134        int ret;
 135
 136        /* SD */
 137        imx_iomux_v3_setup_multiple_pads(sd_pads, ARRAY_SIZE(sd_pads));
 138        gpio_direction_input(SD_CD_GPIO);
 139        sd_cfg.sdhc_clk = mxc_get_clock(MXC_ESDHC_CLK);
 140
 141        ret = fsl_esdhc_initialize(bis, &sd_cfg);
 142        if (ret) {
 143                printf("Warning: failed to initialize mmc dev 0 (SD)\n");
 144                return ret;
 145        }
 146
 147        return litesom_mmc_init(bis);
 148}
 149
 150static int check_mmc_autodetect(void)
 151{
 152        char *autodetect_str = env_get("mmcautodetect");
 153
 154        if ((autodetect_str != NULL) &&
 155            (strcmp(autodetect_str, "yes") == 0)) {
 156                return 1;
 157        }
 158
 159        return 0;
 160}
 161
 162void board_late_mmc_init(void)
 163{
 164        char cmd[32];
 165        char mmcblk[32];
 166        u32 dev_no = mmc_get_env_devno();
 167
 168        if (!check_mmc_autodetect())
 169                return;
 170
 171        env_set_ulong("mmcdev", dev_no);
 172
 173        /* Set mmcblk env */
 174        sprintf(mmcblk, "/dev/mmcblk%dp2 rootwait rw",
 175                dev_no);
 176        env_set("mmcroot", mmcblk);
 177
 178        sprintf(cmd, "mmc dev %d", dev_no);
 179        run_command(cmd, 0);
 180}
 181#endif
 182
 183#ifdef CONFIG_FEC_MXC
 184int board_eth_init(bd_t *bis)
 185{
 186        setup_iomux_fec();
 187
 188        return fecmxc_initialize(bis);
 189}
 190
 191static int setup_fec(void)
 192{
 193        struct iomuxc *const iomuxc_regs = (struct iomuxc *)IOMUXC_BASE_ADDR;
 194        int ret;
 195
 196        /* Use 50M anatop loopback REF_CLK1 for ENET1, clear gpr1[13],
 197           set gpr1[17]*/
 198        clrsetbits_le32(&iomuxc_regs->gpr[1], IOMUX_GPR1_FEC1_MASK,
 199                        IOMUX_GPR1_FEC1_CLOCK_MUX1_SEL_MASK);
 200
 201        ret = enable_fec_anatop_clock(0, ENET_50MHZ);
 202        if (ret)
 203                return ret;
 204
 205        enable_enet_clk(1);
 206
 207        return 0;
 208}
 209#endif
 210
 211#ifdef CONFIG_USB_EHCI_MX6
 212int board_usb_phy_mode(int port)
 213{
 214        return USB_INIT_HOST;
 215}
 216#endif
 217
 218int board_early_init_f(void)
 219{
 220        setup_iomux_uart();
 221
 222        return 0;
 223}
 224
 225int board_init(void)
 226{
 227        /* Address of boot parameters */
 228        gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
 229
 230#ifdef  CONFIG_FEC_MXC
 231        setup_fec();
 232#endif
 233
 234        return 0;
 235}
 236
 237#ifdef CONFIG_CMD_BMODE
 238static const struct boot_mode board_boot_modes[] = {
 239        /* 4 bit bus width */
 240        {"sd",   MAKE_CFGVAL(0x40, 0x20, 0x00, 0x00)},
 241        {"emmc", MAKE_CFGVAL(0x60, 0x48, 0x00, 0x00)},
 242        {NULL,   0},
 243};
 244#endif
 245
 246int board_late_init(void)
 247{
 248#ifdef CONFIG_CMD_BMODE
 249        add_board_boot_modes(board_boot_modes);
 250#endif
 251
 252#ifdef CONFIG_ENV_IS_IN_MMC
 253        board_late_mmc_init();
 254#endif
 255
 256        return 0;
 257}
 258
 259int checkboard(void)
 260{
 261        puts("Board: Grinn liteBoard\n");
 262
 263        return 0;
 264}
 265
 266#ifdef CONFIG_SPL_BUILD
 267void board_boot_order(u32 *spl_boot_list)
 268{
 269        struct src *psrc = (struct src *)SRC_BASE_ADDR;
 270        unsigned gpr10_boot = readl(&psrc->gpr10) & (1 << 28);
 271        unsigned reg = gpr10_boot ? readl(&psrc->gpr9) : readl(&psrc->sbmr1);
 272        unsigned port = (reg >> 11) & 0x1;
 273
 274        if (port == 0) {
 275                spl_boot_list[0] = BOOT_DEVICE_MMC1;
 276                spl_boot_list[1] = BOOT_DEVICE_MMC2;
 277        } else {
 278                spl_boot_list[0] = BOOT_DEVICE_MMC2;
 279                spl_boot_list[1] = BOOT_DEVICE_MMC1;
 280        }
 281}
 282
 283void board_init_f(ulong dummy)
 284{
 285        litesom_init_f();
 286}
 287#endif
 288