common: Drop linux/bitops.h from common header
[platform/kernel/u-boot.git] / board / softing / vining_2000 / vining_2000.c
index 19b9b37..e5e33dc 100644 (file)
@@ -6,6 +6,8 @@
  * Author: Christoph Fritz <chf.fritz@googlemail.com>
  */
 
+#include <init.h>
+#include <net.h>
 #include <asm/arch/clock.h>
 #include <asm/arch/crm_regs.h>
 #include <asm/arch/iomux.h>
 #include <asm/mach-imx/iomux-v3.h>
 #include <asm/io.h>
 #include <asm/mach-imx/mxc_i2c.h>
+#include <env.h>
+#include <linux/bitops.h>
+#include <linux/delay.h>
 #include <linux/sizes.h>
 #include <common.h>
-#include <environment.h>
-#include <fsl_esdhc.h>
+#include <fsl_esdhc_imx.h>
 #include <mmc.h>
 #include <i2c.h>
 #include <miiphy.h>
@@ -71,42 +75,23 @@ int dram_init(void)
        return 0;
 }
 
-static iomux_v3_cfg_t const fec1_pads[] = {
-       MX6_PAD_ENET1_MDC__ENET1_MDC | MUX_PAD_CTRL(ENET_PAD_CTRL),
-       MX6_PAD_ENET1_MDIO__ENET1_MDIO | MUX_PAD_CTRL(ENET_PAD_CTRL),
-       MX6_PAD_RGMII1_RD0__ENET1_RX_DATA_0 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-       MX6_PAD_RGMII1_RD1__ENET1_RX_DATA_1 | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-       MX6_PAD_RGMII1_TD0__ENET1_TX_DATA_0 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-       MX6_PAD_RGMII1_TD1__ENET1_TX_DATA_1 | MUX_PAD_CTRL(ENET_PAD_CTRL),
-       MX6_PAD_RGMII1_RX_CTL__ENET1_RX_EN | MUX_PAD_CTRL(ENET_RX_PAD_CTRL),
-       MX6_PAD_RGMII1_TX_CTL__ENET1_TX_EN | MUX_PAD_CTRL(ENET_PAD_CTRL),
-       MX6_PAD_ENET1_TX_CLK__ENET1_REF_CLK1 | MUX_PAD_CTRL(ENET_CLK_PAD_CTRL) |
-               MUX_MODE_SION,
-       /* LAN8720 PHY Reset */
-       MX6_PAD_RGMII1_TD3__GPIO5_IO_9 | MUX_PAD_CTRL(NO_PAD_CTRL),
-};
-
 static iomux_v3_cfg_t const pwm_led_pads[] = {
        MX6_PAD_RGMII2_RD2__PWM2_OUT | MUX_PAD_CTRL(NO_PAD_CTRL), /* green */
        MX6_PAD_RGMII2_TD2__PWM6_OUT | MUX_PAD_CTRL(NO_PAD_CTRL), /* red */
        MX6_PAD_RGMII2_RD3__PWM1_OUT | MUX_PAD_CTRL(NO_PAD_CTRL), /* blue */
 };
 
-#define PHY_RESET IMX_GPIO_NR(5, 9)
-
-int board_eth_init(bd_t *bis)
+static int board_net_init(void)
 {
        struct iomuxc *iomuxc_regs = (struct iomuxc *)IOMUXC_BASE_ADDR;
-       int ret;
        unsigned char eth1addr[6];
+       int ret;
 
-       /* just to get secound mac address */
+       /* just to get second mac address */
        imx_get_mac_from_fuse(1, eth1addr);
        if (!env_get("eth1addr") && is_valid_ethaddr(eth1addr))
                eth_env_set_enetaddr("eth1addr", eth1addr);
 
-       imx_iomux_v3_setup_multiple_pads(fec1_pads, ARRAY_SIZE(fec1_pads));
-
        /*
         * Generate phy reference clock via pin IOMUX ENET_REF_CLK1/2 by erasing
         * ENET1/2_TX_CLK_DIR gpr1[14:13], so that reference clock is driven by
@@ -122,15 +107,7 @@ int board_eth_init(bd_t *bis)
        if (ret)
                goto eth_fail;
 
-       /* reset phy */
-       gpio_request(PHY_RESET, "PHY-reset");
-       gpio_direction_output(PHY_RESET, 0);
-       mdelay(16);
-       gpio_set_value(PHY_RESET, 1);
-       mdelay(1);
-
-       ret = fecmxc_initialize_multi(bis, 0, CONFIG_FEC_MXC_PHYADDR,
-                                       IMX_FEC_BASE);
+       ret = enable_fec_anatop_clock(1, ENET_50MHZ);
        if (ret)
                goto eth_fail;
 
@@ -138,7 +115,6 @@ int board_eth_init(bd_t *bis)
 
 eth_fail:
        printf("FEC MXC: %s:failed (%i)\n", __func__, ret);
-       gpio_set_value(PHY_RESET, 0);
        return ret;
 }
 
@@ -173,7 +149,7 @@ static struct pmic *pfuze_init(unsigned char i2cbus)
                return NULL;
 
        pmic_reg_read(p, PFUZE100_DEVICEID, &reg);
-       printf("PMIC:  PFUZE100 ID=0x%02x\n", reg);
+       printf("PMIC:  PFUZE%i00 ID=0x%02x\n", (reg & 1) ? 2 : 1, reg);
 
        /* Set SW1AB stanby volage to 0.975V */
        pmic_reg_read(p, PFUZE100_SW1ABSTBY, &reg);
@@ -253,6 +229,9 @@ int power_init_board(void)
        if (ret < 0)
                return ret;
 
+       set_ldo_voltage(LDO_ARM, 1175); /* Set VDDARM to 1.175V */
+       set_ldo_voltage(LDO_SOC, 1175); /* Set VDDSOC to 1.175V */
+
        return 0;
 }
 
@@ -423,7 +402,7 @@ int board_init(void)
        setup_i2c(0, CONFIG_SYS_I2C_SPEED, 0x7f, &i2c_pad_info1);
 #endif
 
-       return 0;
+       return board_net_init();
 }
 
 int checkboard(void)
@@ -432,3 +411,199 @@ int checkboard(void)
 
        return 0;
 }
+
+#define PCIE_PHY_PUP_REQ               BIT(7)
+
+void board_preboot_os(void)
+{
+       struct iomuxc *iomuxc_regs = (struct iomuxc *)IOMUXC_BASE_ADDR;
+       struct gpc *gpc_regs = (struct gpc *)GPC_BASE_ADDR;
+
+       /* Bring the PCI power domain up, so that old vendorkernel works. */
+       setbits_le32(&iomuxc_regs->gpr[12], IOMUXC_GPR12_TEST_POWERDOWN);
+       setbits_le32(&iomuxc_regs->gpr[5], IOMUXC_GPR5_PCIE_BTNRST);
+       setbits_le32(&gpc_regs->cntr, PCIE_PHY_PUP_REQ);
+}
+
+#ifdef CONFIG_SPL_BUILD
+#include <linux/libfdt.h>
+#include <spl.h>
+#include <asm/arch/mx6-ddr.h>
+
+static iomux_v3_cfg_t const pcie_pads[] = {
+       MX6_PAD_NAND_DATA02__GPIO4_IO_6 | MUX_PAD_CTRL(GPIO_PAD_CTRL),
+};
+
+static iomux_v3_cfg_t const uart_pads[] = {
+       MX6_PAD_GPIO1_IO04__UART1_TX | MUX_PAD_CTRL(UART_PAD_CTRL),
+       MX6_PAD_GPIO1_IO05__UART1_RX | MUX_PAD_CTRL(UART_PAD_CTRL),
+};
+
+static iomux_v3_cfg_t const usdhc4_pads[] = {
+       MX6_PAD_SD4_CLK__USDHC4_CLK | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_CMD__USDHC4_CMD | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA0__USDHC4_DATA0 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA1__USDHC4_DATA1 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA2__USDHC4_DATA2 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA3__USDHC4_DATA3 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA4__USDHC4_DATA4 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA5__USDHC4_DATA5 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA6__USDHC4_DATA6 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+       MX6_PAD_SD4_DATA7__USDHC4_DATA7 | MUX_PAD_CTRL(USDHC_PAD_CTRL),
+};
+
+static void vining2000_spl_setup_iomux_pcie(void)
+{
+       imx_iomux_v3_setup_multiple_pads(pcie_pads, ARRAY_SIZE(pcie_pads));
+}
+
+static void vining2000_spl_setup_iomux_uart(void)
+{
+       imx_iomux_v3_setup_multiple_pads(uart_pads, ARRAY_SIZE(uart_pads));
+}
+
+static struct fsl_esdhc_cfg usdhc_cfg = { USDHC4_BASE_ADDR };
+
+int board_mmc_init(bd_t *bis)
+{
+       imx_iomux_v3_setup_multiple_pads(usdhc4_pads, ARRAY_SIZE(usdhc4_pads));
+
+       usdhc_cfg.sdhc_clk = mxc_get_clock(MXC_ESDHC4_CLK);
+       gd->arch.sdhc_clk = usdhc_cfg.sdhc_clk;
+       return fsl_esdhc_initialize(bis, &usdhc_cfg);
+}
+
+int board_mmc_getcd(struct mmc *mmc)
+{
+       return 1;
+}
+
+const struct mx6sx_iomux_ddr_regs mx6_ddr_ioregs = {
+       .dram_dqm0              = 0x00000028,
+       .dram_dqm1              = 0x00000028,
+       .dram_dqm2              = 0x00000028,
+       .dram_dqm3              = 0x00000028,
+       .dram_ras               = 0x00000028,
+       .dram_cas               = 0x00000028,
+       .dram_odt0              = 0x00000028,
+       .dram_odt1              = 0x00000028,
+       .dram_sdba2             = 0x00000000,
+       .dram_sdcke0            = 0x00003000,
+       .dram_sdcke1            = 0x00003000,
+       .dram_sdclk_0           = 0x00000030,
+       .dram_sdqs0             = 0x00000028,
+       .dram_sdqs1             = 0x00000028,
+       .dram_sdqs2             = 0x00000028,
+       .dram_sdqs3             = 0x00000028,
+       .dram_reset             = 0x00000028,
+};
+
+const struct mx6sx_iomux_grp_regs mx6_grp_ioregs = {
+       .grp_addds              = 0x00000028,
+       .grp_b0ds               = 0x00000028,
+       .grp_b1ds               = 0x00000028,
+       .grp_b2ds               = 0x00000028,
+       .grp_b3ds               = 0x00000028,
+       .grp_ctlds              = 0x00000028,
+       .grp_ddr_type           = 0x000c0000,
+       .grp_ddrmode            = 0x00020000,
+       .grp_ddrmode_ctl        = 0x00020000,
+       .grp_ddrpke             = 0x00000000,
+};
+
+const struct mx6_mmdc_calibration mx6_mmcd_calib = {
+       .p0_mpwldectrl0         = 0x0022001C,
+       .p0_mpwldectrl1         = 0x001F001A,
+       .p0_mpdgctrl0           = 0x01380134,
+       .p0_mpdgctrl1           = 0x0124011C,
+       .p0_mprddlctl           = 0x42404444,
+       .p0_mpwrdlctl           = 0x36383C38,
+};
+
+static struct mx6_ddr3_cfg mem_ddr = {
+       .mem_speed      = 1600,
+       .density        = 4,
+       .width          = 32,
+       .banks          = 8,
+       .rowaddr        = 15,
+       .coladdr        = 10,
+       .pagesz         = 2,
+       .trcd           = 1391,
+       .trcmin         = 4875,
+       .trasmin        = 3500,
+};
+
+static void ccgr_init(void)
+{
+       struct mxc_ccm_reg *ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
+
+       writel(0xF000000F, &ccm->CCGR0);        /* AIPS_TZ{1,2,3} */
+       writel(0x303C0000, &ccm->CCGR1);        /* GPT, OCRAM */
+       writel(0x00FFFCC0, &ccm->CCGR2);        /* IPMUX, I2C1, I2C3 */
+       writel(0x3F300030, &ccm->CCGR3);        /* OCRAM, MMDC, ENET */
+       writel(0x0000C003, &ccm->CCGR4);        /* PCI, PL301 */
+       writel(0x0F0330C3, &ccm->CCGR5);        /* UART, ROM */
+       writel(0x00000F00, &ccm->CCGR6);        /* SDHI4, EIM */
+}
+
+static void vining2000_spl_dram_init(void)
+{
+       struct mx6_ddr_sysinfo sysinfo = {
+               .dsize          = mem_ddr.width / 32,
+               .cs_density     = 24,
+               .ncs            = 1,
+               .cs1_mirror     = 0,
+               .rtt_wr         = 1,    /* RTT_wr = RZQ/4 */
+               .rtt_nom        = 1,    /* RTT_Nom = RZQ/4 */
+               .walat          = 1,    /* Write additional latency */
+               .ralat          = 5,    /* Read additional latency */
+               .mif3_mode      = 3,    /* Command prediction working mode */
+               .bi_on          = 1,    /* Bank interleaving enabled */
+               .sde_to_rst     = 0x10, /* 14 cycles, 200us (JEDEC default) */
+               .rst_to_cke     = 0x23, /* 33 cycles, 500us (JEDEC default) */
+               .ddr_type       = DDR_TYPE_DDR3,
+               .refsel         = 1,    /* Refresh cycles at 32KHz */
+               .refr           = 7,    /* 8 refresh commands per refresh cycle */
+       };
+
+       mx6sx_dram_iocfg(mem_ddr.width, &mx6_ddr_ioregs, &mx6_grp_ioregs);
+       mx6_dram_cfg(&sysinfo, &mx6_mmcd_calib, &mem_ddr);
+
+       /* Perform DDR DRAM calibration */
+       udelay(100);
+       mmdc_do_write_level_calibration(&sysinfo);
+       mmdc_do_dqs_calibration(&sysinfo);
+}
+
+void board_init_f(ulong dummy)
+{
+       /* setup AIPS and disable watchdog */
+       arch_cpu_init();
+
+       ccgr_init();
+
+       /* iomux setup */
+       vining2000_spl_setup_iomux_pcie();
+       vining2000_spl_setup_iomux_uart();
+
+       /* setup GP timer */
+       timer_init();
+
+       /* reset the PCIe device */
+       gpio_set_value(IMX_GPIO_NR(4, 6), 1);
+       udelay(50);
+       gpio_set_value(IMX_GPIO_NR(4, 6), 0);
+
+       /* UART clocks enabled and gd valid - init serial console */
+       preloader_console_init();
+
+       /* DDR initialization */
+       vining2000_spl_dram_init();
+
+       /* Clear the BSS. */
+       memset(__bss_start, 0, __bss_end - __bss_start);
+
+       /* load/boot image from boot device */
+       board_init_r(NULL, 0);
+}
+#endif