u-boot/board/gumstix/duovero/duovero.c
Jean-Jacques Hiblot d5abcf94c7 ti: boot: Register the MMC controllers in SPL in the same way as in u-boot
To keep a consistent MMC device mapping in SPL and in u-boot, let's
register the MMC controllers the same way in u-boot and in the SPL.
In terms of boot time, it doesn't hurt to register more controllers than
needed because the MMC device is initialized only prior being accessed for
the first time.
Having the same device mapping in SPL and u-boot allows us to use the
environment in SPL whatever the MMC boot device.

Signed-off-by: Jean-Jacques Hiblot <jjhiblot@ti.com>
2017-03-19 22:17:14 -04:00

270 lines
6.2 KiB
C

/*
* (C) Copyright 2013
* Gumstix Inc. <www.gumstix.com>
* Maintainer: Ash Charles <ash@gumstix.com>
*
* SPDX-License-Identifier: GPL-2.0+
*/
#include <common.h>
#include <netdev.h>
#include <asm/arch/sys_proto.h>
#include <asm/arch/mmc_host_def.h>
#include <twl6030.h>
#include <asm/emif.h>
#include <asm/arch/clock.h>
#include <asm/arch/gpio.h>
#include <asm/gpio.h>
#include "duovero_mux_data.h"
#define WIFI_EN 43
#if defined(CONFIG_CMD_NET)
#define SMSC_NRESET 45
static void setup_net_chip(void);
#endif
#ifdef CONFIG_USB_EHCI
#include <usb.h>
#include <asm/arch/ehci.h>
#include <asm/ehci-omap.h>
#endif
DECLARE_GLOBAL_DATA_PTR;
const struct omap_sysinfo sysinfo = {
"Board: duovero\n"
};
struct omap4_scrm_regs *const scrm = (struct omap4_scrm_regs *)0x4a30a000;
/**
* @brief board_init
*
* @return 0
*/
int board_init(void)
{
gpmc_init();
gd->bd->bi_arch_number = MACH_TYPE_DUOVERO;
gd->bd->bi_boot_params = CONFIG_SYS_SDRAM_BASE + 0x100;
return 0;
}
/**
* @brief misc_init_r - Configure board specific configurations
* such as power configurations, ethernet initialization as phase2 of
* boot sequence
*
* @return 0
*/
int misc_init_r(void)
{
int ret = 0;
u8 val;
/* wifi setup: first enable 32Khz clock from 6030 pmic */
val = 0xe1;
ret = i2c_write(TWL6030_CHIP_PM, 0xbe, 1, &val, 1);
if (ret)
printf("Failed to enable 32Khz clock to wifi module\n");
/* then setup WIFI_EN as an output pin and send reset pulse */
if (!gpio_request(WIFI_EN, "")) {
gpio_direction_output(WIFI_EN, 0);
gpio_set_value(WIFI_EN, 1);
udelay(1);
gpio_set_value(WIFI_EN, 0);
udelay(1);
gpio_set_value(WIFI_EN, 1);
}
#if defined(CONFIG_CMD_NET)
setup_net_chip();
#endif
return 0;
}
void set_muxconf_regs(void)
{
do_set_mux((*ctrl)->control_padconf_core_base,
core_padconf_array_essential,
sizeof(core_padconf_array_essential) /
sizeof(struct pad_conf_entry));
do_set_mux((*ctrl)->control_padconf_wkup_base,
wkup_padconf_array_essential,
sizeof(wkup_padconf_array_essential) /
sizeof(struct pad_conf_entry));
do_set_mux((*ctrl)->control_padconf_core_base,
core_padconf_array_non_essential,
sizeof(core_padconf_array_non_essential) /
sizeof(struct pad_conf_entry));
do_set_mux((*ctrl)->control_padconf_wkup_base,
wkup_padconf_array_non_essential,
sizeof(wkup_padconf_array_non_essential) /
sizeof(struct pad_conf_entry));
}
#if defined(CONFIG_GENERIC_MMC)
int board_mmc_init(bd_t *bis)
{
return omap_mmc_init(0, 0, 0, -1, -1);
}
#if !defined(CONFIG_SPL_BUILD)
void board_mmc_power_init(void)
{
twl6030_power_mmc_init(0);
}
#endif
#endif
#if defined(CONFIG_CMD_NET)
#define GPMC_SIZE_16M 0xF
#define GPMC_BASEADDR_MASK 0x3F
#define GPMC_CS_ENABLE 0x1
static void enable_gpmc_net_config(const u32 *gpmc_config, const struct gpmc_cs *cs,
u32 base, u32 size)
{
writel(0, &cs->config7);
sdelay(1000);
/* Delay for settling */
writel(gpmc_config[0], &cs->config1);
writel(gpmc_config[1], &cs->config2);
writel(gpmc_config[2], &cs->config3);
writel(gpmc_config[3], &cs->config4);
writel(gpmc_config[4], &cs->config5);
writel(gpmc_config[5], &cs->config6);
/*
* Enable the config. size is the CS size and goes in
* bits 11:8. We set bit 6 to enable this CS and the base
* address goes into bits 5:0.
*/
writel((size << 8) | (GPMC_CS_ENABLE << 6) |
((base >> 24) & GPMC_BASEADDR_MASK),
&cs->config7);
sdelay(2000);
}
/* GPMC CS configuration for an SMSC LAN9221 ethernet controller */
#define NET_LAN9221_GPMC_CONFIG1 0x2a001203
#define NET_LAN9221_GPMC_CONFIG2 0x000a0a02
#define NET_LAN9221_GPMC_CONFIG3 0x00020200
#define NET_LAN9221_GPMC_CONFIG4 0x0a030a03
#define NET_LAN9221_GPMC_CONFIG5 0x000a0a0a
#define NET_LAN9221_GPMC_CONFIG6 0x8a070707
#define NET_LAN9221_GPMC_CONFIG7 0x00000f6c
/* GPMC definitions for LAN9221 chips on expansion boards */
static const u32 gpmc_lan_config[] = {
NET_LAN9221_GPMC_CONFIG1,
NET_LAN9221_GPMC_CONFIG2,
NET_LAN9221_GPMC_CONFIG3,
NET_LAN9221_GPMC_CONFIG4,
NET_LAN9221_GPMC_CONFIG5,
NET_LAN9221_GPMC_CONFIG6,
/*CONFIG7- computed as params */
};
/*
* Routine: setup_net_chip
* Description: Setting up the configuration GPMC registers specific to the
* Ethernet hardware.
*/
static void setup_net_chip(void)
{
enable_gpmc_net_config(gpmc_lan_config, &gpmc_cfg->cs[5], 0x2C000000,
GPMC_SIZE_16M);
/* Make GPIO SMSC_NRESET as output pin and send reset pulse */
if (!gpio_request(SMSC_NRESET, "")) {
gpio_direction_output(SMSC_NRESET, 0);
gpio_set_value(SMSC_NRESET, 1);
udelay(1);
gpio_set_value(SMSC_NRESET, 0);
udelay(1);
gpio_set_value(SMSC_NRESET, 1);
}
}
#endif
int board_eth_init(bd_t *bis)
{
int rc = 0;
#ifdef CONFIG_SMC911X
rc = smc911x_initialize(0, CONFIG_SMC911X_BASE);
#endif
return rc;
}
#ifdef CONFIG_USB_EHCI
static struct omap_usbhs_board_data usbhs_bdata = {
.port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
.port_mode[1] = OMAP_USBHS_PORT_MODE_UNUSED,
.port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
};
int ehci_hcd_init(int index, enum usb_init_type init,
struct ehci_hccr **hccr, struct ehci_hcor **hcor)
{
int ret;
unsigned int utmi_clk;
u32 auxclk, altclksrc;
/* Now we can enable our port clocks */
utmi_clk = readl((void *)CM_L3INIT_HSUSBHOST_CLKCTRL);
utmi_clk |= HSUSBHOST_CLKCTRL_CLKSEL_UTMI_P1_MASK;
setbits_le32((void *)CM_L3INIT_HSUSBHOST_CLKCTRL, utmi_clk);
auxclk = readl(&scrm->auxclk3);
/* Select sys_clk */
auxclk &= ~AUXCLK_SRCSELECT_MASK;
auxclk |= AUXCLK_SRCSELECT_SYS_CLK << AUXCLK_SRCSELECT_SHIFT;
/* Set the divisor to 2 */
auxclk &= ~AUXCLK_CLKDIV_MASK;
auxclk |= AUXCLK_CLKDIV_2 << AUXCLK_CLKDIV_SHIFT;
/* Request auxilary clock #3 */
auxclk |= AUXCLK_ENABLE_MASK;
writel(auxclk, &scrm->auxclk3);
altclksrc = readl(&scrm->altclksrc);
/* Activate alternate system clock supplier */
altclksrc &= ~ALTCLKSRC_MODE_MASK;
altclksrc |= ALTCLKSRC_MODE_ACTIVE;
/* enable clocks */
altclksrc |= ALTCLKSRC_ENABLE_INT_MASK | ALTCLKSRC_ENABLE_EXT_MASK;
writel(altclksrc, &scrm->altclksrc);
ret = omap_ehci_hcd_init(index, &usbhs_bdata, hccr, hcor);
if (ret < 0)
return ret;
return 0;
}
int ehci_hcd_stop(int index)
{
return omap_ehci_hcd_stop();
}
#endif
/*
* get_board_rev() - get board revision
*/
u32 get_board_rev(void)
{
return 0x20;
}