1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (C) 2012-2020  ASPEED Technology Inc.
4  *
5  * Copyright 2016 Google, Inc
6  */
7 
8 #include <common.h>
9 #include <clk.h>
10 #include <dm.h>
11 #include <errno.h>
12 #include <ram.h>
13 #include <regmap.h>
14 #include <reset.h>
15 #include <asm/io.h>
16 #include <asm/arch/scu_ast2600.h>
17 #include <asm/arch/sdram_ast2600.h>
18 #include <asm/arch/wdt.h>
19 #include <linux/err.h>
20 #include <linux/kernel.h>
21 #include <dt-bindings/clock/ast2600-clock.h>
22 #include "sdram_phy_ast2600.h"
23 
24 #define AST2600_SDRAMMC_FPGA
25 
26 /* in order to speed up DRAM init time, write pre-defined values to registers
27  * directly */
28 #define AST2600_SDRAMMC_MANUAL_CLK
29 
30 #ifdef AST2600_SDRAMMC_FPGA
31 /* mode register settings for FPGA are fixed */
32 #define DDR4_MR01_MODE		0x03010100
33 #define DDR4_MR23_MODE		0x00000000
34 #define DDR4_MR45_MODE		0x04C00000
35 #define DDR4_MR6_MODE		0x00000050
36 #define DDR4_TRFC		0x17263434
37 
38 /* FPGA need for an additional initialization procedure: search read window */
39 #define SEARCH_RDWIN_ANCHOR_0   (CONFIG_SYS_SDRAM_BASE + 0x0000)
40 #define SEARCH_RDWIN_ANCHOR_1   (CONFIG_SYS_SDRAM_BASE + 0x0004)
41 #define SEARCH_RDWIN_PTRN_0     0x12345678
42 #define SEARCH_RDWIN_PTRN_1     0xaabbccdd
43 #define SEARCH_RDWIN_PTRN_SUM   0xbcf02355
44 #else
45 /* mode register setting for real chip are derived from the model GDDR4-1600 */
46 #define DDR4_MR01_MODE		0x03010510
47 #define DDR4_MR23_MODE		0x00000000
48 #define DDR4_MR45_MODE		0x04000000
49 #define DDR4_MR6_MODE           0x00000400
50 #define DDR4_TRFC               0x467299f1
51 #endif  /* end of "#ifdef AST2600_SDRAMMC_FPGA" */
52 
53 #define SDRAM_SIZE_1KB		(1024U)
54 #define SDRAM_SIZE_1MB		(SDRAM_SIZE_1KB * SDRAM_SIZE_1KB)
55 #define SDRAM_MIN_SIZE		(256 * SDRAM_SIZE_1MB)
56 #define SDRAM_MAX_SIZE		(2048 * SDRAM_SIZE_1MB)
57 
58 /* register offset */
59 #define AST_SCU_CONFIG		0x004
60 #define AST_SCU_HANDSHAKE	0x100
61 #define AST_SCU_MPLL		0x220
62 #define AST_SCU_FPGA_PLL	0x400
63 #define AST_SCU_HW_STRAP	0x500
64 
65 /* bit-field of AST_SCU_HW_STRAP */
66 #define SCU_HWSTRAP_VGAMEM_SHIFT	2
67 #define SCU_HWSTRAP_VGAMEM_MASK		(3 << SCU_HWSTRAP_VGAMEM_SHIFT)
68 #define SCU_HWSTRAP_DDR3		(1 << 25)
69 
70 
71 /* bit-field of AST_SCU_HANDSHAKE */
72 #define SCU_SDRAM_INIT_READY_SHIFT	6
73 #define SCU_SDRAM_INIT_READY_MASK	(0x1 << SCU_SDRAM_INIT_READY_SHIFT)
74 #define SCU_SDRAM_INIT_BY_SOC_SHIFT	7
75 #define SCU_SDRAM_INIT_BY_SOC_MASK	(0x1 << SCU_SDRAM_INIT_BY_SOC_SHIFT)
76 
77 
78 /* bit-field of AST_SCU_MPLL */
79 #define SCU_MPLL_FREQ_MASK		0x007FFFFF	/* bit[22:0] */
80 #define SCU_MPLL_FREQ_400M		0x0008405F	/* 0x0038007F */
81 #define SCU_MPLL_FREQ_200M		0x0078007F
82 #define SCU_MPLL_FREQ_CFG		SCU_MPLL_FREQ_400M
83 
84 #define SCU_MPLL_TURN_OFF		BIT(23)
85 #define SCU_MPLL_BYPASS			BIT(24)
86 #define SCU_MPLL_RESET			BIT(25)
87 
88 DECLARE_GLOBAL_DATA_PTR;
89 
90 /*
91  * Bandwidth configuration parameters for different SDRAM requests.
92  * These are hardcoded settings taken from Aspeed SDK.
93  */
94 #ifdef AST2600_SDRAMMC_FPGA
95 static const u32 ddr4_ac_timing[4] = {0x030C0207, 0x04451133, 0x0E010200,
96                                       0x00000140};
97 
98 static const u32 ddr_max_grant_params[4] = {0x88888888, 0x88888888, 0x88888888,
99                                             0x88888888};
100 #else
101 static const u32 ddr4_ac_timing[4] = {0x040e0307, 0x0f4711f1, 0x0e060304,
102                                       0x00001240};
103 
104 static const u32 ddr_max_grant_params[4] = {0x44444444, 0x44444444, 0x44444444,
105                                             0x44444444};
106 #endif
107 
108 struct dram_info {
109 	struct ram_info info;
110 	struct clk ddr_clk;
111 	struct ast2600_sdrammc_regs *regs;
112 	void __iomem *scu;
113 	struct ast2600_ddr_phy *phy;
114 	void __iomem *phy_setting;
115 	void __iomem *phy_status;
116 	ulong clock_rate;
117 };
118 
119 static void ast2600_sdramphy_kick_training(struct dram_info *info)
120 {
121 #ifndef AST2600_SDRAMMC_FPGA
122         struct ast2600_sdrammc_regs *regs = info->regs;
123         u32 mask = SDRAM_PHYCTRL0_INIT | SDRAM_PHYCTRL0_PLL_LOCKED;
124         u32 data;
125 
126         writel(0, &regs->phy_ctrl[0]);
127         udelay(2);
128         writel(SDRAM_PHYCTRL0_NRST | SDRAM_PHYCTRL0_INIT, &regs->phy_ctrl[0]);
129 
130         /* wait for (PLL_LOCKED == 1) and (INIT == 0) */
131         do {
132                 data = readl(&regs->phy_ctrl[0]) & mask;
133         } while (SDRAM_PHYCTRL0_PLL_LOCKED != data);
134 #endif
135 }
136 
137 /**
138  * @brief	load DDR-PHY configurations table to the PHY registers
139  * @param[in]	p_tbl - pointer to the configuration table
140  * @param[in]	info - pointer to the DRAM info struct
141 */
142 static void ast2600_sdramphy_init(u32 *p_tbl, struct dram_info *info)
143 {
144 #ifndef AST2600_SDRAMMC_FPGA
145 	u32 reg_base = (u32)info->phy_setting;
146 	u32 addr = p_tbl[0];
147         u32 data;
148         int i = 1;
149 
150         debug("%s:reg base = 0x%08x, 1st addr = 0x%08x\n", __func__, reg_base,
151                addr);
152 
153         /* load PHY configuration table into PHY-setting registers */
154         while (1) {
155                 if (addr < reg_base) {
156                         debug("invalid DDR-PHY addr: 0x%08x\n", addr);
157                         break;
158                 }
159                 data = p_tbl[i++];
160 
161                 if (DDR_PHY_TBL_END == data) {
162                         break;
163                 } else if (DDR_PHY_TBL_CHG_ADDR == data) {
164                         addr = p_tbl[i++];
165                 } else {
166                         writel(data, addr);
167                         addr += 4;
168                 }
169         }
170 #endif
171 }
172 
173 static void ast2600_sdramphy_show_status(struct dram_info *info)
174 {
175 #ifndef AST2600_SDRAMMC_FPGA
176         u32 value;
177         u32 reg_base = (u32)info->phy_status;
178 
179         debug("%s:reg base = 0x%08x\n", __func__, reg_base);
180 
181         value = readl(reg_base + 0x00);
182         if (value & BIT(3)) {
183                 debug("initial PVT calibration fail\n");
184         }
185         if (value & BIT(5)) {
186                 debug("runtime calibration fail\n");
187         }
188 
189         value = readl(reg_base + 0x30);
190         debug("IO PU = 0x%02x\n", value & 0xff);
191         debug("IO PD = 0x%02x\n", (value >> 16) & 0xff);
192 
193         value = readl(reg_base + 0x88);
194         debug("PHY vref: 0x%02x_%02x\n", value & 0xff, (value >> 8) & 0xff);
195         value = readl(reg_base + 0x90);
196         debug("DDR vref: 0x%02x\n", value & 0x3f);
197 
198         value = readl(reg_base + 0x40);
199         debug("MLB Gate training result: 0x%04x_%04x\n", value & 0xffff,
200               (value >> 16) & 0xffff);
201         value = readl(reg_base + 0x50);
202         debug("MLB Gate pass window: 0x%04x_%04x\n", value & 0xffff,
203               (value >> 16) & 0xffff);
204         value = readl(reg_base + 0x60);
205         debug("Rising  edge Read Data Eye Training Result      = 0x%x_%x\n",
206               value & 0xff, (value >> 8) & 0xff);
207 
208         value = readl(reg_base + 0x68);
209         debug("Rising  edge Read Data Eye Training Pass Window = 0x%x_%x\n",
210               value & 0xff, (value >> 8) & 0xff);
211 
212         value = readl(reg_base + 0xC0);
213         debug("Falling edge Read Data Eye Training Result      = 0x%x_%x\n",
214               value & 0xff, (value >> 8) & 0xff);
215 
216         value = readl(reg_base + 0xC8);
217         debug("Falling edge Read Data Eye Training Pass Window = 0x%x_%x\n",
218               value & 0xff, (value >> 8) & 0xff);
219 
220         value = readl(reg_base + 0x74);
221         debug("Write Data Eye fine Training Result             = %X_%X\n",
222               value & 0xff, (value >> 8) & 0xff);
223 
224         value = readl(reg_base + 0x7C);
225         debug("Write Data Eye Training Pass Window             = 0x%x_%x\n",
226               value & 0xff, (value >> 8) & 0xff);
227 #endif
228 }
229 
230 /**
231  * @brief       SDRAM memory controller test mode with data-generation
232  * @param[in]   - info - pointer to the current dram_info
233  * @param[in]   - data_gen - data_gen index
234  * @param[in]	- mode - 0:single, 1:burst
235  * @return      - 0:success, others:fail
236 */
237 static int ast2600_sdrammc_dg_test(struct dram_info *info, u32 data_gen,
238                                    u32 mode)
239 {
240         u32 data;
241 	u32 mask;
242 	struct ast2600_sdrammc_regs *regs = info->regs;
243 
244         writel(0, &regs->ecc_test_ctrl);
245         data = (data_gen << SDRAM_TEST_GEN_MODE_SHIFT) | SDRAM_TEST_ERRSTOP |
246                SDRAM_TEST_EN;
247         if (mode) {
248                 data |=
249                     (SDRAM_TEST_ERRSTOP | SDRAM_TEST_EN | SDRAM_TEST_MODE_RW);
250         } else {
251                 data |= (SDRAM_TEST_ERRSTOP | SDRAM_TEST_EN |
252                          SDRAM_TEST_MODE_WO | SDRAM_TEST_TWO_MODES);
253         }
254         writel(data, &regs->ecc_test_ctrl);
255 
256 	mask = SDRAM_TEST_DONE | SDRAM_TEST_FAIL;
257         do {
258                 data = readl(&regs->ecc_test_ctrl) & mask;
259                 if (data & SDRAM_TEST_FAIL) {
260                         debug("%s %d fail\n", __func__, data_gen);
261                         return 1;
262                 }
263         } while (!data);
264 
265         writel(0x00000000, &regs->ecc_test_ctrl);
266         return 0;
267 }
268 
269 static int ast2600_sdrammc_cbr_test(struct dram_info *info, u32 pattern)
270 {
271         struct ast2600_sdrammc_regs *regs = info->regs;
272         int i;
273         int ret = 0;
274 
275         writel((0xff << SDRAM_TEST_LEN_SHIFT), &regs->test_addr);
276         writel(pattern, &regs->test_init_val);
277 
278         /* scan all data-generation mode */
279         for (i = 0; i < 8; i++) {
280                 if (0 == ast2600_sdrammc_dg_test(info, i, 0)) {
281                         debug("sdrammc calibration test fail: single data "
282                               "mode\n");
283                         ret = 1;
284                         break;
285                 }
286         }
287 
288         for (i = 0; i < 8; i++) {
289                 if (0 == ast2600_sdrammc_dg_test(info, i, 1)) {
290                         debug(
291                             "sdrammc calibration test fail: burst data mode\n");
292                         ret = 1;
293                         break;
294                 }
295         }
296 
297         writel(0, &regs->ecc_test_ctrl);
298         return ret;
299 }
300 
301 #define MC_TEST_PATTERN_N 8
302 static u32 as2600_sdrammc_test_pattern[MC_TEST_PATTERN_N] = {
303     0xcc33cc33, 0xff00ff00, 0xaa55aa55, 0x88778877,
304     0x92cc4d6e, 0x543d3cde, 0xf1e843c7, 0x7c61d253};
305 
306 static int ast2600_sdrammc_test(struct dram_info *info)
307 {
308         int i;
309         int ret;
310 
311         for (i = 0; i < MC_TEST_PATTERN_N; i++) {
312                 ret = ast2600_sdrammc_cbr_test(info,
313                                                as2600_sdrammc_test_pattern[i]);
314                 if (ret) {
315                         return ret;
316                 }
317                 debug("%s: pass %d\n", __func__, i);
318         }
319 
320         return ret;
321 }
322 
323 static size_t ast2600_sdrammc_get_vga_mem_size(struct dram_info *info)
324 {
325         u32 vga_hwconf;
326         size_t vga_mem_size_base = 8 * 1024 * 1024;
327 
328         vga_hwconf = readl(info->scu + AST_SCU_HW_STRAP) &
329                      SCU_HWSTRAP_VGAMEM_MASK >> SCU_HWSTRAP_VGAMEM_SHIFT;
330 
331         return vga_mem_size_base << vga_hwconf;
332 }
333 #ifdef AST2600_SDRAMMC_FPGA
334 static void ast2600_sdrammc_fpga_set_pll(struct dram_info *info)
335 {
336         u32 data;
337         u32 scu_base = (u32)info->scu;
338 
339         writel(0x00000303, scu_base + AST_SCU_FPGA_PLL);
340 
341         do {
342                 data = readl(scu_base + AST_SCU_CONFIG);
343         } while (!(data & 0x100));
344 
345         writel(0x00000103, scu_base + AST_SCU_FPGA_PLL);
346 }
347 
348 static int ast2600_sdrammc_search_read_window(struct dram_info *info)
349 {
350         u32 pll, pll_min, pll_max, dat1, offset;
351         u32 win = 0x03, gwin = 0, gwinsize = 0;
352         u32 phy_setting = (u32)info->phy_setting;
353 
354         writel(SEARCH_RDWIN_PTRN_0, SEARCH_RDWIN_ANCHOR_0);
355         writel(SEARCH_RDWIN_PTRN_1, SEARCH_RDWIN_ANCHOR_1);
356 
357         while (gwin == 0) {
358                 while (!(win & 0x80)) {
359                         debug("Window = 0x%X\n", win);
360                         writel(win, phy_setting + 0x0000);
361 
362                         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
363                         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
364                         while (dat1 == SEARCH_RDWIN_PTRN_SUM) {
365                                 ast2600_sdrammc_fpga_set_pll(info);
366                                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
367                                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
368                         }
369 
370                         pll_min = 0xfff;
371                         pll_max = 0x0;
372                         pll = 0;
373                         while (pll_max > 0 || pll < 256) {
374                                 ast2600_sdrammc_fpga_set_pll(info);
375                                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
376                                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
377                                 if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
378                                         if (pll_min > pll) {
379                                                 pll_min = pll;
380                                         }
381                                         if (pll_max < pll) {
382                                                 pll_max = pll;
383                                         }
384                                         debug("%3d_(%3d:%3d)\n", pll, pll_min,
385                                                pll_max);
386                                 } else if (pll_max > 0) {
387                                         pll_min = pll_max - pll_min;
388                                         if (gwinsize < pll_min) {
389                                                 gwin = win;
390                                                 gwinsize = pll_min;
391                                         }
392                                         break;
393                                 }
394                                 pll += 1;
395                         }
396 
397                         if (gwin != 0 && pll_max == 0) {
398                                 break;
399                         }
400                         win = win << 1;
401                 }
402                 if (gwin == 0) {
403                         win = 0x7;
404                 }
405         }
406         debug("Set PLL Read Gating Window = %x\n", gwin);
407         writel(gwin, phy_setting + 0x0000);
408 
409         debug("PLL Read Window training\n");
410         pll_min = 0xfff;
411         pll_max = 0x0;
412 
413         debug("Search Window Start\n");
414         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
415         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
416         while (dat1 == SEARCH_RDWIN_PTRN_SUM) {
417                 ast2600_sdrammc_fpga_set_pll(info);
418                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
419                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
420         }
421 
422         debug("Search Window Margin\n");
423         pll = 0;
424         while (pll_max > 0 || pll < 256) {
425                 ast2600_sdrammc_fpga_set_pll(info);
426                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
427                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
428                 if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
429                         if (pll_min > pll) {
430                                 pll_min = pll;
431                         }
432                         if (pll_max < pll) {
433                                 pll_max = pll;
434                         }
435                         debug("%3d_(%3d:%3d)\n", pll, pll_min, pll_max);
436                 } else if (pll_max > 0 && (pll_max - pll_min) > 20) {
437                         break;
438                 } else if (pll_max > 0) {
439                         pll_min = 0xfff;
440                         pll_max = 0x0;
441                 }
442                 pll += 1;
443         }
444         if (pll_min < pll_max) {
445                 debug("PLL Read window = %d\n", (pll_max - pll_min));
446                 offset = (pll_max - pll_min) >> 1;
447                 pll_min = 0xfff;
448                 pll = 0;
449                 while (pll < (pll_min + offset)) {
450                         ast2600_sdrammc_fpga_set_pll(info);
451                         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
452                         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
453                         if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
454                                 if (pll_min > pll) {
455                                         pll_min = pll;
456                                 }
457                                 debug("%d\n", pll);
458                         } else {
459                                 pll_min = 0xfff;
460                                 pll_max = 0x0;
461                         }
462                         pll += 1;
463                 }
464                 return (1);
465         } else {
466                 debug("PLL Read window training fail\n");
467                 return (0);
468         }
469 }
470 #endif  /* end of "#ifdef AST2600_SDRAMMC_FPGA" */
471 
472 /*
473  * Find out RAM size and save it in dram_info
474  *
475  * The procedure is taken from Aspeed SDK
476  */
477 static void ast2600_sdrammc_calc_size(struct dram_info *info)
478 {
479 	/* The controller supports 256/512/1024/2048 MB ram */
480 	size_t ram_size = SDRAM_MIN_SIZE;
481 	const int write_test_offset = 0x100000;
482 	u32 test_pattern = 0xdeadbeef;
483 	u32 cap_param = SDRAM_CONF_CAP_2048M;
484 	u32 refresh_timing_param = DDR4_TRFC;
485 	const u32 write_addr_base = CONFIG_SYS_SDRAM_BASE + write_test_offset;
486 
487 	for (ram_size = SDRAM_MAX_SIZE; ram_size > SDRAM_MIN_SIZE;
488 	     ram_size >>= 1) {
489 		writel(test_pattern, write_addr_base + (ram_size >> 1));
490 		test_pattern = (test_pattern >> 4) | (test_pattern << 28);
491 	}
492 
493 	/* One last write to overwrite all wrapped values */
494 	writel(test_pattern, write_addr_base);
495 
496 	/* Reset the pattern and see which value was really written */
497 	test_pattern = 0xdeadbeef;
498 	for (ram_size = SDRAM_MAX_SIZE; ram_size > SDRAM_MIN_SIZE;
499 	     ram_size >>= 1) {
500 		if (readl(write_addr_base + (ram_size >> 1)) == test_pattern)
501 			break;
502 
503 		--cap_param;
504 		refresh_timing_param >>= 8;
505 		test_pattern = (test_pattern >> 4) | (test_pattern << 28);
506 	}
507 
508 	clrsetbits_le32(&info->regs->ac_timing[1],
509 			(SDRAM_AC_TRFC_MASK << SDRAM_AC_TRFC_SHIFT),
510 			((refresh_timing_param & SDRAM_AC_TRFC_MASK)
511 			 << SDRAM_AC_TRFC_SHIFT));
512 
513 	info->info.base = CONFIG_SYS_SDRAM_BASE;
514 	info->info.size = ram_size - ast2600_sdrammc_get_vga_mem_size(info);
515 	clrsetbits_le32(&info->regs->config,
516 			(SDRAM_CONF_CAP_MASK << SDRAM_CONF_CAP_SHIFT),
517 			((cap_param & SDRAM_CONF_CAP_MASK)
518 			 << SDRAM_CONF_CAP_SHIFT));
519 }
520 
521 static int ast2600_sdrammc_init_ddr4(struct dram_info *info)
522 {
523         const u32 power_ctrl = MCR34_CKE_EN | MCR34_AUTOPWRDN_EN |
524                                MCR34_MREQ_BYPASS_DIS | MCR34_RESETN_DIS |
525                                MCR34_ODT_EN | MCR34_ODT_AUTO_ON |
526                                (0x1 << MCR34_ODT_EXT_SHIFT);
527 
528 #ifdef CONFIG_DUALX8_RAM
529 	setbits_le32(&info->regs->config, SDRAM_CONF_DDR4 | SDRAM_CONF_DUALX8);
530 #else
531 	setbits_le32(&info->regs->config, SDRAM_CONF_DDR4);
532 #endif
533 
534         /* init SDRAM-PHY only on real chip */
535 	ast2600_sdramphy_init(ast2600_sdramphy_config, info);
536 	ast2600_sdramphy_kick_training(info);
537 
538         writel((MCR34_CKE_EN | MCR34_MREQI_DIS | MCR34_RESETN_DIS),
539                &info->regs->power_ctrl);
540         writel(SDRAM_RESET_DLL_ZQCL_EN, &info->regs->refresh_timing);
541 
542         writel(MCR30_SET_MR(3), &info->regs->mode_setting_control);
543         writel(MCR30_SET_MR(6), &info->regs->mode_setting_control);
544         writel(MCR30_SET_MR(5), &info->regs->mode_setting_control);
545         writel(MCR30_SET_MR(4), &info->regs->mode_setting_control);
546         writel(MCR30_SET_MR(2), &info->regs->mode_setting_control);
547         writel(MCR30_SET_MR(1), &info->regs->mode_setting_control);
548         writel(MCR30_SET_MR(0) | MCR30_RESET_DLL_DELAY_EN,
549                &info->regs->mode_setting_control);
550 
551 #ifdef AST2600_SDRAMMC_FPGA
552         writel(SDRAM_REFRESH_EN | SDRAM_RESET_DLL_ZQCL_EN |
553                    (0x5d << SDRAM_REFRESH_PERIOD_SHIFT),
554                &info->regs->refresh_timing);
555 #else
556         writel(SDRAM_REFRESH_EN | SDRAM_RESET_DLL_ZQCL_EN |
557                    (0x5f << SDRAM_REFRESH_PERIOD_SHIFT),
558                &info->regs->refresh_timing);
559 #endif
560 
561         /* wait self-refresh idle */
562         while (readl(&info->regs->power_ctrl) & MCR34_SELF_REFRESH_STATUS_MASK)
563                 ;
564 
565 #ifdef AST2600_SDRAMMC_FPGA
566         writel(SDRAM_REFRESH_EN | SDRAM_LOW_PRI_REFRESH_EN |
567                    SDRAM_REFRESH_ZQCS_EN |
568                    (0x5d << SDRAM_REFRESH_PERIOD_SHIFT) |
569                    (0x4000 << SDRAM_REFRESH_PERIOD_ZQCS_SHIFT),
570                &info->regs->refresh_timing);
571 #else
572         writel(SDRAM_REFRESH_EN | SDRAM_LOW_PRI_REFRESH_EN |
573                    SDRAM_REFRESH_ZQCS_EN |
574                    (0x5f << SDRAM_REFRESH_PERIOD_SHIFT) |
575                    (0x42aa << SDRAM_REFRESH_PERIOD_ZQCS_SHIFT),
576                &info->regs->refresh_timing);
577 #endif
578 
579         writel(power_ctrl, &info->regs->power_ctrl);
580 
581 #ifdef AST2600_SDRAMMC_FPGA
582         /* toggle Vref training */
583         setbits_le32(&info->regs->mr6_mode_setting, 0x80);
584         writel(MCR30_RESET_DLL_DELAY_EN | MCR30_SET_MR(6),
585                &info->regs->mode_setting_control);
586         clrbits_le32(&info->regs->mr6_mode_setting, 0x80);
587         writel(MCR30_RESET_DLL_DELAY_EN | MCR30_SET_MR(6),
588                &info->regs->mode_setting_control);
589 #endif
590 	return 0;
591 }
592 
593 static void ast2600_sdrammc_unlock(struct dram_info *info)
594 {
595 	writel(SDRAM_UNLOCK_KEY, &info->regs->protection_key);
596 	while (!readl(&info->regs->protection_key))
597 		;
598 }
599 
600 static void ast2600_sdrammc_lock(struct dram_info *info)
601 {
602 	writel(~SDRAM_UNLOCK_KEY, &info->regs->protection_key);
603 	while (readl(&info->regs->protection_key))
604 		;
605 }
606 
607 static void ast2600_sdrammc_common_init(struct ast2600_sdrammc_regs *regs)
608 {
609 	int i;
610 
611         writel(SDRAM_VIDEO_UNLOCK_KEY, &regs->gm_protection_key);
612         writel(MCR34_MREQI_DIS | MCR34_RESETN_DIS, &regs->power_ctrl);
613         writel(0x10 << MCR38_RW_MAX_GRANT_CNT_RQ_SHIFT,
614                &regs->arbitration_ctrl);
615         writel(0xFFFFFFFF, &regs->req_limit_mask);
616 
617         for (i = 0; i < ARRAY_SIZE(ddr_max_grant_params); ++i)
618                 writel(ddr_max_grant_params[i], &regs->max_grant_len[i]);
619 
620         writel(MCR50_RESET_ALL_INTR, &regs->intr_ctrl);
621 
622         /* FIXME: the sample code does NOT match the datasheet */
623         writel(0x7FFFFFF, &regs->ecc_range_ctrl);
624 
625         writel(0, &regs->ecc_test_ctrl);
626         writel(0, &regs->test_addr);
627         writel(0, &regs->test_fail_dq_bit);
628         writel(0, &regs->test_init_val);
629 
630         writel(0xFFFFFFFF, &regs->req_input_ctrl);
631         writel(0, &regs->req_high_pri_ctrl);
632 
633 #ifdef AST2600_SDRAMMC_FPGA
634         //writel(0xFF, 0x1e6e0100);
635 #endif
636         udelay(500);
637 
638 	/* set capacity to the max size */
639         clrsetbits_le32(&regs->config, SDRAM_CONF_CAP_MASK,
640                         SDRAM_CONF_CAP_2048M);
641 
642 	/* load controller setting */
643 	for (i = 0; i < ARRAY_SIZE(ddr4_ac_timing); ++i)
644 		writel(ddr4_ac_timing[i], &regs->ac_timing[i]);
645 
646 	writel(DDR4_MR01_MODE, &regs->mr01_mode_setting);
647 	writel(DDR4_MR23_MODE, &regs->mr23_mode_setting);
648 	writel(DDR4_MR45_MODE, &regs->mr45_mode_setting);
649 	writel(DDR4_MR6_MODE, &regs->mr6_mode_setting);
650 }
651 
652 static int ast2600_sdrammc_probe(struct udevice *dev)
653 {
654 	struct reset_ctl reset_ctl;
655 	struct dram_info *priv = (struct dram_info *)dev_get_priv(dev);
656 	struct ast2600_sdrammc_regs *regs = priv->regs;
657 	struct udevice *clk_dev;
658 	int ret = clk_get_by_index(dev, 0, &priv->ddr_clk);
659 	uint32_t reg;
660 
661 	if (ret) {
662 		debug("DDR:No CLK\n");
663 		return ret;
664 	}
665 
666 	/* find SCU base address from clock device */
667 	ret = uclass_get_device_by_driver(UCLASS_CLK, DM_GET_DRIVER(aspeed_scu),
668                                           &clk_dev);
669 	if (ret) {
670 		debug("clock device not defined\n");
671 		return ret;
672 	}
673 
674 	priv->scu = devfdt_get_addr_ptr(clk_dev);
675 	if (IS_ERR(priv->scu)) {
676 		debug("%s(): can't get SCU\n", __func__);
677 		return PTR_ERR(priv->scu);
678 	}
679 
680 	if (readl(priv->scu + AST_SCU_HANDSHAKE) & SCU_SDRAM_INIT_READY_MASK) {
681 		debug("%s(): DDR SDRAM had been initialized\n", __func__);
682 		ast2600_sdrammc_calc_size(priv);
683 		return 0;
684 	}
685 
686 #ifdef AST2600_SDRAMMC_MANUAL_CLK
687 	reg = readl(priv->scu + AST_SCU_MPLL);
688 	reg |= (SCU_MPLL_RESET | SCU_MPLL_TURN_OFF);
689 	writel(reg, priv->scu + AST_SCU_MPLL);
690 	reg &= ~(SCU_MPLL_RESET | SCU_MPLL_TURN_OFF| SCU_MPLL_FREQ_MASK);
691 	reg |= SCU_MPLL_FREQ_CFG;
692 	writel(reg, priv->scu + AST_SCU_MPLL);
693 #else
694 	clk_set_rate(&priv->ddr_clk, priv->clock_rate);
695 #endif
696 
697 #if 0
698 	/* FIXME: enable the following code if reset-driver is ready */
699 	ret = reset_get_by_index(dev, 0, &reset_ctl);
700 	if (ret) {
701 		debug("%s(): Failed to get reset signal\n", __func__);
702 		return ret;
703 	}
704 
705 	ret = reset_assert(&reset_ctl);
706 	if (ret) {
707 		debug("%s(): SDRAM reset failed: %u\n", __func__, ret);
708 		return ret;
709 	}
710 #endif
711 
712 	ast2600_sdrammc_unlock(priv);
713 	ast2600_sdrammc_common_init(regs);
714 
715 	if (readl(priv->scu + AST_SCU_HW_STRAP) & SCU_HWSTRAP_DDR3) {
716 		debug("Unsupported SDRAM type: DDR3\n");
717 		return -EINVAL;
718 	} else {
719 		ast2600_sdrammc_init_ddr4(priv);
720 	}
721 
722 #ifdef AST2600_SDRAMMC_FPGA
723         ast2600_sdrammc_search_read_window(priv);
724 #endif
725 
726 	ast2600_sdramphy_show_status(priv);
727 	ast2600_sdrammc_calc_size(priv);
728 #if 0
729 	ast2600_sdrammc_test(priv);
730 #endif
731 	clrbits_le32(&regs->intr_ctrl, MCR50_RESET_ALL_INTR);
732 	ast2600_sdrammc_lock(priv);
733 	return 0;
734 }
735 
736 static int ast2600_sdrammc_ofdata_to_platdata(struct udevice *dev)
737 {
738 	struct dram_info *priv = dev_get_priv(dev);
739 	int ret;
740 
741 	priv->regs = (void *)(uintptr_t)devfdt_get_addr_index(dev, 0);
742 	priv->phy_setting = (void *)(uintptr_t)devfdt_get_addr_index(dev, 1);
743 	priv->phy_status = (void *)(uintptr_t)devfdt_get_addr_index(dev, 2);
744 
745 	priv->clock_rate = fdtdec_get_int(gd->fdt_blob, dev_of_offset(dev),
746 					  "clock-frequency", 0);
747 	if (!priv->clock_rate) {
748 		debug("DDR Clock Rate not defined\n");
749 		return -EINVAL;
750 	}
751 
752 	return 0;
753 }
754 
755 static int ast2600_sdrammc_get_info(struct udevice *dev, struct ram_info *info)
756 {
757 	struct dram_info *priv = dev_get_priv(dev);
758 
759 	*info = priv->info;
760 
761 	return 0;
762 }
763 
764 static struct ram_ops ast2600_sdrammc_ops = {
765 	.get_info = ast2600_sdrammc_get_info,
766 };
767 
768 static const struct udevice_id ast2600_sdrammc_ids[] = {
769 	{ .compatible = "aspeed,ast2600-sdrammc" },
770 	{ }
771 };
772 
773 U_BOOT_DRIVER(sdrammc_ast2600) = {
774 	.name = "aspeed_ast2600_sdrammc",
775 	.id = UCLASS_RAM,
776 	.of_match = ast2600_sdrammc_ids,
777 	.ops = &ast2600_sdrammc_ops,
778 	.ofdata_to_platdata = ast2600_sdrammc_ofdata_to_platdata,
779 	.probe = ast2600_sdrammc_probe,
780 	.priv_auto_alloc_size = sizeof(struct dram_info),
781 };
782