uboot/arch/arm/cpu/armv7/am33xx/board.c
<<
>>
Prefs
   1/*
   2 * board.c
   3 *
   4 * Common board functions for AM33XX based boards
   5 *
   6 * Copyright (C) 2011, Texas Instruments, Incorporated - http://www.ti.com/
   7 *
   8 * This program is free software; you can redistribute it and/or
   9 * modify it under the terms of the GNU General Public License as
  10 * published by the Free Software Foundation; either version 2 of
  11 * the License, or (at your option) any later version.
  12 *
  13 * This program is distributed in the hope that it will be useful,
  14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR /PURPOSE.  See the
  16 * GNU General Public License for more details.
  17 */
  18
  19#include <common.h>
  20#include <errno.h>
  21#include <spl.h>
  22#include <asm/arch/cpu.h>
  23#include <asm/arch/hardware.h>
  24#include <asm/arch/omap.h>
  25#include <asm/arch/ddr_defs.h>
  26#include <asm/arch/clock.h>
  27#include <asm/arch/gpio.h>
  28#include <asm/arch/mmc_host_def.h>
  29#include <asm/arch/sys_proto.h>
  30#include <asm/io.h>
  31#include <asm/emif.h>
  32#include <asm/gpio.h>
  33#include <i2c.h>
  34#include <miiphy.h>
  35#include <cpsw.h>
  36
  37DECLARE_GLOBAL_DATA_PTR;
  38
  39struct wd_timer *wdtimer = (struct wd_timer *)WDT_BASE;
  40struct uart_sys *uart_base = (struct uart_sys *)DEFAULT_UART_BASE;
  41
  42static const struct gpio_bank gpio_bank_am33xx[4] = {
  43        { (void *)AM33XX_GPIO0_BASE, METHOD_GPIO_24XX },
  44        { (void *)AM33XX_GPIO1_BASE, METHOD_GPIO_24XX },
  45        { (void *)AM33XX_GPIO2_BASE, METHOD_GPIO_24XX },
  46        { (void *)AM33XX_GPIO3_BASE, METHOD_GPIO_24XX },
  47};
  48
  49const struct gpio_bank *const omap_gpio_bank = gpio_bank_am33xx;
  50
  51/* MII mode defines */
  52#define MII_MODE_ENABLE         0x0
  53#define RGMII_MODE_ENABLE       0xA
  54
  55/* GPIO that controls power to DDR on EVM-SK */
  56#define GPIO_DDR_VTT_EN         7
  57
  58static struct ctrl_dev *cdev = (struct ctrl_dev *)CTRL_DEVICE_BASE;
  59
  60static struct am335x_baseboard_id __attribute__((section (".data"))) header;
  61
  62static inline int board_is_bone(void)
  63{
  64        return !strncmp(header.name, "A335BONE", HDR_NAME_LEN);
  65}
  66
  67static inline int board_is_evm_sk(void)
  68{
  69        return !strncmp("A335X_SK", header.name, HDR_NAME_LEN);
  70}
  71
  72/*
  73 * Read header information from EEPROM into global structure.
  74 */
  75static int read_eeprom(void)
  76{
  77        /* Check if baseboard eeprom is available */
  78        if (i2c_probe(CONFIG_SYS_I2C_EEPROM_ADDR)) {
  79                puts("Could not probe the EEPROM; something fundamentally "
  80                        "wrong on the I2C bus.\n");
  81                return -ENODEV;
  82        }
  83
  84        /* read the eeprom using i2c */
  85        if (i2c_read(CONFIG_SYS_I2C_EEPROM_ADDR, 0, 2, (uchar *)&header,
  86                                                        sizeof(header))) {
  87                puts("Could not read the EEPROM; something fundamentally"
  88                        " wrong on the I2C bus.\n");
  89                return -EIO;
  90        }
  91
  92        if (header.magic != 0xEE3355AA) {
  93                /*
  94                 * read the eeprom using i2c again,
  95                 * but use only a 1 byte address
  96                 */
  97                if (i2c_read(CONFIG_SYS_I2C_EEPROM_ADDR, 0, 1,
  98                                        (uchar *)&header, sizeof(header))) {
  99                        puts("Could not read the EEPROM; something "
 100                                "fundamentally wrong on the I2C bus.\n");
 101                        return -EIO;
 102                }
 103
 104                if (header.magic != 0xEE3355AA) {
 105                        printf("Incorrect magic number (0x%x) in EEPROM\n",
 106                                        header.magic);
 107                        return -EINVAL;
 108                }
 109        }
 110
 111        return 0;
 112}
 113
 114/* UART Defines */
 115#ifdef CONFIG_SPL_BUILD
 116#define UART_RESET              (0x1 << 1)
 117#define UART_CLK_RUNNING_MASK   0x1
 118#define UART_SMART_IDLE_EN      (0x1 << 0x3)
 119#endif
 120
 121/*
 122 * Determine what type of DDR we have.
 123 */
 124static short inline board_memory_type(void)
 125{
 126        /* The following boards are known to use DDR3. */
 127        if (board_is_evm_sk())
 128                return EMIF_REG_SDRAM_TYPE_DDR3;
 129
 130        return EMIF_REG_SDRAM_TYPE_DDR2;
 131}
 132
 133/*
 134 * early system init of muxing and clocks.
 135 */
 136void s_init(void)
 137{
 138        /* WDT1 is already running when the bootloader gets control
 139         * Disable it to avoid "random" resets
 140         */
 141        writel(0xAAAA, &wdtimer->wdtwspr);
 142        while (readl(&wdtimer->wdtwwps) != 0x0)
 143                ;
 144        writel(0x5555, &wdtimer->wdtwspr);
 145        while (readl(&wdtimer->wdtwwps) != 0x0)
 146                ;
 147
 148#ifdef CONFIG_SPL_BUILD
 149        /* Setup the PLLs and the clocks for the peripherals */
 150        pll_init();
 151
 152        /* UART softreset */
 153        u32 regVal;
 154
 155        enable_uart0_pin_mux();
 156
 157        regVal = readl(&uart_base->uartsyscfg);
 158        regVal |= UART_RESET;
 159        writel(regVal, &uart_base->uartsyscfg);
 160        while ((readl(&uart_base->uartsyssts) &
 161                UART_CLK_RUNNING_MASK) != UART_CLK_RUNNING_MASK)
 162                ;
 163
 164        /* Disable smart idle */
 165        regVal = readl(&uart_base->uartsyscfg);
 166        regVal |= UART_SMART_IDLE_EN;
 167        writel(regVal, &uart_base->uartsyscfg);
 168
 169        gd = &gdata;
 170
 171        preloader_console_init();
 172
 173        /* Initalize the board header */
 174        enable_i2c0_pin_mux();
 175        i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
 176        if (read_eeprom() < 0)
 177                puts("Could not get board ID.\n");
 178
 179        enable_board_pin_mux(&header);
 180        if (board_is_evm_sk()) {
 181                /*
 182                 * EVM SK 1.2A and later use gpio0_7 to enable DDR3.
 183                 * This is safe enough to do on older revs.
 184                 */
 185                gpio_request(GPIO_DDR_VTT_EN, "ddr_vtt_en");
 186                gpio_direction_output(GPIO_DDR_VTT_EN, 1);
 187        }
 188
 189        config_ddr(board_memory_type());
 190#endif
 191}
 192
 193#if defined(CONFIG_OMAP_HSMMC) && !defined(CONFIG_SPL_BUILD)
 194int board_mmc_init(bd_t *bis)
 195{
 196        int ret;
 197        
 198        ret = omap_mmc_init(0, 0, 0);
 199        if (ret)
 200                return ret;
 201
 202        return omap_mmc_init(1, 0, 0);
 203}
 204#endif
 205
 206void setup_clocks_for_console(void)
 207{
 208        /* Not yet implemented */
 209        return;
 210}
 211
 212/*
 213 * Basic board specific setup.  Pinmux has been handled already.
 214 */
 215int board_init(void)
 216{
 217        i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
 218        if (read_eeprom() < 0)
 219                puts("Could not get board ID.\n");
 220
 221        gd->bd->bi_boot_params = PHYS_DRAM_1 + 0x100;
 222
 223        return 0;
 224}
 225
 226#ifdef CONFIG_DRIVER_TI_CPSW
 227static void cpsw_control(int enabled)
 228{
 229        /* VTP can be added here */
 230
 231        return;
 232}
 233
 234static struct cpsw_slave_data cpsw_slaves[] = {
 235        {
 236                .slave_reg_ofs  = 0x208,
 237                .sliver_reg_ofs = 0xd80,
 238                .phy_id         = 0,
 239        },
 240        {
 241                .slave_reg_ofs  = 0x308,
 242                .sliver_reg_ofs = 0xdc0,
 243                .phy_id         = 1,
 244        },
 245};
 246
 247static struct cpsw_platform_data cpsw_data = {
 248        .mdio_base              = AM335X_CPSW_MDIO_BASE,
 249        .cpsw_base              = AM335X_CPSW_BASE,
 250        .mdio_div               = 0xff,
 251        .channels               = 8,
 252        .cpdma_reg_ofs          = 0x800,
 253        .slaves                 = 1,
 254        .slave_data             = cpsw_slaves,
 255        .ale_reg_ofs            = 0xd00,
 256        .ale_entries            = 1024,
 257        .host_port_reg_ofs      = 0x108,
 258        .hw_stats_reg_ofs       = 0x900,
 259        .mac_control            = (1 << 5),
 260        .control                = cpsw_control,
 261        .host_port_num          = 0,
 262        .version                = CPSW_CTRL_VERSION_2,
 263};
 264
 265int board_eth_init(bd_t *bis)
 266{
 267        uint8_t mac_addr[6];
 268        uint32_t mac_hi, mac_lo;
 269
 270        if (!eth_getenv_enetaddr("ethaddr", mac_addr)) {
 271                debug("<ethaddr> not set. Reading from E-fuse\n");
 272                /* try reading mac address from efuse */
 273                mac_lo = readl(&cdev->macid0l);
 274                mac_hi = readl(&cdev->macid0h);
 275                mac_addr[0] = mac_hi & 0xFF;
 276                mac_addr[1] = (mac_hi & 0xFF00) >> 8;
 277                mac_addr[2] = (mac_hi & 0xFF0000) >> 16;
 278                mac_addr[3] = (mac_hi & 0xFF000000) >> 24;
 279                mac_addr[4] = mac_lo & 0xFF;
 280                mac_addr[5] = (mac_lo & 0xFF00) >> 8;
 281
 282                if (is_valid_ether_addr(mac_addr))
 283                        eth_setenv_enetaddr("ethaddr", mac_addr);
 284                else
 285                        return -1;
 286        }
 287
 288        if (board_is_bone()) {
 289                writel(MII_MODE_ENABLE, &cdev->miisel);
 290                cpsw_slaves[0].phy_if = cpsw_slaves[1].phy_if =
 291                                PHY_INTERFACE_MODE_MII;
 292        } else {
 293                writel(RGMII_MODE_ENABLE, &cdev->miisel);
 294                cpsw_slaves[0].phy_if = cpsw_slaves[1].phy_if =
 295                                PHY_INTERFACE_MODE_RGMII;
 296        }
 297
 298        return cpsw_register(&cpsw_data);
 299}
 300#endif
 301