|
@@ -6,6 +6,9 @@
|
|
|
* Licensed under the GPL-2 or later.
|
|
|
*/
|
|
|
|
|
|
+#ifndef __MEM_INIT_H__
|
|
|
+#define __MEM_INIT_H__
|
|
|
+
|
|
|
#if defined(EBIU_SDGCTL)
|
|
|
#if defined(CONFIG_MEM_MT48LC16M16A2TG_75) || \
|
|
|
defined(CONFIG_MEM_MT48LC64M4A2FB_7E) || \
|
|
@@ -277,3 +280,212 @@
|
|
|
#else
|
|
|
#define PLL_BYPASS 0
|
|
|
#endif
|
|
|
+
|
|
|
+#ifdef CONFIG_BF60x
|
|
|
+
|
|
|
+/* DMC status bits */
|
|
|
+#define IDLE 0x1
|
|
|
+#define MEMINITDONE 0x4
|
|
|
+#define SRACK 0x8
|
|
|
+#define PDACK 0x10
|
|
|
+#define DPDACK 0x20
|
|
|
+#define DLLCALDONE 0x2000
|
|
|
+#define PENDREF 0xF0000
|
|
|
+#define PHYRDPHASE 0xF00000
|
|
|
+#define PHYRDPHASE_OFFSET 20
|
|
|
+
|
|
|
+/* DMC control bits */
|
|
|
+#define LPDDR 0x2
|
|
|
+#define INIT 0x4
|
|
|
+#define SRREQ 0x8
|
|
|
+#define PDREQ 0x10
|
|
|
+#define DPDREQ 0x20
|
|
|
+#define PREC 0x40
|
|
|
+#define ADDRMODE 0x100
|
|
|
+#define RDTOWR 0xE00
|
|
|
+#define PPREF 0x1000
|
|
|
+#define DLLCAL 0x2000
|
|
|
+
|
|
|
+/* DMC DLL control bits */
|
|
|
+#define DLLCALRDCNT 0xFF
|
|
|
+#define DATACYC 0xF00
|
|
|
+#define DATACYC_OFFSET 8
|
|
|
+
|
|
|
+/* CGU Divisor bits */
|
|
|
+#define CSEL_OFFSET 0
|
|
|
+#define S0SEL_OFFSET 5
|
|
|
+#define SYSSEL_OFFSET 8
|
|
|
+#define S1SEL_OFFSET 13
|
|
|
+#define DSEL_OFFSET 16
|
|
|
+#define OSEL_OFFSET 22
|
|
|
+#define ALGN 0x20000000
|
|
|
+#define UPDT 0x40000000
|
|
|
+#define LOCK 0x80000000
|
|
|
+
|
|
|
+/* CGU Status bits */
|
|
|
+#define PLLEN 0x1
|
|
|
+#define PLLBP 0x2
|
|
|
+#define PLOCK 0x4
|
|
|
+#define CLKSALGN 0x8
|
|
|
+
|
|
|
+/* CGU Control bits */
|
|
|
+#define MSEL_MASK 0x7F00
|
|
|
+#define DF_MASK 0x1
|
|
|
+
|
|
|
+struct ddr_config {
|
|
|
+ u32 ddr_clk;
|
|
|
+ u32 dmc_ddrctl;
|
|
|
+ u32 dmc_ddrcfg;
|
|
|
+ u32 dmc_ddrtr0;
|
|
|
+ u32 dmc_ddrtr1;
|
|
|
+ u32 dmc_ddrtr2;
|
|
|
+ u32 dmc_ddrmr;
|
|
|
+ u32 dmc_ddrmr1;
|
|
|
+};
|
|
|
+
|
|
|
+#if defined(CONFIG_MEM_MT47H64M16)
|
|
|
+static struct ddr_config ddr_config_table[] __attribute__((section(".data_l1"))) = {
|
|
|
+ [0] = {
|
|
|
+ .ddr_clk = 125,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20705212,
|
|
|
+ .dmc_ddrtr1 = 0x201003CF,
|
|
|
+ .dmc_ddrtr2 = 0x00320107,
|
|
|
+ .dmc_ddrmr = 0x00000422,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [1] = {
|
|
|
+ .ddr_clk = 133,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20806313,
|
|
|
+ .dmc_ddrtr1 = 0x2013040D,
|
|
|
+ .dmc_ddrtr2 = 0x00320108,
|
|
|
+ .dmc_ddrmr = 0x00000632,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [2] = {
|
|
|
+ .ddr_clk = 150,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20A07323,
|
|
|
+ .dmc_ddrtr1 = 0x20160492,
|
|
|
+ .dmc_ddrtr2 = 0x00320209,
|
|
|
+ .dmc_ddrmr = 0x00000632,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [3] = {
|
|
|
+ .ddr_clk = 166,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20A07323,
|
|
|
+ .dmc_ddrtr1 = 0x2016050E,
|
|
|
+ .dmc_ddrtr2 = 0x00320209,
|
|
|
+ .dmc_ddrmr = 0x00000632,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [4] = {
|
|
|
+ .ddr_clk = 200,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20a07323,
|
|
|
+ .dmc_ddrtr1 = 0x2016050f,
|
|
|
+ .dmc_ddrtr2 = 0x00320509,
|
|
|
+ .dmc_ddrmr = 0x00000632,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [5] = {
|
|
|
+ .ddr_clk = 225,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20E0A424,
|
|
|
+ .dmc_ddrtr1 = 0x302006DB,
|
|
|
+ .dmc_ddrtr2 = 0x0032020D,
|
|
|
+ .dmc_ddrmr = 0x00000842,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+ [6] = {
|
|
|
+ .ddr_clk = 250,
|
|
|
+ .dmc_ddrctl = 0x00000904,
|
|
|
+ .dmc_ddrcfg = 0x00000422,
|
|
|
+ .dmc_ddrtr0 = 0x20E0A424,
|
|
|
+ .dmc_ddrtr1 = 0x3020079E,
|
|
|
+ .dmc_ddrtr2 = 0x0032020D,
|
|
|
+ .dmc_ddrmr = 0x00000842,
|
|
|
+ .dmc_ddrmr1 = 0x4,
|
|
|
+ },
|
|
|
+};
|
|
|
+#endif
|
|
|
+
|
|
|
+static inline void dmc_enter_self_refresh(void)
|
|
|
+{
|
|
|
+ if (bfin_read_DMC0_STAT() & MEMINITDONE) {
|
|
|
+ bfin_write_DMC0_CTL(bfin_read_DMC0_CTL() | SRREQ);
|
|
|
+ while (!(bfin_read_DMC0_STAT() & SRACK))
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+static inline void dmc_exit_self_refresh(void)
|
|
|
+{
|
|
|
+ if (bfin_read_DMC0_STAT() & MEMINITDONE) {
|
|
|
+ bfin_write_DMC0_CTL(bfin_read_DMC0_CTL() & ~SRREQ);
|
|
|
+ while (bfin_read_DMC0_STAT() & SRACK)
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+static inline void init_cgu(u32 cgu_div, u32 cgu_ctl)
|
|
|
+{
|
|
|
+ dmc_enter_self_refresh();
|
|
|
+
|
|
|
+ /* Don't set the same value of MSEL and DF to CGU_CTL */
|
|
|
+ if ((bfin_read32(CGU0_CTL) & (MSEL_MASK | DF_MASK))
|
|
|
+ != cgu_ctl) {
|
|
|
+ bfin_write32(CGU0_DIV, cgu_div);
|
|
|
+ bfin_write32(CGU0_CTL, cgu_ctl);
|
|
|
+ while ((bfin_read32(CGU0_STAT) & (CLKSALGN | PLLBP)) ||
|
|
|
+ !(bfin_read32(CGU0_STAT) & PLOCK))
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+
|
|
|
+ bfin_write32(CGU0_DIV, cgu_div | UPDT);
|
|
|
+ while (bfin_read32(CGU0_STAT) & CLKSALGN)
|
|
|
+ continue;
|
|
|
+
|
|
|
+ dmc_exit_self_refresh();
|
|
|
+}
|
|
|
+
|
|
|
+static inline void init_dmc(u32 dmc_clk)
|
|
|
+{
|
|
|
+ int i, dlldatacycle, dll_ctl;
|
|
|
+
|
|
|
+ for (i = 0; i < 7; i++) {
|
|
|
+ if (ddr_config_table[i].ddr_clk == dmc_clk) {
|
|
|
+ bfin_write_DMC0_CFG(ddr_config_table[i].dmc_ddrcfg);
|
|
|
+ bfin_write_DMC0_TR0(ddr_config_table[i].dmc_ddrtr0);
|
|
|
+ bfin_write_DMC0_TR1(ddr_config_table[i].dmc_ddrtr1);
|
|
|
+ bfin_write_DMC0_TR2(ddr_config_table[i].dmc_ddrtr2);
|
|
|
+ bfin_write_DMC0_MR(ddr_config_table[i].dmc_ddrmr);
|
|
|
+ bfin_write_DMC0_EMR1(ddr_config_table[i].dmc_ddrmr1);
|
|
|
+ bfin_write_DMC0_CTL(ddr_config_table[i].dmc_ddrctl);
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ while (!(bfin_read_DMC0_STAT() & MEMINITDONE))
|
|
|
+ continue;
|
|
|
+
|
|
|
+ dlldatacycle = (bfin_read_DMC0_STAT() & PHYRDPHASE) >> PHYRDPHASE_OFFSET;
|
|
|
+ dll_ctl = bfin_read_DMC0_DLLCTL();
|
|
|
+ dll_ctl &= ~DATACYC;
|
|
|
+ bfin_write_DMC0_DLLCTL(dll_ctl | (dlldatacycle << DATACYC_OFFSET));
|
|
|
+
|
|
|
+ while (!(bfin_read_DMC0_STAT() & DLLCALDONE))
|
|
|
+ continue;
|
|
|
+}
|
|
|
+#endif
|
|
|
+
|
|
|
+#endif /*__MEM_INIT_H__*/
|
|
|
+
|