18ec8d58eSZhihuan He // SPDX-License-Identifier: GPL-2.0+
28ec8d58eSZhihuan He /*
38ec8d58eSZhihuan He * Copyright (C) 2020 Rockchip Electronics Co., Ltd
48ec8d58eSZhihuan He */
58ec8d58eSZhihuan He
68ec8d58eSZhihuan He #include <common.h>
719d63b30SZhihuan He
819d63b30SZhihuan He #ifdef CONFIG_TPL_BUILD
98ec8d58eSZhihuan He #include <debug_uart.h>
108ec8d58eSZhihuan He #include <dm.h>
118ec8d58eSZhihuan He #include <dt-structs.h>
128ec8d58eSZhihuan He #include <ram.h>
138ec8d58eSZhihuan He #include <regmap.h>
148ec8d58eSZhihuan He #include <syscon.h>
158ec8d58eSZhihuan He #include <asm/io.h>
168ec8d58eSZhihuan He #include <asm/arch/clock.h>
178ec8d58eSZhihuan He #include <asm/arch/hardware.h>
188ec8d58eSZhihuan He #include <asm/arch/rk_atags.h>
198ec8d58eSZhihuan He #include <asm/arch/timer.h>
208ec8d58eSZhihuan He #include <asm/arch/grf_rk3308.h>
218ec8d58eSZhihuan He #include <asm/arch/sdram.h>
228ec8d58eSZhihuan He #include <asm/arch/sdram_rk3308.h>
238ec8d58eSZhihuan He #include <asm/arch/sdram_rv1108_pctl_phy.h>
248ec8d58eSZhihuan He
258ec8d58eSZhihuan He DECLARE_GLOBAL_DATA_PTR;
268ec8d58eSZhihuan He
278ec8d58eSZhihuan He #define CRU_BASE 0xff500000
288ec8d58eSZhihuan He #define GRF_BASE 0xff000000
298ec8d58eSZhihuan He #define SGRF_BASE 0xff2b0000
308ec8d58eSZhihuan He #define DDR_PHY_BASE 0xff530000
318ec8d58eSZhihuan He #define DDR_PCTL_BASE 0xff010000
328ec8d58eSZhihuan He #define DDR_STANDBY_BASE 0xff030000
338ec8d58eSZhihuan He #define PMU_BASS_ADDR 0xff520000
348ec8d58eSZhihuan He #define SERVICE_MSCH_BASE 0xff5c8000
358ec8d58eSZhihuan He
368ec8d58eSZhihuan He struct rk3308_ddr_gd ddr_gd = {
378ec8d58eSZhihuan He #include "sdram-rk3308-ddr-skew.inc"
388ec8d58eSZhihuan He };
398ec8d58eSZhihuan He
408ec8d58eSZhihuan He struct sdram_params sdram_configs[] = {
418ec8d58eSZhihuan He #if (CONFIG_ROCKCHIP_TPL_INIT_DRAM_TYPE == 3)
428ec8d58eSZhihuan He #include "sdram_inc/rk3308/sdram-rk3308-ddr3-detect-589.inc"
438ec8d58eSZhihuan He #elif (CONFIG_ROCKCHIP_TPL_INIT_DRAM_TYPE == 2)
448ec8d58eSZhihuan He #include "sdram_inc/rk3308/sdram-rk3308-ddr2-detect-451.inc"
458ec8d58eSZhihuan He #elif (CONFIG_ROCKCHIP_TPL_INIT_DRAM_TYPE == 5)
468ec8d58eSZhihuan He #include "sdram_inc/rk3308/sdram-rk3308-lpddr2-detect-451.inc"
478ec8d58eSZhihuan He #endif
488ec8d58eSZhihuan He };
498ec8d58eSZhihuan He
508ec8d58eSZhihuan He #define DDR3_DDR2_ODT_DISABLE_FREQ (666)
518ec8d58eSZhihuan He
528ec8d58eSZhihuan He #define DDR2_TRFC_256MBIT (75)
538ec8d58eSZhihuan He #define DDR2_TRFC_512MBIT (105)
548ec8d58eSZhihuan He #define DDR2_TRFC_1GBIT (128)
558ec8d58eSZhihuan He #define DDR2_TRFC_2GBIT (195)
568ec8d58eSZhihuan He #define DDR2_TRFC_4GBIT (328)
578ec8d58eSZhihuan He
588ec8d58eSZhihuan He #define DDR3_TRFC_512MBIT (90)
598ec8d58eSZhihuan He #define DDR3_TRFC_1GBIT (110)
608ec8d58eSZhihuan He #define DDR3_TRFC_2GBIT (160)
618ec8d58eSZhihuan He #define DDR3_TRFC_4GBIT (300)
628ec8d58eSZhihuan He #define DDR3_TRFC_8GBIT (350)
638ec8d58eSZhihuan He
648ec8d58eSZhihuan He #define LPDDR2_TRFC_8GBIT (210) /*ns*/
658ec8d58eSZhihuan He #define LPDDR2_TRFC_4GBIT (130) /*ns*/
668ec8d58eSZhihuan He #define LPDDR2_TREC_512MBIT (90) /*ns*/
678ec8d58eSZhihuan He
enable_ddr_io_ret(struct dram_info * priv)688ec8d58eSZhihuan He void enable_ddr_io_ret(struct dram_info *priv)
698ec8d58eSZhihuan He {
708ec8d58eSZhihuan He rk_clrsetreg(&priv->pmu->sft_con_lo, DDR_IO_RET_CFG_MASK,
718ec8d58eSZhihuan He DDR_IO_RET_CFG << DDR_IO_RET_CFG_SHIFT);
728ec8d58eSZhihuan He
738ec8d58eSZhihuan He rk_clrsetreg(&priv->grf->upctl_con0, GRF_DDR_16BIT_EN_MASK,
748ec8d58eSZhihuan He GRF_DDR_16BIT_EN << GRF_DDR_16BIT_EN_SHIFT);
758ec8d58eSZhihuan He }
768ec8d58eSZhihuan He
pll_set(u32 pll_type,struct dram_info * priv,struct rockchip_pll_rate_table * pll_priv)778ec8d58eSZhihuan He void pll_set(u32 pll_type, struct dram_info *priv,
788ec8d58eSZhihuan He struct rockchip_pll_rate_table *pll_priv)
798ec8d58eSZhihuan He {
808ec8d58eSZhihuan He /* pll power down */
818ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->pll[pll_type].con1, PLLPD0_MASK,
828ec8d58eSZhihuan He PLLPD0_POWER_DOWN << PLLPD0_SHIFT);
838ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->pll[pll_type].con1,
848ec8d58eSZhihuan He DSMPD_MASK, pll_priv->dsmpd << DSMPD_SHIFT);
858ec8d58eSZhihuan He
868ec8d58eSZhihuan He /* set pll freq */
878ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->pll[pll_type].con0,
888ec8d58eSZhihuan He FBDIV_MASK | POSTDIV1_MASK,
898ec8d58eSZhihuan He pll_priv->fbdiv << FBDIV_SHIFT |
908ec8d58eSZhihuan He pll_priv->postdiv1 << POSTDIV1_SHIFT);
918ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->pll[pll_type].con1,
928ec8d58eSZhihuan He POSTDIV2_MASK | REFDIV_MASK,
938ec8d58eSZhihuan He pll_priv->postdiv2 << POSTDIV2_SHIFT |
948ec8d58eSZhihuan He pll_priv->refdiv << REFDIV_SHIFT);
958ec8d58eSZhihuan He writel(pll_priv->frac << FRACDIV_SHIFT,
968ec8d58eSZhihuan He &priv->cru->pll[pll_type].con2);
978ec8d58eSZhihuan He /* pll power up */
988ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->pll[pll_type].con1, PLLPD0_MASK,
998ec8d58eSZhihuan He PLLPD0_NO_POWER_DOWN << PLLPD0_SHIFT);
1008ec8d58eSZhihuan He
1018ec8d58eSZhihuan He /* wait until pll lock */
1028ec8d58eSZhihuan He while (!(readl(&priv->cru->pll[pll_type].con1) &
1038ec8d58eSZhihuan He (1u << PLL_LOCK_SHIFT)))
1048ec8d58eSZhihuan He udelay(1);
1058ec8d58eSZhihuan He }
1068ec8d58eSZhihuan He
rkdclk_init(struct dram_info * priv,struct sdram_params * params_priv)1078ec8d58eSZhihuan He void rkdclk_init(struct dram_info *priv,
1088ec8d58eSZhihuan He struct sdram_params *params_priv)
1098ec8d58eSZhihuan He {
1108ec8d58eSZhihuan He u32 ddr_pll_sel;
1118ec8d58eSZhihuan He u32 ddr_phy_div_con;
1128ec8d58eSZhihuan He u32 uart_div[5] = {15, 15, 15, 15, 15};
1138ec8d58eSZhihuan He struct rockchip_pll_rate_table rk3308_pll_div;
1148ec8d58eSZhihuan He
1158ec8d58eSZhihuan He /* DPLL VPLL0 VPLL1 mode in 24MHz*/
1168ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL1_WORK_MODE_MASK,
1178ec8d58eSZhihuan He VPLL1_WORK_MODE_XIN_OSC0 << VPLL1_WORK_MODE_SHIFT);
1188ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL0_WORK_MODE_MASK,
1198ec8d58eSZhihuan He VPLL0_WORK_MODE_XIN_OSC0 << VPLL0_WORK_MODE_SHIFT);
1208ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, DPLL_WORK_MODE_MASK,
1218ec8d58eSZhihuan He DPLL_WORK_MODE_XIN_OSC0 << DPLL_WORK_MODE_SHIFT);
1228ec8d58eSZhihuan He
1238ec8d58eSZhihuan He /* set PLL without level shift */
1248ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL1_CLK_SEL_MASK,
1258ec8d58eSZhihuan He VPLL1_CLK_SEL_WITHOUT_LVL_SHIFT << VPLL1_CLK_SEL_SHIFT);
1268ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL0_CLK_SEL_MASK,
1278ec8d58eSZhihuan He VPLL0_CLK_SEL_WITHOUT_LVL_SHIFT << VPLL0_CLK_SEL_SHIFT);
1288ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, DPLL_CLK_SEL_MASK,
1298ec8d58eSZhihuan He DPLL_CLK_SEL_WITHOUT_LVL_SHIFT << DPLL_CLK_SEL_SHIFT);
1308ec8d58eSZhihuan He
1318ec8d58eSZhihuan He /* set vpll1 in 903.168MHz vco = 1.806GHz */
1328ec8d58eSZhihuan He rk3308_pll_div.refdiv = 2;
1338ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 150;
1348ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 2;
1358ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
1368ec8d58eSZhihuan He rk3308_pll_div.frac = 0x872B02;
1378ec8d58eSZhihuan He rk3308_pll_div.dsmpd = 0;
1388ec8d58eSZhihuan He pll_set(VPLL1, priv, &rk3308_pll_div);
1398ec8d58eSZhihuan He
1408ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq == 393) {
1418ec8d58eSZhihuan He /* set vpll0 in 786.432MHz vco = 3.146GHz */
1428ec8d58eSZhihuan He rk3308_pll_div.refdiv = 2;
1438ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 262;
1448ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 4;
1458ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
1468ec8d58eSZhihuan He rk3308_pll_div.frac = 0x24DD2F;
1478ec8d58eSZhihuan He rk3308_pll_div.dsmpd = 0;
1488ec8d58eSZhihuan He } else {
1498ec8d58eSZhihuan He /* set vpll0 in 1179.648MHz, vco = 2.359GHz*/
1508ec8d58eSZhihuan He rk3308_pll_div.refdiv = 2;
1518ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 196;
1528ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 2;
1538ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
1548ec8d58eSZhihuan He rk3308_pll_div.frac = 0x9BA5E3;
1558ec8d58eSZhihuan He rk3308_pll_div.dsmpd = 0;
1568ec8d58eSZhihuan He }
1578ec8d58eSZhihuan He pll_set(VPLL0, priv, &rk3308_pll_div);
1588ec8d58eSZhihuan He
1598ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq == 800) {
1608ec8d58eSZhihuan He ddr_pll_sel = 0;
1618ec8d58eSZhihuan He ddr_phy_div_con = 0;
1628ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 589) {
1638ec8d58eSZhihuan He ddr_pll_sel = 1;
1648ec8d58eSZhihuan He ddr_phy_div_con = 0;
1658ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 451) {
1668ec8d58eSZhihuan He ddr_pll_sel = 2;
1678ec8d58eSZhihuan He ddr_phy_div_con = 0;
1688ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 393) {
1698ec8d58eSZhihuan He ddr_pll_sel = 1;
1708ec8d58eSZhihuan He ddr_phy_div_con = 0;
1718ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 294) {
1728ec8d58eSZhihuan He ddr_pll_sel = 1;
1738ec8d58eSZhihuan He ddr_phy_div_con = 1;
1748ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 225) {
1758ec8d58eSZhihuan He ddr_pll_sel = 2;
1768ec8d58eSZhihuan He ddr_phy_div_con = 1;
1778ec8d58eSZhihuan He } else {
1788ec8d58eSZhihuan He printascii("err\n");
1798ec8d58eSZhihuan He while (1)
1808ec8d58eSZhihuan He ;
1818ec8d58eSZhihuan He }
1828ec8d58eSZhihuan He
1838ec8d58eSZhihuan He /* dpll default set in 1300MHz */
1848ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq == 800) {
1858ec8d58eSZhihuan He /* set dpll in 1584 MHz ,vco=3.168G*/
1868ec8d58eSZhihuan He rk3308_pll_div.refdiv = 1;
1878ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 132;
1888ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 2;
1898ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
1908ec8d58eSZhihuan He rk3308_pll_div.frac = 0;
1918ec8d58eSZhihuan He rk3308_pll_div.dsmpd = 1;
1928ec8d58eSZhihuan He } else {
1938ec8d58eSZhihuan He /* 1300000000,vco = 1.3GHz */
1948ec8d58eSZhihuan He rk3308_pll_div.refdiv = 6;
1958ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 325;
1968ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 1;
1978ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
1988ec8d58eSZhihuan He rk3308_pll_div.frac = 0;
1998ec8d58eSZhihuan He rk3308_pll_div.dsmpd = 1;
2008ec8d58eSZhihuan He }
2018ec8d58eSZhihuan He
2028ec8d58eSZhihuan He pll_set(DPLL, priv, &rk3308_pll_div);
2038ec8d58eSZhihuan He
2048ec8d58eSZhihuan He /* set ddrphy freq */
2058ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[1],
2068ec8d58eSZhihuan He DDRPHY4X_PLL_CLK_SEL_MASK | DDRPHY4X_DIV_CON_MASK,
2078ec8d58eSZhihuan He ddr_pll_sel << DDRPHY4X_PLL_CLK_SEL_SHIFT |
2088ec8d58eSZhihuan He ddr_phy_div_con << DDRPHY4X_DIV_CON_SIHFT);
2098ec8d58eSZhihuan He
2108ec8d58eSZhihuan He /* set aclk_bus 216.7MHz */
2118ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[5],
2128ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_MASK | ACLK_BUS_DIV_CON_MASK,
2138ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_DPLL << A_H_PCLK_BUS_PLL_SEL_SHIFT |
2148ec8d58eSZhihuan He ACLK_BUS_DIV_CON_5 << ACLK_BUS_DIV_CON_SHIFT);
2158ec8d58eSZhihuan He /* set pclk_bus 50MHz,hclk_bus 92.857MHz */
2168ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[6],
2178ec8d58eSZhihuan He PCLK_BUS_DIV_CON_MASK | HCLK_BUS_DIV_CON_MASK,
2188ec8d58eSZhihuan He PCLK_BUS_DIV_CON_25 << PCLK_BUS_DIV_CON_SHIFT |
2198ec8d58eSZhihuan He HCLK_BUS_DIV_CON_13 << HCLK_BUS_DIV_CON_SHIFT);
2208ec8d58eSZhihuan He /* set crypto 92.857MHz,crypto_apk 92.857MHz */
2218ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[7],
2228ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_MASK | CLK_CRYPTO_APK_DIV_MASK |
2238ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_MASK | CLK_CRYPTO_DIV_CON_MASK,
2248ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_DPLL << CLK_CRYPTO_APK_SEL_SHIFT |
2258ec8d58eSZhihuan He CLK_CRYPTO_APK_DIV_13 << CLK_CRYPTO_APK_DIV_SHIFT |
2268ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_DPLL << CLK_CRYPTO_PLL_SEL_SHIFT |
2278ec8d58eSZhihuan He CLK_CRYPTO_DIV_CON_13 << CLK_CRYPTO_DIV_CON_SHIFT);
2288ec8d58eSZhihuan He /* set aclk_peri 216.7MHz */
2298ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[36],
2308ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_MASK | ACLK_PERI_DIV_CON_MASK,
2318ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_DPLL << A_H_P_PERI_PLL_SEL_SHIFT |
2328ec8d58eSZhihuan He ACLK_PERI_DIV_CON_5 << ACLK_PERI_DIV_CON_SHIFT);
2338ec8d58eSZhihuan He /* set hclk_peri 92.857MHz,pclk_peri 46.428MHz */
2348ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[37],
2358ec8d58eSZhihuan He PCLK_PERI_DIV_CON_MASK | HCLK_PERI_DIV_CON_MASK,
2368ec8d58eSZhihuan He PCLK_PERI_DIV_CON_27 << PCLK_PERI_DIV_CON_SHIFT |
2378ec8d58eSZhihuan He HCLK_PERI_DIV_CON_13 << HCLK_PERI_DIV_CON_SHIFT);
2388ec8d58eSZhihuan He /* set NANDC 92.857MHz */
2398ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[38],
2408ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_MASK |
2418ec8d58eSZhihuan He CLK_NANDC_DIV_CON_MASK,
2428ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_DPLL << CLK_NANDC_PLL_SEL_SHIFT |
2438ec8d58eSZhihuan He CLK_NANDC_DIV_CON_13 << CLK_NANDC_DIV_CON_SHIFT);
2448ec8d58eSZhihuan He /* set SDMMC 46.4/(internal freq_div 2)=23.2MHz */
2458ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[39],
2468ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_MASK |
2478ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_MASK,
2488ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_DPLL << CLK_SDMMC_PLL_SEL_SHIFT |
2498ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_27 << CLK_SDMMC_DIV_CON_SHIFT);
2508ec8d58eSZhihuan He /* set emmc 46.4/(internal freq_div 2)=23.2MHz */
2518ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[41],
2528ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_MASK |
2538ec8d58eSZhihuan He CLK_EMMC_DIV_CON_MASK,
2548ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_DPLL << CLK_EMMC_PLL_SEL_SHIFT |
2558ec8d58eSZhihuan He CLK_EMMC_DIV_CON_27 << CLK_EMMC_DIV_CON_SHIFT);
2568ec8d58eSZhihuan He /* set SFC 24.07/(internal freq_div 2)=12.0MHz */
2578ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[42],
2588ec8d58eSZhihuan He CLK_SFC_PLL_SEL_MASK | CLK_SFC_DIV_CON_MASK,
2598ec8d58eSZhihuan He CLK_SFC_PLL_SEL_DPLL << CLK_SFC_PLL_SEL_SHIFT |
2608ec8d58eSZhihuan He CLK_SFC_DIV_CON_53 << CLK_SFC_DIV_CON_SHIFT);
2618ec8d58eSZhihuan He #if defined(CONFIG_DPLL_FREQ_1200MHZ)
2628ec8d58eSZhihuan He /*vco=1.2GHz*/
2638ec8d58eSZhihuan He rk3308_pll_div.refdiv = 2;
2648ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 100;
2658ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 1;
2668ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
2678ec8d58eSZhihuan He rk3308_pll_div.frac = 0;
2688ec8d58eSZhihuan He
2698ec8d58eSZhihuan He /* set dpll in 1200 MHz */
2708ec8d58eSZhihuan He pll_set(DPLL, priv, &rk3308_pll_div);
2718ec8d58eSZhihuan He
2728ec8d58eSZhihuan He /* set aclk_bus 200MHz */
2738ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[5],
2748ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_MASK | ACLK_BUS_DIV_CON_MASK,
2758ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_DPLL << A_H_PCLK_BUS_PLL_SEL_SHIFT |
2768ec8d58eSZhihuan He ACLK_BUS_DIV_CON_5 << ACLK_BUS_DIV_CON_SHIFT);
2778ec8d58eSZhihuan He /* set pclk_bus 46.15MHz,hclk_bus 100MHz */
2788ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[6],
2798ec8d58eSZhihuan He PCLK_BUS_DIV_CON_MASK | HCLK_BUS_DIV_CON_MASK,
2808ec8d58eSZhihuan He PCLK_BUS_DIV_CON_25 << PCLK_BUS_DIV_CON_SHIFT |
2818ec8d58eSZhihuan He HCLK_BUS_DIV_CON_11 << HCLK_BUS_DIV_CON_SHIFT);
2828ec8d58eSZhihuan He /* set crypto,crypto_apk 100MHz */
2838ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[7],
2848ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_MASK | CLK_CRYPTO_APK_DIV_MASK |
2858ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_MASK | CLK_CRYPTO_DIV_CON_MASK,
2868ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_DPLL << CLK_CRYPTO_APK_SEL_SHIFT |
2878ec8d58eSZhihuan He CLK_CRYPTO_APK_DIV_11 << CLK_CRYPTO_APK_DIV_SHIFT |
2888ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_DPLL << CLK_CRYPTO_PLL_SEL_SHIFT |
2898ec8d58eSZhihuan He CLK_CRYPTO_DIV_CON_11 << CLK_CRYPTO_DIV_CON_SHIFT);
2908ec8d58eSZhihuan He /* set aclk_peri 200MHz */
2918ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[36],
2928ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_MASK | ACLK_PERI_DIV_CON_MASK,
2938ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_DPLL << A_H_P_PERI_PLL_SEL_SHIFT |
2948ec8d58eSZhihuan He ACLK_PERI_DIV_CON_5 << ACLK_PERI_DIV_CON_SHIFT);
2958ec8d58eSZhihuan He /* set hclk_peri 100MHz,pclk_peri 50MHz */
2968ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[37],
2978ec8d58eSZhihuan He PCLK_PERI_DIV_CON_MASK | HCLK_PERI_DIV_CON_MASK,
2988ec8d58eSZhihuan He PCLK_PERI_DIV_CON_23 << PCLK_PERI_DIV_CON_SHIFT |
2998ec8d58eSZhihuan He HCLK_PERI_DIV_CON_11 << HCLK_PERI_DIV_CON_SHIFT);
3008ec8d58eSZhihuan He /* set NANDC 100MHz */
3018ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[38],
3028ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_MASK |
3038ec8d58eSZhihuan He CLK_NANDC_DIV_CON_MASK,
3048ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_DPLL << CLK_NANDC_PLL_SEL_SHIFT |
3058ec8d58eSZhihuan He CLK_NANDC_DIV_CON_11 << CLK_NANDC_DIV_CON_SHIFT);
3068ec8d58eSZhihuan He /* set SDMMC 50MHz */
3078ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[39],
3088ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_MASK |
3098ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_MASK,
3108ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_DPLL << CLK_SDMMC_PLL_SEL_SHIFT |
3118ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_23 << CLK_SDMMC_DIV_CON_SHIFT);
3128ec8d58eSZhihuan He /* set emmc 50MHz */
3138ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[41],
3148ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_MASK |
3158ec8d58eSZhihuan He CLK_EMMC_DIV_CON_MASK,
3168ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_DPLL << CLK_EMMC_PLL_SEL_SHIFT |
3178ec8d58eSZhihuan He CLK_EMMC_DIV_CON_23 << CLK_EMMC_DIV_CON_SHIFT);
3188ec8d58eSZhihuan He /* set SFC 24MHz */
3198ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[42],
3208ec8d58eSZhihuan He CLK_SFC_PLL_SEL_MASK | CLK_SFC_DIV_CON_MASK,
3218ec8d58eSZhihuan He CLK_SFC_PLL_SEL_DPLL << CLK_SFC_PLL_SEL_SHIFT |
3228ec8d58eSZhihuan He CLK_SFC_DIV_CON_49 << CLK_SFC_DIV_CON_SHIFT);
3238ec8d58eSZhihuan He
3248ec8d58eSZhihuan He #elif defined(CONFIG_DPLL_FREQ_748MHZ)
3258ec8d58eSZhihuan He /*vco=1.5GHz*/
3268ec8d58eSZhihuan He rk3308_pll_div.refdiv = 6;
3278ec8d58eSZhihuan He rk3308_pll_div.fbdiv = 374;
3288ec8d58eSZhihuan He rk3308_pll_div.postdiv1 = 2;
3298ec8d58eSZhihuan He rk3308_pll_div.postdiv2 = 1;
3308ec8d58eSZhihuan He rk3308_pll_div.frac = 0;
3318ec8d58eSZhihuan He
3328ec8d58eSZhihuan He /* set dpll in 748 MHz */
3338ec8d58eSZhihuan He pll_set(DPLL, priv, &rk3308_pll_div);
3348ec8d58eSZhihuan He
3358ec8d58eSZhihuan He /* set aclk_bus 187MHz */
3368ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[5],
3378ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_MASK | ACLK_BUS_DIV_CON_MASK,
3388ec8d58eSZhihuan He A_H_PCLK_BUS_PLL_SEL_DPLL << A_H_PCLK_BUS_PLL_SEL_SHIFT |
3398ec8d58eSZhihuan He ACLK_BUS_DIV_CON_3 << ACLK_BUS_DIV_CON_SHIFT);
3408ec8d58eSZhihuan He /* set pclk_bus 46.75MHz,hclk_bus 93.5MHz */
3418ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[6],
3428ec8d58eSZhihuan He PCLK_BUS_DIV_CON_MASK | HCLK_BUS_DIV_CON_MASK,
3438ec8d58eSZhihuan He PCLK_BUS_DIV_CON_15 << PCLK_BUS_DIV_CON_SHIFT |
3448ec8d58eSZhihuan He HCLK_BUS_DIV_CON_7 << HCLK_BUS_DIV_CON_SHIFT);
3458ec8d58eSZhihuan He /* set crypto,crypto_apk 93.5MHz */
3468ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[7],
3478ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_MASK | CLK_CRYPTO_APK_DIV_MASK |
3488ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_MASK | CLK_CRYPTO_DIV_CON_MASK,
3498ec8d58eSZhihuan He CLK_CRYPTO_APK_SEL_DPLL << CLK_CRYPTO_APK_SEL_SHIFT |
3508ec8d58eSZhihuan He CLK_CRYPTO_APK_DIV_7 << CLK_CRYPTO_APK_DIV_SHIFT |
3518ec8d58eSZhihuan He CLK_CRYPTO_PLL_SEL_DPLL << CLK_CRYPTO_PLL_SEL_SHIFT |
3528ec8d58eSZhihuan He CLK_CRYPTO_DIV_CON_7 << CLK_CRYPTO_DIV_CON_SHIFT);
3538ec8d58eSZhihuan He /* set aclk_peri 187MHz */
3548ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[36],
3558ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_MASK | ACLK_PERI_DIV_CON_MASK,
3568ec8d58eSZhihuan He A_H_P_PERI_PLL_SEL_DPLL << A_H_P_PERI_PLL_SEL_SHIFT |
3578ec8d58eSZhihuan He ACLK_PERI_DIV_CON_3 << ACLK_PERI_DIV_CON_SHIFT);
3588ec8d58eSZhihuan He /* set hclk_peri 93.5MHz,pclk_peri 46.75MHz */
3598ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[37],
3608ec8d58eSZhihuan He PCLK_PERI_DIV_CON_MASK | HCLK_PERI_DIV_CON_MASK,
3618ec8d58eSZhihuan He PCLK_PERI_DIV_CON_15 << PCLK_PERI_DIV_CON_SHIFT |
3628ec8d58eSZhihuan He HCLK_PERI_DIV_CON_7 << HCLK_PERI_DIV_CON_SHIFT);
3638ec8d58eSZhihuan He /* set NANDC 93.5MHz */
3648ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[38],
3658ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_MASK |
3668ec8d58eSZhihuan He CLK_NANDC_DIV_CON_MASK,
3678ec8d58eSZhihuan He CLK_NANDC_SEL50_ALWAYS << CLK_NANDC_SEL50_SHIFT |
3688ec8d58eSZhihuan He CLK_NANDC_PLL_SEL_DPLL << CLK_NANDC_PLL_SEL_SHIFT |
3698ec8d58eSZhihuan He CLK_NANDC_DIV_CON_7 << CLK_NANDC_DIV_CON_SHIFT);
3708ec8d58eSZhihuan He /* set NANDC 46.75MHz */
3718ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[39],
3728ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_MASK |
3738ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_MASK,
3748ec8d58eSZhihuan He CLK_SDMMC_PLL_SEL_DPLL << CLK_SDMMC_PLL_SEL_SHIFT |
3758ec8d58eSZhihuan He CLK_SDMMC_DIV_CON_15 << CLK_SDMMC_DIV_CON_SHIFT);
3768ec8d58eSZhihuan He /* set emmc 46.75MHz */
3778ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[41],
3788ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_MASK |
3798ec8d58eSZhihuan He CLK_EMMC_DIV_CON_MASK,
3808ec8d58eSZhihuan He CLK_EMMC_PLL_SEL_DPLL << CLK_EMMC_PLL_SEL_SHIFT |
3818ec8d58eSZhihuan He CLK_EMMC_DIV_CON_15 << CLK_EMMC_DIV_CON_SHIFT);
3828ec8d58eSZhihuan He /* set SFC 23.375MHz */
3838ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[42],
3848ec8d58eSZhihuan He CLK_SFC_PLL_SEL_MASK | CLK_SFC_DIV_CON_MASK,
3858ec8d58eSZhihuan He CLK_SFC_PLL_SEL_DPLL << CLK_SFC_PLL_SEL_SHIFT |
3868ec8d58eSZhihuan He CLK_SFC_DIV_CON_31 << CLK_SFC_DIV_CON_SHIFT);
3878ec8d58eSZhihuan He
3888ec8d58eSZhihuan He #endif
3898ec8d58eSZhihuan He /* set spdif tx lower than 100Mhz */
3908ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[48],
3918ec8d58eSZhihuan He CLK_SPDIFTX_DIV_CON_MASK,
3928ec8d58eSZhihuan He CLK_SPDIFTX_DIV_CON_15 << CLK_SPDIFTX_DIV_CON_SHIFT);
3938ec8d58eSZhihuan He
3948ec8d58eSZhihuan He if (UART_INFO_ID(ddr_gd.head_info.g_uart_info) < 5)
3958ec8d58eSZhihuan He uart_div[UART_INFO_ID(ddr_gd.head_info.g_uart_info)] = 0;
3968ec8d58eSZhihuan He
3978ec8d58eSZhihuan He /* set uart0~4 lower than 100Mhz */
3988ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[10],
3998ec8d58eSZhihuan He CLK_UART0_DIV_CON_MASK,
4008ec8d58eSZhihuan He uart_div[0] << CLK_UART0_DIV_CON_SHIFT);
4018ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[13],
4028ec8d58eSZhihuan He CLK_UART1_DIV_CON_MASK,
4038ec8d58eSZhihuan He uart_div[1] << CLK_UART1_DIV_CON_SHIFT);
4048ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[16],
4058ec8d58eSZhihuan He CLK_UART2_DIV_CON_MASK,
4068ec8d58eSZhihuan He uart_div[2] << CLK_UART2_DIV_CON_SHIFT);
4078ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[19],
4088ec8d58eSZhihuan He CLK_UART3_DIV_CON_MASK,
4098ec8d58eSZhihuan He uart_div[3] << CLK_UART3_DIV_CON_SHIFT);
4108ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->clksel_con[22],
4118ec8d58eSZhihuan He CLK_UART4_DIV_CON_MASK,
4128ec8d58eSZhihuan He uart_div[4] << CLK_UART4_DIV_CON_SHIFT);
4138ec8d58eSZhihuan He
4148ec8d58eSZhihuan He /* pll clk in pll out */
4158ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL1_WORK_MODE_MASK,
4168ec8d58eSZhihuan He VPLL1_WORK_MODE_PLL << VPLL1_WORK_MODE_SHIFT);
4178ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, VPLL0_WORK_MODE_MASK,
4188ec8d58eSZhihuan He VPLL0_WORK_MODE_PLL << VPLL0_WORK_MODE_SHIFT);
4198ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->mode, DPLL_WORK_MODE_MASK,
4208ec8d58eSZhihuan He DPLL_WORK_MODE_PLL << DPLL_WORK_MODE_SHIFT);
4218ec8d58eSZhihuan He }
4228ec8d58eSZhihuan He
phy_pctrl_reset_cru(struct dram_info * priv)4238ec8d58eSZhihuan He void phy_pctrl_reset_cru(struct dram_info *priv)
4248ec8d58eSZhihuan He {
4258ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->softrst_con[1],
4268ec8d58eSZhihuan He PRESETN_DDRPHY_REQ_MASK | RESETN_DDRPHYDIV_REQ_MASK |
4278ec8d58eSZhihuan He RESETN_DDRPHY_REQ_MASK | PRESETN_DDRUPCTL_REQ_MASK |
4288ec8d58eSZhihuan He RESETN_DDRUPCTL_REQ_MASK,
4298ec8d58eSZhihuan He PRESETN_DDRPHY_REQ_EN << PRESETN_DDRPHY_REQ_SHIFT |
4308ec8d58eSZhihuan He RESETN_DDRPHYDIV_REQ_EN << RESETN_DDRPHYDIV_REQ_SHIFT |
4318ec8d58eSZhihuan He RESETN_DDRPHY_REQ_EN << RESETN_DDRPHY_REQ_SHIFT |
4328ec8d58eSZhihuan He PRESETN_DDRUPCTL_REQ_EN << PRESETN_DDRUPCTL_REQ_SHIFT |
4338ec8d58eSZhihuan He RESETN_DDRUPCTL_REQ_EN << RESETN_DDRUPCTL_REQ_SHIFT);
4348ec8d58eSZhihuan He udelay(10);
4358ec8d58eSZhihuan He
4368ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->softrst_con[1],
4378ec8d58eSZhihuan He PRESETN_DDRPHY_REQ_MASK | RESETN_DDRPHYDIV_REQ_MASK |
4388ec8d58eSZhihuan He RESETN_DDRPHY_REQ_MASK,
4398ec8d58eSZhihuan He PRESETN_DDRPHY_REQ_DIS << PRESETN_DDRPHY_REQ_SHIFT |
4408ec8d58eSZhihuan He RESETN_DDRPHYDIV_REQ_DIS << RESETN_DDRPHYDIV_REQ_SHIFT |
4418ec8d58eSZhihuan He RESETN_DDRPHY_REQ_DIS << RESETN_DDRPHY_REQ_SHIFT);
4428ec8d58eSZhihuan He udelay(10);
4438ec8d58eSZhihuan He
4448ec8d58eSZhihuan He rk_clrsetreg(&priv->cru->softrst_con[1],
4458ec8d58eSZhihuan He PRESETN_DDRUPCTL_REQ_MASK | RESETN_DDRUPCTL_REQ_MASK,
4468ec8d58eSZhihuan He PRESETN_DDRUPCTL_REQ_DIS << PRESETN_DDRUPCTL_REQ_SHIFT |
4478ec8d58eSZhihuan He RESETN_DDRUPCTL_REQ_DIS << RESETN_DDRUPCTL_REQ_SHIFT);
4488ec8d58eSZhihuan He udelay(10);
4498ec8d58eSZhihuan He }
4508ec8d58eSZhihuan He
pctl_cfg_grf(struct dram_info * priv,struct sdram_params * params_priv)4518ec8d58eSZhihuan He void pctl_cfg_grf(struct dram_info *priv,
4528ec8d58eSZhihuan He struct sdram_params *params_priv)
4538ec8d58eSZhihuan He {
4548ec8d58eSZhihuan He if (params_priv->ddr_config_t.ddr_type == DDR3 ||
4558ec8d58eSZhihuan He params_priv->ddr_config_t.ddr_type == DDR2)
4568ec8d58eSZhihuan He rk_clrsetreg(&priv->grf->soc_con12, NOC_MSCH_MAINDDR3_MASK,
4578ec8d58eSZhihuan He NOC_MSCH_MAINDDR3_EN << NOC_MSCH_MAINDDR3_SHIFT);
4588ec8d58eSZhihuan He else
4598ec8d58eSZhihuan He rk_clrsetreg(&priv->grf->soc_con12, NOC_MSCH_MAINDDR3_MASK,
4608ec8d58eSZhihuan He NOC_MSCH_MAINDDR3_DIS << NOC_MSCH_MAINDDR3_SHIFT);
4618ec8d58eSZhihuan He }
4628ec8d58eSZhihuan He
ddr_msch_cfg(struct dram_info * priv,struct sdram_params * params_priv)4638ec8d58eSZhihuan He void ddr_msch_cfg(struct dram_info *priv,
4648ec8d58eSZhihuan He struct sdram_params *params_priv)
4658ec8d58eSZhihuan He {
4668ec8d58eSZhihuan He writel(BWRATIO_HALF_BW | params_priv->ddr_timing_t.noc_timing.d32,
4678ec8d58eSZhihuan He &priv->service_msch->ddrtiming);
4688ec8d58eSZhihuan He writel(params_priv->ddr_timing_t.readlatency,
4698ec8d58eSZhihuan He &priv->service_msch->readlatency);
4708ec8d58eSZhihuan He }
4718ec8d58eSZhihuan He
ddr_msch_cfg_rbc(struct sdram_params * params_priv,struct dram_info * priv)4728ec8d58eSZhihuan He void ddr_msch_cfg_rbc(struct sdram_params *params_priv,
4738ec8d58eSZhihuan He struct dram_info *priv)
4748ec8d58eSZhihuan He {
4758ec8d58eSZhihuan He int i = 0;
4768ec8d58eSZhihuan He
4778ec8d58eSZhihuan He if (params_priv->ddr_config_t.bank == 3) {
4788ec8d58eSZhihuan He /* bank = 8 */
4798ec8d58eSZhihuan He if (params_priv->ddr_config_t.col == 10)
4808ec8d58eSZhihuan He i = 1;
4818ec8d58eSZhihuan He else if (params_priv->ddr_config_t.col == 11)
4828ec8d58eSZhihuan He i = 2;
4838ec8d58eSZhihuan He else
4848ec8d58eSZhihuan He goto msch_err;
4858ec8d58eSZhihuan He
4868ec8d58eSZhihuan He } else if (params_priv->ddr_config_t.bank == 2) {
4878ec8d58eSZhihuan He /* bank = 4 */
4888ec8d58eSZhihuan He i = 0;
4898ec8d58eSZhihuan He } else {
4908ec8d58eSZhihuan He goto msch_err;
4918ec8d58eSZhihuan He }
4928ec8d58eSZhihuan He
4938ec8d58eSZhihuan He writel(i, &priv->service_msch->ddrconf);
4948ec8d58eSZhihuan He return;
4958ec8d58eSZhihuan He
4968ec8d58eSZhihuan He msch_err:
4978ec8d58eSZhihuan He printascii("msch_err\n");
4988ec8d58eSZhihuan He while (1)
4998ec8d58eSZhihuan He ;
5008ec8d58eSZhihuan He }
5018ec8d58eSZhihuan He
ddr_phy_skew_cfg(struct dram_info * priv)5028ec8d58eSZhihuan He void ddr_phy_skew_cfg(struct dram_info *priv)
5038ec8d58eSZhihuan He {
5048ec8d58eSZhihuan He copy_to_reg(&priv->phy->phy_reg_ca_skew[0],
5058ec8d58eSZhihuan He &ddr_gd.ddr_skew.a0_a1_skew[0], 14 * 4);
5068ec8d58eSZhihuan He copy_to_reg(&priv->phy->phy_reg_skew_cs0data[0],
5078ec8d58eSZhihuan He &ddr_gd.ddr_skew.cs0_dm0_skew[0], 22 * 4);
5088ec8d58eSZhihuan He
5098ec8d58eSZhihuan He writel(PHY_TX_DE_SKEW_EN << PHY_TX_DE_SKEW_SHIFT,
5108ec8d58eSZhihuan He &priv->phy->phy_reg2);
5118ec8d58eSZhihuan He }
5128ec8d58eSZhihuan He
set_ds_odt(struct dram_info * priv,struct sdram_params * params_priv)5138ec8d58eSZhihuan He void set_ds_odt(struct dram_info *priv,
5148ec8d58eSZhihuan He struct sdram_params *params_priv)
5158ec8d58eSZhihuan He {
5168ec8d58eSZhihuan He /* set phy drive resistance */
5178ec8d58eSZhihuan He writel(PHY_RON_RTT_56OHM, &priv->phy->phy_reg11);
5188ec8d58eSZhihuan He clrsetbits_le32(&priv->phy->phy_reg12, CMD_PRCOMP_MASK,
5198ec8d58eSZhihuan He PHY_RON_RTT_56OHM << CMD_PRCOMP_SHIFT);
5208ec8d58eSZhihuan He
5218ec8d58eSZhihuan He writel(PHY_RON_RTT_45OHM, &priv->phy->phy_reg16);
5228ec8d58eSZhihuan He writel(PHY_RON_RTT_45OHM, &priv->phy->phy_reg18);
5238ec8d58eSZhihuan He writel(PHY_RON_RTT_56OHM, &priv->phy->phy_reg20);
5248ec8d58eSZhihuan He writel(PHY_RON_RTT_56OHM, &priv->phy->phy_reg2f);
5258ec8d58eSZhihuan He writel(PHY_RON_RTT_56OHM, &priv->phy->phy_reg30);
5268ec8d58eSZhihuan He writel(PHY_RON_RTT_56OHM, &priv->phy->phy_reg3f);
5278ec8d58eSZhihuan He if (params_priv->ddr_config_t.ddr_type == LPDDR2) {
5288ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg21);
5298ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg2e);
5308ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg31);
5318ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg3e);
5328ec8d58eSZhihuan He } else {
5338ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq >
5348ec8d58eSZhihuan He DDR3_DDR2_ODT_DISABLE_FREQ) {
5358ec8d58eSZhihuan He /*set phy odt*/
5368ec8d58eSZhihuan He writel(PHY_RON_RTT_225OHM, &priv->phy->phy_reg21);
5378ec8d58eSZhihuan He writel(PHY_RON_RTT_225OHM, &priv->phy->phy_reg2e);
5388ec8d58eSZhihuan He writel(PHY_RON_RTT_225OHM, &priv->phy->phy_reg31);
5398ec8d58eSZhihuan He writel(PHY_RON_RTT_225OHM, &priv->phy->phy_reg3e);
5408ec8d58eSZhihuan He } else {
5418ec8d58eSZhihuan He /*disable phy odt*/
5428ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg21);
5438ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg2e);
5448ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg31);
5458ec8d58eSZhihuan He writel(PHY_RON_RTT_DISABLE, &priv->phy->phy_reg3e);
5468ec8d58eSZhihuan He }
5478ec8d58eSZhihuan He }
5488ec8d58eSZhihuan He }
5498ec8d58eSZhihuan He
ddr_phy_dqs_rx_dll_cfg(struct dram_info * priv,u32 freq)5508ec8d58eSZhihuan He void ddr_phy_dqs_rx_dll_cfg(struct dram_info *priv, u32 freq)
5518ec8d58eSZhihuan He {
5528ec8d58eSZhihuan He if (freq > 736) {
5538ec8d58eSZhihuan He /* 22.5 degree delay */
5548ec8d58eSZhihuan He writel(LEFT_CHN_A_READ_DQS_22_5_DELAY, &priv->phy->phy_reg28);
5558ec8d58eSZhihuan He writel(RIGHT_CHN_A_READ_DQS_22_5_DELAY, &priv->phy->phy_reg38);
556b175adb4SWesley Yao } else {
5578ec8d58eSZhihuan He /* 45 degree delay */
5588ec8d58eSZhihuan He writel(LEFT_CHN_A_READ_DQS_45_DELAY, &priv->phy->phy_reg28);
5598ec8d58eSZhihuan He writel(RIGHT_CHN_A_READ_DQS_45_DELAY, &priv->phy->phy_reg38);
5608ec8d58eSZhihuan He }
5618ec8d58eSZhihuan He }
5628ec8d58eSZhihuan He
ddr_msch_get_max_col(struct dram_info * priv,struct ddr_schedule * sch_priv)5638ec8d58eSZhihuan He void ddr_msch_get_max_col(struct dram_info *priv,
5648ec8d58eSZhihuan He struct ddr_schedule *sch_priv)
5658ec8d58eSZhihuan He {
5668ec8d58eSZhihuan He writel(2, &priv->service_msch->ddrconf);
5678ec8d58eSZhihuan He sch_priv->col = 11;
5688ec8d58eSZhihuan He sch_priv->bank = 3;
5698ec8d58eSZhihuan He }
5708ec8d58eSZhihuan He
ddr_msch_get_max_row(struct dram_info * priv,struct ddr_schedule * sch_priv)5718ec8d58eSZhihuan He void ddr_msch_get_max_row(struct dram_info *priv,
5728ec8d58eSZhihuan He struct ddr_schedule *sch_priv)
5738ec8d58eSZhihuan He {
5748ec8d58eSZhihuan He writel(1, &priv->service_msch->ddrconf);
5758ec8d58eSZhihuan He sch_priv->row = 15;
5768ec8d58eSZhihuan He sch_priv->col = 10;
5778ec8d58eSZhihuan He sch_priv->bank = 3;
5788ec8d58eSZhihuan He }
5798ec8d58eSZhihuan He
enable_ddr_standby(struct dram_info * priv,struct sdram_params * params_priv)5808ec8d58eSZhihuan He void enable_ddr_standby(struct dram_info *priv,
5818ec8d58eSZhihuan He struct sdram_params *params_priv)
5828ec8d58eSZhihuan He {
5838ec8d58eSZhihuan He rk_clrsetreg(&priv->grf->upctl_con0, CYSYREQ_UPCTL_DDRSTDBY_MASK,
5848ec8d58eSZhihuan He CYSYREQ_UPCTL_DDRSTDBY_EN <<
5858ec8d58eSZhihuan He CYSYREQ_UPCTL_DDRSTDBY_SHIFT);
5868ec8d58eSZhihuan He
5878ec8d58eSZhihuan He /* CG_EXIT_TH is equal phy dll lock time when we gate phy 4x clk */
5888ec8d58eSZhihuan He writel(CG_EXIT_TH << CG_EXIT_TH_SHIFT, &priv->standby->con1);
5898ec8d58eSZhihuan He
5908ec8d58eSZhihuan He if (params_priv->stdby_idle == 128) {
5918ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq == 451)
5928ec8d58eSZhihuan He params_priv->stdby_idle = 105;
5938ec8d58eSZhihuan He else if (params_priv->ddr_timing_t.freq == 393)
5948ec8d58eSZhihuan He params_priv->stdby_idle = 10;
5958ec8d58eSZhihuan He }
5968ec8d58eSZhihuan He writel(params_priv->stdby_idle << IDLE_TH_SHIFT |
5978ec8d58eSZhihuan He DDRPHY4X_GATE_EN << DDRPHY4X_GATE_SHIFT |
5988ec8d58eSZhihuan He UPCTL_CORE_CLK_GATE_EN << UPCTL_CORE_CLK_GATE_SHIFT |
5998ec8d58eSZhihuan He UPCTL_ACLK_GATE_EN << UPCTL_ACLK_GATE_SHIFT |
6008ec8d58eSZhihuan He CTL_IDLR_EN << CTL_IDLR_SHIFT |
6018ec8d58eSZhihuan He STDBY_EN << STDBY_EN_SHIFT, &priv->standby->con0);
6028ec8d58eSZhihuan He
6038ec8d58eSZhihuan He while (1) {
6048ec8d58eSZhihuan He if ((readl(&priv->standby->status0) &
6058ec8d58eSZhihuan He STDBY_STATUS_MASK) == ST_STDBY) {
6068ec8d58eSZhihuan He break;
6078ec8d58eSZhihuan He }
6088ec8d58eSZhihuan He }
6098ec8d58eSZhihuan He }
6108ec8d58eSZhihuan He
ddr_set_atags(void)6118ec8d58eSZhihuan He void ddr_set_atags(void)
6128ec8d58eSZhihuan He {
6138ec8d58eSZhihuan He struct tag_serial t_serial;
6148ec8d58eSZhihuan He
6158ec8d58eSZhihuan He memset(&t_serial, 0, sizeof(struct tag_serial));
6168ec8d58eSZhihuan He #ifdef CONFIG_DRAM_INIT_BUILD
6178ec8d58eSZhihuan He u32 uart_info;
6188ec8d58eSZhihuan He
6198ec8d58eSZhihuan He t_serial.version = 0;
6208ec8d58eSZhihuan He uart_info = ddr_gd.head_info.g_uart_info;
6218ec8d58eSZhihuan He if (UART_INFO_ID(uart_info) >= MAX_UART_NUMBER_) {
6228ec8d58eSZhihuan He t_serial.enable = 0;
6238ec8d58eSZhihuan He } else {
6248ec8d58eSZhihuan He t_serial.enable = 1;
6258ec8d58eSZhihuan He t_serial.baudrate = UART_INFO_BAUD(uart_info);
6268ec8d58eSZhihuan He t_serial.m_mode = UART_INFO_IOMUX(uart_info);
6278ec8d58eSZhihuan He t_serial.id = UART_INFO_ID(uart_info);
6288ec8d58eSZhihuan He if (UART_INFO_ID(uart_info) == 0)
6298ec8d58eSZhihuan He t_serial.addr = UART0_BASE;
6308ec8d58eSZhihuan He else if (UART_INFO_ID(uart_info) == 1)
6318ec8d58eSZhihuan He t_serial.addr = UART1_BASE;
6328ec8d58eSZhihuan He else if (UART_INFO_ID(uart_info) == 2)
6338ec8d58eSZhihuan He t_serial.addr = UART2_BASE;
6348ec8d58eSZhihuan He else if (UART_INFO_ID(uart_info) == 3)
6358ec8d58eSZhihuan He t_serial.addr = UART3_BASE;
6368ec8d58eSZhihuan He else
6378ec8d58eSZhihuan He t_serial.addr = UART4_BASE;
6388ec8d58eSZhihuan He }
6398ec8d58eSZhihuan He #else
6408ec8d58eSZhihuan He /* set serial data to &t_serial */
6418ec8d58eSZhihuan He #if defined(CONFIG_DEBUG_UART_BASE)
6428ec8d58eSZhihuan He t_serial.version = 0;
6438ec8d58eSZhihuan He t_serial.enable = 1;
6448ec8d58eSZhihuan He t_serial.addr = CONFIG_DEBUG_UART_BASE;
6458ec8d58eSZhihuan He t_serial.baudrate = CONFIG_BAUDRATE;
6468ec8d58eSZhihuan He
6478ec8d58eSZhihuan He #if (CONFIG_DEBUG_UART_BASE == 0xFF0A0000)
6488ec8d58eSZhihuan He /* uart0 as debug uart */
6498ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M0;
6508ec8d58eSZhihuan He t_serial.id = 0;
6518ec8d58eSZhihuan He #elif (CONFIG_DEBUG_UART_BASE == 0xFF0B0000)
6528ec8d58eSZhihuan He /* uart1 as debug uart */
6538ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M0;
6548ec8d58eSZhihuan He t_serial.id = 1;
6558ec8d58eSZhihuan He #elif (CONFIG_DEBUG_UART_BASE == 0xFF0C0000)
6568ec8d58eSZhihuan He #if (CONFIG_ROCKCHIP_UART_MUX_SEL_M == 0)
6578ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M0;
6588ec8d58eSZhihuan He #elif (CONFIG_ROCKCHIP_UART_MUX_SEL_M == 1)
6598ec8d58eSZhihuan He /* uart2 m1 as debug uart */
6608ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M1;
6618ec8d58eSZhihuan He #else
6628ec8d58eSZhihuan He #error "Please select M0 or M1 for uart2 !!!"
6638ec8d58eSZhihuan He #endif
6648ec8d58eSZhihuan He t_serial.id = 2;
6658ec8d58eSZhihuan He #elif (CONFIG_DEBUG_UART_BASE == 0xFF0D0000)
6668ec8d58eSZhihuan He /* uart3 as debug uart */
6678ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M0;
6688ec8d58eSZhihuan He t_serial.id = 3;
6698ec8d58eSZhihuan He #elif (CONFIG_DEBUG_UART_BASE == 0xFF0E0000)
6708ec8d58eSZhihuan He /* uart4 as debug uart */
6718ec8d58eSZhihuan He t_serial.m_mode = SERIAL_M_MODE_M0;
6728ec8d58eSZhihuan He t_serial.id = 4;
6738ec8d58eSZhihuan He #else
6748ec8d58eSZhihuan He #error "Please select proper uart as debug uart !!!"
6758ec8d58eSZhihuan He #endif
6768ec8d58eSZhihuan He
6778ec8d58eSZhihuan He #endif /* defined(CONFIG_DEBUG_UART_BASE) */
6788ec8d58eSZhihuan He #endif /* CONFIG_DRAM_INIT_BUILD */
6798ec8d58eSZhihuan He
6808ec8d58eSZhihuan He /* First pre-loader must call it before atags_set_tag() */
6818ec8d58eSZhihuan He atags_destroy();
6828ec8d58eSZhihuan He atags_set_tag(ATAG_SERIAL, &t_serial);
6838ec8d58eSZhihuan He }
6848ec8d58eSZhihuan He
modify_sdram_params(struct dram_info * priv,struct sdram_params * params_priv)6858ec8d58eSZhihuan He static void modify_sdram_params(struct dram_info *priv,
6868ec8d58eSZhihuan He struct sdram_params *params_priv)
6878ec8d58eSZhihuan He {
6888ec8d58eSZhihuan He u32 tmp = 0;
6898ec8d58eSZhihuan He u32 bw = 1;
6908ec8d58eSZhihuan He u32 nMHz = params_priv->ddr_timing_t.freq;
6918ec8d58eSZhihuan He
6928ec8d58eSZhihuan He size_t size = 1llu << (bw +
6938ec8d58eSZhihuan He params_priv->ddr_config_t.col +
6948ec8d58eSZhihuan He params_priv->ddr_config_t.cs0_row +
6958ec8d58eSZhihuan He params_priv->ddr_config_t.bank);
6968ec8d58eSZhihuan He
6978ec8d58eSZhihuan He move_to_config_state(priv);
6988ec8d58eSZhihuan He switch (params_priv->ddr_config_t.ddr_type) {
6998ec8d58eSZhihuan He case DDR2:
7008ec8d58eSZhihuan He if (size <= 0x4000000)
7018ec8d58eSZhihuan He tmp = DDR2_TRFC_512MBIT;
7028ec8d58eSZhihuan He else if (size <= 0x8000000)
7038ec8d58eSZhihuan He tmp = DDR2_TRFC_1GBIT;
7048ec8d58eSZhihuan He else if (size <= 0x10000000)
7058ec8d58eSZhihuan He tmp = DDR2_TRFC_2GBIT;
7068ec8d58eSZhihuan He else
7078ec8d58eSZhihuan He tmp = DDR2_TRFC_4GBIT;
7088ec8d58eSZhihuan He
7098ec8d58eSZhihuan He priv->pctl->trfc = (tmp * nMHz + 999) / 1000;
7108ec8d58eSZhihuan He tmp = (((tmp + 10) * nMHz + 999) / 1000);
7118ec8d58eSZhihuan He if (tmp < 200)
7128ec8d58eSZhihuan He tmp = 200;
7138ec8d58eSZhihuan He priv->pctl->texsr = tmp & 0x3FF;
7148ec8d58eSZhihuan He break;
7158ec8d58eSZhihuan He case DDR3:
7168ec8d58eSZhihuan He if (size <= 0x4000000)
7178ec8d58eSZhihuan He tmp = DDR3_TRFC_512MBIT;
7188ec8d58eSZhihuan He else if (size <= 0x8000000)
7198ec8d58eSZhihuan He tmp = DDR3_TRFC_1GBIT;
7208ec8d58eSZhihuan He else if (size <= 0x10000000)
7218ec8d58eSZhihuan He tmp = DDR3_TRFC_2GBIT;
7228ec8d58eSZhihuan He else if (size <= 0x20000000)
7238ec8d58eSZhihuan He tmp = DDR3_TRFC_4GBIT;
7248ec8d58eSZhihuan He else
7258ec8d58eSZhihuan He tmp = DDR3_TRFC_8GBIT;
7268ec8d58eSZhihuan He priv->pctl->trfc = (tmp * nMHz + 999) / 1000;
7278ec8d58eSZhihuan He break;
7288ec8d58eSZhihuan He case LPDDR2:
7298ec8d58eSZhihuan He if (size <= 0x4000000)
7308ec8d58eSZhihuan He tmp = LPDDR2_TREC_512MBIT;
7318ec8d58eSZhihuan He else if (size <= 0x20000000)
7328ec8d58eSZhihuan He tmp = LPDDR2_TRFC_4GBIT;
7338ec8d58eSZhihuan He else
7348ec8d58eSZhihuan He tmp = LPDDR2_TRFC_8GBIT;
7358ec8d58eSZhihuan He
7368ec8d58eSZhihuan He priv->pctl->trfc = (tmp * nMHz + 999) / 1000;
7378ec8d58eSZhihuan He tmp = (((tmp + 10) * nMHz + 999) / 1000);
7388ec8d58eSZhihuan He if (tmp < 2)
7398ec8d58eSZhihuan He tmp = 2;
7408ec8d58eSZhihuan He priv->pctl->texsr = tmp & 0x3FF;
7418ec8d58eSZhihuan He break;
7428ec8d58eSZhihuan He }
7438ec8d58eSZhihuan He move_to_access_state(priv);
7448ec8d58eSZhihuan He }
7458ec8d58eSZhihuan He
check_rd_gate(struct dram_info * priv)7468ec8d58eSZhihuan He int check_rd_gate(struct dram_info *priv)
7478ec8d58eSZhihuan He {
7488ec8d58eSZhihuan He u32 max_val = 0;
7498ec8d58eSZhihuan He u32 min_val = 0xff;
7508ec8d58eSZhihuan He u32 gate[2];
7518ec8d58eSZhihuan He
7528ec8d58eSZhihuan He gate[0] = readl(&priv->phy->phy_regfb);
7538ec8d58eSZhihuan He gate[1] = readl(&priv->phy->phy_regfc);
7548ec8d58eSZhihuan He max_val = max(gate[0], gate[1]);
7558ec8d58eSZhihuan He min_val = min(gate[0], gate[1]);
7568ec8d58eSZhihuan He
7578ec8d58eSZhihuan He if (max_val > 0x80 || min_val < 0x20)
7588ec8d58eSZhihuan He return -1;
7598ec8d58eSZhihuan He else
7608ec8d58eSZhihuan He return 0;
7618ec8d58eSZhihuan He }
7628ec8d58eSZhihuan He
dram_test(u32 i,u32 dqs)7638ec8d58eSZhihuan He static u32 dram_test(u32 i, u32 dqs)
7648ec8d58eSZhihuan He {
7658ec8d58eSZhihuan He for (phys_addr_t j = 4 * dqs; j < 0x2000; j += 8)
7668ec8d58eSZhihuan He writel(PATTERN + i, j);
7678ec8d58eSZhihuan He
7688ec8d58eSZhihuan He for (phys_addr_t j = 4 * dqs; j < 0x2000; j += 8)
7698ec8d58eSZhihuan He if ((PATTERN + i) != readl(j))
7708ec8d58eSZhihuan He return 1;
7718ec8d58eSZhihuan He
7728ec8d58eSZhihuan He return 0;
7738ec8d58eSZhihuan He }
7748ec8d58eSZhihuan He
7758ec8d58eSZhihuan He /**
7768ec8d58eSZhihuan He * modify_data_training() - Setting DQS gating calibration bypass,
7778ec8d58eSZhihuan He * scanning data training range and then select center one.
7788ec8d58eSZhihuan He */
7798ec8d58eSZhihuan He #define PHY_REG3C(n) (0x10 * (n))
7808ec8d58eSZhihuan He
modify_data_training(struct dram_info * priv,struct sdram_params * params_priv)7818ec8d58eSZhihuan He void modify_data_training(struct dram_info *priv,
7828ec8d58eSZhihuan He struct sdram_params *params_priv)
7838ec8d58eSZhihuan He {
7848ec8d58eSZhihuan He u32 value = 0;
7858ec8d58eSZhihuan He u32 i = 0, dqs = 0;
7868ec8d58eSZhihuan He u32 max_value = 0, min_value = 0;
7878ec8d58eSZhihuan He
7888ec8d58eSZhihuan He writel(readl(&priv->phy->phy_regfb), &priv->phy->phy_reg2c);
7898ec8d58eSZhihuan He writel(readl(&priv->phy->phy_regfc), &priv->phy->phy_reg3c);
7908ec8d58eSZhihuan He
7918ec8d58eSZhihuan He /* DQS gating calibration bypass */
7928ec8d58eSZhihuan He setbits_le32(&priv->phy->phy_reg2, BIT(1));
7938ec8d58eSZhihuan He
7948ec8d58eSZhihuan He /* rk3308 only support DQS0, DQS1 */
7958ec8d58eSZhihuan He for (dqs = 0; dqs < 2; dqs++) {
7968ec8d58eSZhihuan He value = readl(&priv->phy->phy_regfb + dqs);
7978ec8d58eSZhihuan He i = 0;
7988ec8d58eSZhihuan He while (dram_test(i, dqs) == 0) {
7998ec8d58eSZhihuan He i++;
8008ec8d58eSZhihuan He writel(value + i,
8018ec8d58eSZhihuan He &priv->phy->phy_reg2c + PHY_REG3C(dqs));
8028ec8d58eSZhihuan He }
8038ec8d58eSZhihuan He max_value = value + i - 1;
8048ec8d58eSZhihuan He
8058ec8d58eSZhihuan He i = 1;
8068ec8d58eSZhihuan He writel(value - i, &priv->phy->phy_reg2c + PHY_REG3C(dqs));
8078ec8d58eSZhihuan He while (dram_test(i, dqs) == 0) {
8088ec8d58eSZhihuan He i++;
8098ec8d58eSZhihuan He writel(value - i,
8108ec8d58eSZhihuan He &priv->phy->phy_reg2c + PHY_REG3C(dqs));
8118ec8d58eSZhihuan He }
8128ec8d58eSZhihuan He min_value = value - i + 1;
8138ec8d58eSZhihuan He
8148ec8d58eSZhihuan He /* select center one as gate training result */
8158ec8d58eSZhihuan He writel((max_value + min_value + 1) / 2,
8168ec8d58eSZhihuan He &priv->phy->phy_reg2c + PHY_REG3C(dqs));
8178ec8d58eSZhihuan He }
8188ec8d58eSZhihuan He printascii("REG2C: 0x");
8198ec8d58eSZhihuan He printhex8(readl(&priv->phy->phy_reg2c));
8208ec8d58eSZhihuan He printascii(", 0x");
8218ec8d58eSZhihuan He printhex8(readl(&priv->phy->phy_reg3c));
8228ec8d58eSZhihuan He printascii("\n");
8238ec8d58eSZhihuan He }
8248ec8d58eSZhihuan He
enable_low_power(struct dram_info * priv,struct sdram_params * params_priv)8258ec8d58eSZhihuan He void enable_low_power(struct dram_info *priv,
8268ec8d58eSZhihuan He struct sdram_params *params_priv)
8278ec8d58eSZhihuan He {
8288ec8d58eSZhihuan He move_to_config_state(priv);
8298ec8d58eSZhihuan He
8308ec8d58eSZhihuan He if (params_priv->idle_pd == 48 && params_priv->idle_sr == 10) {
8318ec8d58eSZhihuan He if (params_priv->ddr_timing_t.freq == 451) {
8328ec8d58eSZhihuan He params_priv->idle_sr = 28;
8338ec8d58eSZhihuan He params_priv->idle_pd = 7;
8348ec8d58eSZhihuan He } else if (params_priv->ddr_timing_t.freq == 393) {
8358ec8d58eSZhihuan He params_priv->idle_sr = 31;
8368ec8d58eSZhihuan He params_priv->idle_pd = 15;
8378ec8d58eSZhihuan He }
8388ec8d58eSZhihuan He }
8398ec8d58eSZhihuan He clrsetbits_le32(&priv->pctl->mcfg, PD_IDLE_MASK,
8408ec8d58eSZhihuan He params_priv->idle_pd << PD_IDLE_SHIFT);
8418ec8d58eSZhihuan He clrsetbits_le32(&priv->pctl->mcfg1,
8428ec8d58eSZhihuan He SR_IDLE_MASK | HW_EXIT_IDLE_EN_MASK,
8438ec8d58eSZhihuan He params_priv->idle_sr | HW_EXIT_IDLE_EN);
8448ec8d58eSZhihuan He
845*5d4a323cSTang Yun ping /* DDRCTL in low_power status because of auto self-refresh */
8468ec8d58eSZhihuan He writel(GO_STATE, &priv->pctl->sctl);
8478ec8d58eSZhihuan He }
8488ec8d58eSZhihuan He
get_uart_config(void)8498ec8d58eSZhihuan He int get_uart_config(void)
8508ec8d58eSZhihuan He {
8518ec8d58eSZhihuan He return ddr_gd.head_info.g_uart_info;
8528ec8d58eSZhihuan He }
8538ec8d58eSZhihuan He
sdram_init(void)8548ec8d58eSZhihuan He int sdram_init(void)
8558ec8d58eSZhihuan He {
8568ec8d58eSZhihuan He struct dram_info sdram_priv;
8578ec8d58eSZhihuan He struct sdram_params *params = sdram_configs;
8588ec8d58eSZhihuan He
8598ec8d58eSZhihuan He sdram_priv.cru = (void *)CRU_BASE;
8608ec8d58eSZhihuan He sdram_priv.grf = (void *)GRF_BASE;
8618ec8d58eSZhihuan He sdram_priv.sgrf = (void *)SGRF_BASE;
8628ec8d58eSZhihuan He sdram_priv.phy = (void *)DDR_PHY_BASE;
8638ec8d58eSZhihuan He sdram_priv.pctl = (void *)DDR_PCTL_BASE;
8648ec8d58eSZhihuan He sdram_priv.standby = (void *)DDR_STANDBY_BASE;
8658ec8d58eSZhihuan He sdram_priv.pmu = (void *)PMU_BASS_ADDR;
8668ec8d58eSZhihuan He sdram_priv.service_msch = (void *)SERVICE_MSCH_BASE;
8678ec8d58eSZhihuan He params->idle_pd = PD_INFO(ddr_gd.head_info.g_sr_pd_idle);
8688ec8d58eSZhihuan He params->idle_sr = SR_INFO(ddr_gd.head_info.g_sr_pd_idle);
8698ec8d58eSZhihuan He params->ddr_2t_en = DDR_2T_INFO(ddr_gd.head_info.g_2t_info);
8708ec8d58eSZhihuan He params->stdby_idle = STANDBY_IDLE(ddr_gd.head_info.g_ch_info);
8718ec8d58eSZhihuan He
8728ec8d58eSZhihuan He rv1108_sdram_init(&sdram_priv, params);
8738ec8d58eSZhihuan He
8748ec8d58eSZhihuan He modify_sdram_params(&sdram_priv, params);
8758ec8d58eSZhihuan He
8768ec8d58eSZhihuan He if (params->idle_pd != 0 && params->idle_sr != 0)
8778ec8d58eSZhihuan He enable_ddr_standby(&sdram_priv, params);
8788ec8d58eSZhihuan He ddr_set_atags();
8798ec8d58eSZhihuan He printascii("OUT\n");
8808ec8d58eSZhihuan He
8818ec8d58eSZhihuan He return 0;
8828ec8d58eSZhihuan He }
88319d63b30SZhihuan He
88419d63b30SZhihuan He #else
88519d63b30SZhihuan He
88619d63b30SZhihuan He /* return: 0 = success, other = fail */
sdram_init(void)88719d63b30SZhihuan He int sdram_init(void)
88819d63b30SZhihuan He {
88919d63b30SZhihuan He return (-1);
89019d63b30SZhihuan He }
89119d63b30SZhihuan He
89219d63b30SZhihuan He #endif /* CONFIG_TPL_BUILD */
893